reorder timer initialization so that timer_create does not depend on free
this allows small programs which only create times, but never delete them, to use simple_malloc instead of the full malloc.
This commit is contained in:
parent
1c1aa32eea
commit
680630011d
2 changed files with 17 additions and 9 deletions
|
|
@ -61,21 +61,28 @@ int timer_create(clockid_t clk, struct sigevent *evp, timer_t *res)
|
||||||
struct start_args args;
|
struct start_args args;
|
||||||
timer_t t;
|
timer_t t;
|
||||||
struct ksigevent ksev;
|
struct ksigevent ksev;
|
||||||
|
int timerid;
|
||||||
|
|
||||||
if (evp) sev = *evp;
|
if (evp) sev = *evp;
|
||||||
|
|
||||||
switch (sev.sigev_notify) {
|
switch (sev.sigev_notify) {
|
||||||
case SIGEV_NONE:
|
case SIGEV_NONE:
|
||||||
case SIGEV_SIGNAL:
|
case SIGEV_SIGNAL:
|
||||||
if (!(t = calloc(1, sizeof *t)))
|
|
||||||
return -1;
|
|
||||||
ksev.sigev_value = evp ? sev.sigev_value
|
ksev.sigev_value = evp ? sev.sigev_value
|
||||||
: (union sigval){.sival_ptr=t};
|
: (union sigval){.sival_ptr=t};
|
||||||
ksev.sigev_signo = sev.sigev_signo;
|
ksev.sigev_signo = sev.sigev_signo;
|
||||||
ksev.sigev_notify = sev.sigev_notify;
|
ksev.sigev_notify = sev.sigev_notify;
|
||||||
ksev.sigev_tid = 0;
|
ksev.sigev_tid = 0;
|
||||||
|
if (syscall(SYS_timer_create, clk, &ksev, &timerid) < 0)
|
||||||
|
return -1;
|
||||||
|
if (!(t = calloc(1, sizeof *t))) {
|
||||||
|
syscall(SYS_timer_delete, timerid);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
t->timerid = timerid;
|
||||||
break;
|
break;
|
||||||
case SIGEV_THREAD:
|
case SIGEV_THREAD:
|
||||||
|
if (!libc.sigtimer) libc.sigtimer = sighandler;
|
||||||
if (sev.sigev_notify_attributes)
|
if (sev.sigev_notify_attributes)
|
||||||
attr = *sev.sigev_notify_attributes;
|
attr = *sev.sigev_notify_attributes;
|
||||||
else
|
else
|
||||||
|
|
@ -95,13 +102,14 @@ int timer_create(clockid_t clk, struct sigevent *evp, timer_t *res)
|
||||||
ksev.sigev_signo = SIGCANCEL;
|
ksev.sigev_signo = SIGCANCEL;
|
||||||
ksev.sigev_notify = 4; /* SIGEV_THREAD_ID */
|
ksev.sigev_notify = 4; /* SIGEV_THREAD_ID */
|
||||||
ksev.sigev_tid = td->tid;
|
ksev.sigev_tid = td->tid;
|
||||||
if (!libc.sigtimer) libc.sigtimer = sighandler;
|
if (syscall(SYS_timer_create, clk, &ksev, &t->timerid) < 0) {
|
||||||
|
t->timerid = -1;
|
||||||
|
pthread_cancel(td);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
default:
|
||||||
|
errno = EINVAL;
|
||||||
t->timerid = -1;
|
|
||||||
if (syscall(SYS_timer_create, clk, &ksev, &t->timerid) < 0) {
|
|
||||||
timer_delete(t);
|
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@ int timer_delete(timer_t t)
|
||||||
{
|
{
|
||||||
if (t->thread) pthread_cancel(t->thread);
|
if (t->thread) pthread_cancel(t->thread);
|
||||||
else {
|
else {
|
||||||
if (t->timerid >= 0) __syscall(SYS_timer_delete, t->timerid);
|
__syscall(SYS_timer_delete, t->timerid);
|
||||||
free(t);
|
free(t);
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue