fixed a wrong field name in chan.c that caused a segfault
This commit is contained in:
parent
89a6bf21ab
commit
c7378287dc
2
Makefile
2
Makefile
@ -1,7 +1,7 @@
|
|||||||
SRCS = chan.c ctx.c
|
SRCS = chan.c ctx.c
|
||||||
OBJS = $(SRCS:.c=.o)
|
OBJS = $(SRCS:.c=.o)
|
||||||
|
|
||||||
CFLAGS := -Wall -g
|
CFLAGS := -Wall -g -O3
|
||||||
LDFLAGS :=
|
LDFLAGS :=
|
||||||
LIBS := -lrt
|
LIBS := -lrt
|
||||||
|
|
||||||
|
64
chan.c
64
chan.c
@ -50,10 +50,12 @@ void hip_chan_close(hip_chan_t* c)
|
|||||||
|
|
||||||
int hip_chan_send(hip_chan_t* c, const void* ptr, hip_oow_t len)
|
int hip_chan_send(hip_chan_t* c, const void* ptr, hip_oow_t len)
|
||||||
{
|
{
|
||||||
hip_uctx_t* self;
|
hip_t* hip;
|
||||||
|
hip_uctx_t* caller;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
self = UCTX_FROM_LINK(c->hip->running);
|
hip = c->hip;
|
||||||
|
caller = UCTX_FROM_LINK(hip->running);
|
||||||
|
|
||||||
// TODO: IS BUFFER EMPTY
|
// TODO: IS BUFFER EMPTY
|
||||||
|
|
||||||
@ -62,38 +64,41 @@ int hip_chan_send(hip_chan_t* c, const void* ptr, hip_oow_t len)
|
|||||||
hip_uctx_link_t* x;
|
hip_uctx_link_t* x;
|
||||||
hip_uctx_t* xx;
|
hip_uctx_t* xx;
|
||||||
|
|
||||||
/* remove the receiving routine from the queue and make it runnable */
|
|
||||||
x = HIP_LIST_HEAD(&c->recvq);
|
x = HIP_LIST_HEAD(&c->recvq);
|
||||||
HIP_LIST_UNCHAIN(x);
|
|
||||||
HIP_LIST_ADD_BACK(x, &c->hip->runnables);
|
|
||||||
|
|
||||||
xx = UCTX_FROM_LINK(x);
|
xx = UCTX_FROM_LINK(x);
|
||||||
|
|
||||||
if (len > xx->chan_data_len) len = xx->chan_data_len;
|
if (len > xx->chan_data_len) len = xx->chan_data_len;
|
||||||
memcpy(xx->chan_data_ptr, ptr, len);
|
memcpy(xx->chan_data_ptr, ptr, len);
|
||||||
|
//printf ("USE SEND CHAT CALLER %p RECEIVER %p RET %p\n", caller, xx, xx->chan_ret_ptr);
|
||||||
*(xx->chan_ret_ptr) = len; /* manipulate the return value of the receiver */
|
*(xx->chan_ret_ptr) = len; /* manipulate the return value of the receiver */
|
||||||
|
|
||||||
hip_yield(c->hip); /* let other routines go first */
|
/* remove the receiving routine from the queue and make it runnable */
|
||||||
|
HIP_LIST_UNCHAIN(x);
|
||||||
|
HIP_LIST_ADD_BACK(x, &hip->runnables);
|
||||||
|
hip_yield(hip); /* let other routines go first */
|
||||||
return len;
|
return len;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/* remember the data holder and places the current running routine in the send queue */
|
/* remember the data holder and places the current running routine in the send queue */
|
||||||
self->chan_data_ptr = (hip_uint8_t*)ptr;
|
caller->chan_data_ptr = (hip_uint8_t*)ptr;
|
||||||
self->chan_data_len = len;
|
caller->chan_data_len = len;
|
||||||
self->chan_ret_ptr = &ret; /* remember the pointer to the return value holder to be set by the receiver */
|
caller->chan_ret_ptr = &ret; /* remember the pointer to the return value holder to be set by the receiver */
|
||||||
HIP_LIST_ADD_BACK(c->hip->running, &c->sendq);
|
//printf ("REMEMBER SEND CHAT caller %p RET %p\n", caller, caller->chan_ret_ptr);
|
||||||
|
|
||||||
hip_switch(c->hip);
|
hip_switch(hip, &c->sendq);
|
||||||
|
//printf ("CALLER RETURNNING SEND caller %p, ret %p/%p => %d\n", caller, caller->chan_ret_ptr, &ret, ret);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int hip_chan_recv(hip_chan_t* c, void* ptr, hip_oow_t len)
|
int hip_chan_recv(hip_chan_t* c, void* ptr, hip_oow_t len)
|
||||||
{
|
{
|
||||||
hip_uctx_t* self;
|
hip_t* hip;
|
||||||
|
hip_uctx_t* caller;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
self = UCTX_FROM_LINK(c->hip->running);
|
hip = c->hip;
|
||||||
|
caller = UCTX_FROM_LINK(hip->running);
|
||||||
|
|
||||||
/* TODO: IS THERE DATA IN BUFFER ? */
|
/* TODO: IS THERE DATA IN BUFFER ? */
|
||||||
|
|
||||||
@ -104,26 +109,35 @@ int hip_chan_recv(hip_chan_t* c, void* ptr, hip_oow_t len)
|
|||||||
|
|
||||||
/* remove the sending routine from the queue and make it runnable */
|
/* remove the sending routine from the queue and make it runnable */
|
||||||
x = HIP_LIST_HEAD(&c->sendq);
|
x = HIP_LIST_HEAD(&c->sendq);
|
||||||
HIP_LIST_UNCHAIN(x);
|
|
||||||
HIP_LIST_ADD_BACK(x, &c->hip->runnables);
|
|
||||||
|
|
||||||
xx = UCTX_FROM_LINK(x);
|
|
||||||
|
|
||||||
/* copy the data from the sending routine's buffer */
|
/* copy the data from the sending routine's buffer */
|
||||||
|
xx = UCTX_FROM_LINK(x);
|
||||||
if (len > xx->chan_data_len) len = xx->chan_data_len; /* TODO: do something else instead of simple truncation */
|
if (len > xx->chan_data_len) len = xx->chan_data_len; /* TODO: do something else instead of simple truncation */
|
||||||
memcpy(ptr, xx->chan_data_ptr, len);
|
memcpy(ptr, xx->chan_data_ptr, len);
|
||||||
*(xx->chan_data_ptr) = len; /* manipulate the return value of the sender */
|
//printf ("USE RECV CHAT caller %p sender %p RET %p\n",caller, xx, xx->chan_ret_ptr);
|
||||||
|
*(xx->chan_ret_ptr) = len; /* manipulate the return value of the sender */
|
||||||
|
|
||||||
hip_yield(c->hip); /* let other routines go first */
|
HIP_LIST_UNCHAIN(x);
|
||||||
|
HIP_LIST_ADD_BACK(x, &hip->runnables);
|
||||||
|
hip_yield(hip); /* let other routines go first */
|
||||||
return len;
|
return len;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* remember the data holder and place the calling routine in the receive queue */
|
/* remember the data holder and place the calling routine in the receive queue */
|
||||||
self->chan_data_ptr = ptr;
|
caller->chan_data_ptr = ptr;
|
||||||
self->chan_data_len = len;
|
caller->chan_data_len = len;
|
||||||
self->chan_ret_ptr = &ret; /* remember the pointer to the return value holder to be set by the sender */
|
caller->chan_ret_ptr = &ret; /* remember the pointer to the return value holder to be set by the sender */
|
||||||
HIP_LIST_ADD_BACK(c->hip->running, &c->recvq);
|
//printf ("REMEMBER RECV caller %p CHAT RET %p\n", caller, caller->chan_ret_ptr);
|
||||||
|
|
||||||
hip_switch(c->hip); /* switch to the scheduler */
|
hip_switch(hip, &c->recvq); /* switch to the scheduler */
|
||||||
|
//printf ("CALLER RETURNNING RECV caller %p, ret %p/%p => %d\n", caller, caller->chan_ret_ptr, &ret, ret);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
int hip_chan_select(hip_chan_t* chans, hip_oow_t count, int nonblock)
|
||||||
|
{
|
||||||
|
/* returns the index to the chan that has data to read */
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
151
ctx.c
151
ctx.c
@ -36,12 +36,13 @@ static void invoke_uf(unsigned int a, unsigned int b)
|
|||||||
#else
|
#else
|
||||||
uctx = (hip_uctx_t*)(((hip_oow_t)a << 32) | (hip_oow_t)b);
|
uctx = (hip_uctx_t*)(((hip_oow_t)a << 32) | (hip_oow_t)b);
|
||||||
#endif
|
#endif
|
||||||
|
printf ("invoke_uf START ...%p\n", uctx);
|
||||||
uctx->uf(uctx, uctx->ctx);
|
uctx->uf(uctx, uctx->ctx);
|
||||||
|
|
||||||
printf ("invoke_uf XXXXXXXXXXXXXXXXXXXXX...%p\n", uctx);
|
printf ("invoke_uf DONE ...%p\n", uctx);
|
||||||
//TODO: This part must not be interrupted by the timer handler???
|
//TODO: This part must not be interrupted by the timer handler???
|
||||||
hip = uctx->hip;
|
hip = uctx->hip;
|
||||||
if (uctx == hip->uctx_sched) /* if not the scheduler itself */
|
if (uctx == hip->uctx_sched) /* if not the scheduler itcaller */
|
||||||
{
|
{
|
||||||
/* back to where the schedule got activated for the first time */
|
/* back to where the schedule got activated for the first time */
|
||||||
setcontext(&hip->uc_main);
|
setcontext(&hip->uc_main);
|
||||||
@ -58,13 +59,14 @@ printf ("invoke_uf XXXXXXXXXXXXXXXXXXXXX...%p\n", uctx);
|
|||||||
|
|
||||||
if (uctx->flags & HIP_RTN_FLAG_AUTO_DESTROY)
|
if (uctx->flags & HIP_RTN_FLAG_AUTO_DESTROY)
|
||||||
{
|
{
|
||||||
|
//printf (">>>>>>>>>> *********************** AUTHO DESTROYING UCTX %p\n", uctx);
|
||||||
hip_uctx_close(uctx);
|
hip_uctx_close(uctx);
|
||||||
printf (">>>>>>>>>> *********************** CLOSED TERMINATED\n");
|
//printf (">>>>>>>>>> *********************** CLOSED TERMINATED %p\n", uctx);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
HIP_LIST_ADD_BACK(&uctx->uctx, &hip->terminated);
|
HIP_LIST_ADD_BACK(&uctx->uctx, &hip->terminated);
|
||||||
printf (">>>>>>>>>> ************************ ADDED TO TERMINATED\n");
|
//printf (">>>>>>>>>> ************************ ADDED TO TERMINATED\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
setcontext(&hip->uctx_sched->uc); /* switch to the scheduler */
|
setcontext(&hip->uctx_sched->uc); /* switch to the scheduler */
|
||||||
@ -78,50 +80,53 @@ printf (">>>>>>>>>> ************************ ADDED TO TERMINATED\n");
|
|||||||
|
|
||||||
hip_uctx_t* hip_uctx_open(hip_t* hip, hip_oow_t stack_size, int flags, hip_ufun_t uf, void* ctx)
|
hip_uctx_t* hip_uctx_open(hip_t* hip, hip_oow_t stack_size, int flags, hip_ufun_t uf, void* ctx)
|
||||||
{
|
{
|
||||||
hip_uctx_t* uc;
|
hip_uctx_t* uctx;
|
||||||
void* sp;
|
void* sp;
|
||||||
|
|
||||||
uc = (hip_uctx_t*)malloc(HIP_SIZEOF(*uc) + stack_size);
|
uctx = (hip_uctx_t*)malloc(HIP_SIZEOF(*uctx) + stack_size);
|
||||||
if (!uc) return HIP_NULL;
|
if (HIP_UNLIKELY(!uctx)) return HIP_NULL;
|
||||||
sp = (void*)(uc + 1);
|
printf ("MALLOC UCTX %p\n", uctx);
|
||||||
|
|
||||||
memset(uc, 0, HIP_SIZEOF(*uc) + stack_size);
|
sp = (void*)(uctx + 1);
|
||||||
uc->hip = hip;
|
|
||||||
uc->flags = flags;
|
|
||||||
uc->uf = uf;
|
|
||||||
uc->ctx = ctx;
|
|
||||||
uc->waiting_fd = HIP_INVALID_FD;
|
|
||||||
|
|
||||||
getcontext(&uc->uc);
|
memset(uctx, 0, HIP_SIZEOF(*uctx) + stack_size);
|
||||||
|
uctx->hip = hip;
|
||||||
|
uctx->flags = flags;
|
||||||
|
uctx->uf = uf;
|
||||||
|
uctx->ctx = ctx;
|
||||||
|
uctx->waiting_fd = HIP_INVALID_FD;
|
||||||
|
|
||||||
|
getcontext(&uctx->uc);
|
||||||
|
|
||||||
if (uf)
|
if (uf)
|
||||||
{
|
{
|
||||||
sigemptyset (&uc->uc.uc_sigmask);
|
sigemptyset (&uctx->uc.uc_sigmask);
|
||||||
// sigaddset (&uc->uc.uc_sigmask, SIGRTMIN); /* block SIGRTMIN. TODO: take this value from the outer scheduler object? */
|
// sigaddset (&uctx->uc.uc_sigmask, SIGRTMIN); /* block SIGRTMIN. TODO: take this value from the outer scheduler object? */
|
||||||
|
|
||||||
uc->stid = VALGRIND_STACK_REGISTER(sp, (hip_uint8_t*)sp + stack_size);
|
uctx->stid = VALGRIND_STACK_REGISTER(sp, (hip_uint8_t*)sp + stack_size);
|
||||||
uc->uc.uc_stack.ss_sp = sp;
|
uctx->uc.uc_stack.ss_sp = sp;
|
||||||
uc->uc.uc_stack.ss_size = stack_size;
|
uctx->uc.uc_stack.ss_size = stack_size;
|
||||||
uc->uc.uc_stack.ss_flags = 0;
|
uctx->uc.uc_stack.ss_flags = 0;
|
||||||
uc->uc.uc_link = HIP_NULL;
|
uctx->uc.uc_link = HIP_NULL;
|
||||||
#if (MKCTX_NARGS <= 1)
|
#if (MKCTX_NARGS <= 1)
|
||||||
makecontext(&uc->uc, (void(*)(void))invoke_uf, 1, uc);
|
makecontext(&uctx->uc, (void(*)(void))invoke_uf, 1, uctx);
|
||||||
#else
|
#else
|
||||||
makecontext(&uc->uc, (void(*)(void))invoke_uf, 2, (unsigned int)((hip_oow_t)uc >> 32), (unsigned int)((hip_oow_t)uc & 0xFFFFFFFFu));
|
makecontext(&uctx->uc, (void(*)(void))invoke_uf, 2, (unsigned int)((hip_oow_t)uctx >> 32), (unsigned int)((hip_oow_t)uctx & 0xFFFFFFFFu));
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
printf("NEW UCTX %p\n", uc);
|
printf("NEW UCTX %p\n", uctx);
|
||||||
return uc;
|
return uctx;
|
||||||
}
|
}
|
||||||
|
|
||||||
void hip_uctx_close(hip_uctx_t* uctx)
|
void hip_uctx_close(hip_uctx_t* uctx)
|
||||||
{
|
{
|
||||||
if (uctx->uf)
|
//printf ("HIP_UCTX_CLOSE %p\n", uctx);
|
||||||
{
|
if (uctx->uf) VALGRIND_STACK_DEREGISTER(uctx->stid);
|
||||||
VALGRIND_STACK_DEREGISTER(uctx->stid);
|
|
||||||
}
|
//printf("FREEING UCTX %p\n", uctx);
|
||||||
free(uctx);
|
free(uctx);
|
||||||
|
//printf("FREEED UCTX %p\n", uctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
void hip_uctx_swap(hip_uctx_t* uc, hip_uctx_t* new_uc)
|
void hip_uctx_swap(hip_uctx_t* uc, hip_uctx_t* new_uc)
|
||||||
@ -318,11 +323,12 @@ hip_t* hip_open(int flags)
|
|||||||
|
|
||||||
hip = (hip_t*)malloc(HIP_SIZEOF(*hip));
|
hip = (hip_t*)malloc(HIP_SIZEOF(*hip));
|
||||||
if (!hip) return HIP_NULL;
|
if (!hip) return HIP_NULL;
|
||||||
|
printf ("MALLOC HIP %p\n", hip);
|
||||||
|
|
||||||
memset(hip, 0, HIP_SIZEOF(*hip));
|
memset(hip, 0, HIP_SIZEOF(*hip));
|
||||||
hip->flags = flags;
|
hip->flags = flags;
|
||||||
|
|
||||||
/* initialize to an empty list by making each pointer point to itself.*/
|
/* initialize to an empty list by making each pointer point to itcaller.*/
|
||||||
HIP_LIST_INIT(&hip->runnables);
|
HIP_LIST_INIT(&hip->runnables);
|
||||||
HIP_LIST_INIT(&hip->terminated);
|
HIP_LIST_INIT(&hip->terminated);
|
||||||
HIP_LIST_INIT(&hip->sleeping);
|
HIP_LIST_INIT(&hip->sleeping);
|
||||||
@ -364,6 +370,7 @@ hip_t* hip_open(int flags)
|
|||||||
if (hip->mux_id <= -1)
|
if (hip->mux_id <= -1)
|
||||||
{
|
{
|
||||||
timer_delete(tid);
|
timer_delete(tid);
|
||||||
|
printf("FREEING HIP %p\n", hip);
|
||||||
free(hip);
|
free(hip);
|
||||||
return HIP_NULL;
|
return HIP_NULL;
|
||||||
}
|
}
|
||||||
@ -434,6 +441,7 @@ void hip_close(hip_t* hip)
|
|||||||
|
|
||||||
if (hip->uctx_mux) hip_uctx_close(hip->uctx_mux);
|
if (hip->uctx_mux) hip_uctx_close(hip->uctx_mux);
|
||||||
if (hip->uctx_sched) hip_uctx_close(hip->uctx_sched);
|
if (hip->uctx_sched) hip_uctx_close(hip->uctx_sched);
|
||||||
|
printf("FREEING HIP2 %p\n", hip);
|
||||||
free(hip);
|
free(hip);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -441,7 +449,7 @@ hip_uctx_t* hip_newrtn(hip_t* hip, int flags, hip_ufun_t uf, void* ctx)
|
|||||||
{
|
{
|
||||||
hip_uctx_t* uctx;
|
hip_uctx_t* uctx;
|
||||||
|
|
||||||
uctx = hip_uctx_open(hip, 8192, flags, uf, ctx); /* TODO: stack size */
|
uctx = hip_uctx_open(hip, 65535, flags, uf, ctx); /* TODO: stack size */
|
||||||
if (!uctx) return HIP_NULL;
|
if (!uctx) return HIP_NULL;
|
||||||
|
|
||||||
/* append to the list */
|
/* append to the list */
|
||||||
@ -493,28 +501,48 @@ int hip_schedule(hip_t* hip, int preempt)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void hip_yield(hip_t* hip)
|
|
||||||
|
void hip_switch(hip_t* hip, hip_uctx_link_t* list_to_deposit)
|
||||||
{
|
{
|
||||||
hip_uctx_t* rr;
|
hip_uctx_t* caller;
|
||||||
assert (hip->running != HIP_NULL);
|
assert (hip->running != HIP_NULL);
|
||||||
|
|
||||||
/* switch from the running context to the scheduler context */
|
/* switch from the running context to the scheduler context */
|
||||||
HIP_LIST_ADD_BACK(hip->running, &hip->runnables);
|
HIP_LIST_ADD_BACK(hip->running, list_to_deposit);
|
||||||
rr = UCTX_FROM_LINK(hip->running);
|
caller = UCTX_FROM_LINK(hip->running);
|
||||||
|
|
||||||
/* TODO: extract these lines to a macro or something */
|
/* TODO: extract these lines to a macro or something */
|
||||||
rr->cso++;
|
caller->cso++;
|
||||||
hip->uctx_sched->csi++;
|
hip->uctx_sched->csi++;
|
||||||
swapcontext(&rr->uc, &hip->uctx_sched->uc);
|
swapcontext(&caller->uc, &hip->uctx_sched->uc);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void hip_yield(hip_t* hip)
|
||||||
|
{
|
||||||
|
hip_switch(hip, &hip->runnables);
|
||||||
|
#if 0
|
||||||
|
hip_uctx_t* caller;
|
||||||
|
/* the caller must deal with hip->running before calling this function */
|
||||||
|
caller = UCTX_FROM_LINK(hip->running);
|
||||||
|
hip->running = HIP_NULL;
|
||||||
|
swapcontext(&caller->uc, &hip->uctx_sched->uc); /* switch to the scheduler */
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
void hip_suspend(hip_t* hip)
|
||||||
|
{
|
||||||
|
/* TODO: this isn't needed as of now. delete it if it's not really needed eventually */
|
||||||
|
hip_switch(hip, &hip->suspended);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void hip_sleep(hip_t* hip, hip_nsecdur_t nsecs)
|
void hip_sleep(hip_t* hip, hip_nsecdur_t nsecs)
|
||||||
{
|
{
|
||||||
hip_uctx_t* rr;
|
hip_uctx_t* caller;
|
||||||
assert (hip->running != HIP_NULL);
|
assert (hip->running != HIP_NULL);
|
||||||
|
|
||||||
rr = UCTX_FROM_LINK(hip->running);
|
caller = UCTX_FROM_LINK(hip->running);
|
||||||
rr->wakeup_time = monotime() + nsecs;
|
caller->wakeup_time = monotime() + nsecs;
|
||||||
|
|
||||||
/* TODO: switch to HEAP. for now simply linear search to keep this list sorted. */
|
/* TODO: switch to HEAP. for now simply linear search to keep this list sorted. */
|
||||||
if (!HIP_LIST_IS_EMPTY(&hip->sleeping))
|
if (!HIP_LIST_IS_EMPTY(&hip->sleeping))
|
||||||
@ -524,7 +552,7 @@ void hip_sleep(hip_t* hip, hip_nsecdur_t nsecs)
|
|||||||
for (l = HIP_LIST_HEAD(&hip->sleeping); l != &hip->sleeping; l = l->next)
|
for (l = HIP_LIST_HEAD(&hip->sleeping); l != &hip->sleeping; l = l->next)
|
||||||
{
|
{
|
||||||
r = UCTX_FROM_LINK(l);
|
r = UCTX_FROM_LINK(l);
|
||||||
if (rr->wakeup_time <= r->wakeup_time)
|
if (caller->wakeup_time <= r->wakeup_time)
|
||||||
{
|
{
|
||||||
HIP_LIST_CHAIN(hip->running, l->prev, l);
|
HIP_LIST_CHAIN(hip->running, l->prev, l);
|
||||||
goto do_sched;
|
goto do_sched;
|
||||||
@ -536,22 +564,7 @@ void hip_sleep(hip_t* hip, hip_nsecdur_t nsecs)
|
|||||||
|
|
||||||
do_sched:
|
do_sched:
|
||||||
hip->running = HIP_NULL;
|
hip->running = HIP_NULL;
|
||||||
swapcontext(&rr->uc, &hip->uctx_sched->uc); /* switch to the scheduler */
|
swapcontext(&caller->uc, &hip->uctx_sched->uc); /* switch to the scheduler */
|
||||||
}
|
|
||||||
|
|
||||||
void hip_suspend(hip_t* hip)
|
|
||||||
{
|
|
||||||
HIP_LIST_ADD_BACK(hip->running, &hip->suspended);
|
|
||||||
hip_switch(hip);
|
|
||||||
}
|
|
||||||
|
|
||||||
void hip_switch(hip_t* hip)
|
|
||||||
{
|
|
||||||
hip_uctx_t* rr;
|
|
||||||
/* the caller must deal with hip->running before calling this function */
|
|
||||||
rr = UCTX_FROM_LINK(hip->running);
|
|
||||||
hip->running = HIP_NULL;
|
|
||||||
swapcontext(&rr->uc, &hip->uctx_sched->uc); /* switch to the scheduler */
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void hip_awaitio(hip_t* hip, int fd, int flags)
|
void hip_awaitio(hip_t* hip, int fd, int flags)
|
||||||
@ -712,7 +725,6 @@ static void uf1(hip_uctx_t* uc, void* ctx)
|
|||||||
{
|
{
|
||||||
hip_chan_t* chan;
|
hip_chan_t* chan;
|
||||||
int i;
|
int i;
|
||||||
char buf[32];
|
|
||||||
|
|
||||||
chan = (hip_chan_t*)ctx;
|
chan = (hip_chan_t*)ctx;
|
||||||
|
|
||||||
@ -726,9 +738,15 @@ printf (">> UF1 SEC [%d]\n", i);
|
|||||||
hip_sleep(uc->hip, 1000000000);
|
hip_sleep(uc->hip, 1000000000);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
int n;
|
||||||
|
char buf[32];
|
||||||
printf (">> UF1 ALMOST DONE. WAITING FOR UF3\n");
|
printf (">> UF1 ALMOST DONE. WAITING FOR UF3\n");
|
||||||
i = hip_chan_recv(chan, buf, sizeof(buf));
|
n = hip_chan_recv(chan, buf, sizeof(buf));
|
||||||
printf (">> UF1 RECEIVED [%.*s]\n", (int)i, buf);
|
printf (">> UF1 RECEIVED [%.*s]\n", (int)i, buf);
|
||||||
|
n = hip_chan_send(chan, "holy cow", 8);
|
||||||
|
printf (">> UF1 SENT [%d]\n", (int)n);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void uf2(hip_uctx_t* uc, void* ctx)
|
static void uf2(hip_uctx_t* uc, void* ctx)
|
||||||
@ -756,6 +774,7 @@ static void uf3(hip_uctx_t* uc, void* ctx)
|
|||||||
hip = uc->hip;
|
hip = uc->hip;
|
||||||
chan = (hip_chan_t*)ctx;
|
chan = (hip_chan_t*)ctx;
|
||||||
|
|
||||||
|
#if 0
|
||||||
memset(&sa, 0, HIP_SIZEOF(sa));
|
memset(&sa, 0, HIP_SIZEOF(sa));
|
||||||
sa.sin_family = AF_INET;
|
sa.sin_family = AF_INET;
|
||||||
sa.sin_addr.s_addr = inet_addr("142.250.206.196");
|
sa.sin_addr.s_addr = inet_addr("142.250.206.196");
|
||||||
@ -784,6 +803,7 @@ printf ("*********CONNECTED>>>>>>>>>>>>>>>\n");
|
|||||||
}
|
}
|
||||||
socket_close(hip, fd);
|
socket_close(hip, fd);
|
||||||
printf ("*********DISCONNECTED>>>>>>>>>>>>>>>\n");
|
printf ("*********DISCONNECTED>>>>>>>>>>>>>>>\n");
|
||||||
|
#endif
|
||||||
|
|
||||||
for (i = 0; i < 15; i++)
|
for (i = 0; i < 15; i++)
|
||||||
{
|
{
|
||||||
@ -796,7 +816,15 @@ hip_sleep(uc->hip, 1000000000);
|
|||||||
if (i == 8) hip_newrtn(uc->hip, HIP_RTN_FLAG_AUTO_DESTROY, uf2, HIP_NULL);
|
if (i == 8) hip_newrtn(uc->hip, HIP_RTN_FLAG_AUTO_DESTROY, uf2, HIP_NULL);
|
||||||
}
|
}
|
||||||
printf (">> UF3 DONE DONE\n");
|
printf (">> UF3 DONE DONE\n");
|
||||||
hip_chan_send(chan, "hello", 5);
|
|
||||||
|
{
|
||||||
|
int n;
|
||||||
|
char buf[64];
|
||||||
|
n = hip_chan_send(chan, "hello", 5);
|
||||||
|
printf (">> UF3 SENT %d\n", (int)n);
|
||||||
|
n = hip_chan_recv(chan, buf, sizeof(buf));
|
||||||
|
printf (">> UF3 RECV [%.*s]\n", (int)n, buf);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int main()
|
int main()
|
||||||
@ -804,6 +832,7 @@ int main()
|
|||||||
hip_t* hip;
|
hip_t* hip;
|
||||||
hip_chan_t* chan;
|
hip_chan_t* chan;
|
||||||
|
|
||||||
|
setbuf(stdout, NULL);
|
||||||
hip = hip_open(HIP_FLAG_LAZY);
|
hip = hip_open(HIP_FLAG_LAZY);
|
||||||
chan = hip_chan_open(hip, 100);
|
chan = hip_chan_open(hip, 100);
|
||||||
|
|
||||||
|
2
hip.h
2
hip.h
@ -114,7 +114,7 @@ void hip_uctx_close(hip_uctx_t* uctx);
|
|||||||
|
|
||||||
void hip_yield(hip_t* hip);
|
void hip_yield(hip_t* hip);
|
||||||
void hip_sleep(hip_t* hip, hip_nsecdur_t nsecs);
|
void hip_sleep(hip_t* hip, hip_nsecdur_t nsecs);
|
||||||
void hip_switch(hip_t* hip);
|
void hip_switch(hip_t* hip, hip_uctx_link_t* list_to_deposit);
|
||||||
void hip_suspend(hip_t* hip);
|
void hip_suspend(hip_t* hip);
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user