コード例 #1
0
ファイル: Coro.c プロジェクト: doublec/io
void Coro_setup(Coro *self, void *arg)
{
	ucontext_t *ucp = (ucontext_t *) &self->env;

	getcontext(ucp);

	ucp->uc_stack.ss_sp    = Coro_stack(self) + Coro_stackSize(self) - 8;
	ucp->uc_stack.ss_size  = Coro_stackSize(self);
	ucp->uc_stack.ss_flags = 0;
	ucp->uc_link = NULL;

	makecontext(ucp, (makecontext_func)Coro_StartWithArg, 1, arg); }
コード例 #2
0
ファイル: Coro.c プロジェクト: asymmetric/io
// This isn't bulletproof, but seems to work Well Enough (TM)
void Coro_setup(Coro *self, void *arg)
{
        uintptr_t stackend = Coro_stackSize(self) + (uintptr_t)Coro_stack(self);
        uintptr_t start = (uintptr_t)Coro_Start;
        /* since ucontext seems to be broken on amd64 */
        globalCallbackBlock.context=((CallbackBlock*)arg)->context;
        globalCallbackBlock.func=((CallbackBlock*)arg)->func;
        setjmp(self->env);
end:
        {
                uintptr_t i;
                uintptr_t * sav = (uintptr_t*)self->env;
                size_t sz = sizeof(self->env)/sizeof(sav[0]);

                // Try to guess PC index
                i = sz;
                while (i--)
                        if (sav[i] == (uintptr_t)&&end)
                                break;
                assert(i < sz);
                sav[i] = start;

                // Try to guess SP index
                i = sz;
                while (i--)
                        if (64 > (- sav[i] + (uintptr_t)&i))
                                break;
                assert(i < sz);
                sav[i] = stackend - sizeof(uintptr_t) - 128;
        }
}
コード例 #3
0
ファイル: Coro.c プロジェクト: ADTSH/io
void Coro_setup(Coro *self, void *arg)
{
	uintptr_t stackend = Coro_stackSize(self) + (uintptr_t)Coro_stack(self);
	uintptr_t start = (uintptr_t)Coro_Start;
	/* since ucontext seems to be broken on amd64 */
	globalCallbackBlock.context=((CallbackBlock*)arg)->context;
	globalCallbackBlock.func=((CallbackBlock*)arg)->func;

	setjmp(self->env);
	/* This is probably not nice in that it deals directly with
	* something with __ in front of it.
	*
	* Anyhow, Coro.h makes the member env of a struct Coro a
	* jmp_buf. A jmp_buf, as defined in the amd64 setjmp.h
	* is an array of one struct that wraps the actual __jmp_buf type
	* which is the array of longs (on a 64 bit machine) that
	* the programmer below expected. This struct begins with
	* the __jmp_buf array of longs, so I think it was supposed
	* to work like he originally had it, but for some reason
	* it didn't. I don't know why.
	* - Bryce Schroeder, 16 December 2006
	*
	*   Explaination of `magic' numbers: 6 is the stack pointer
	*   (RSP, the 64 bit equivalent of ESP), 7 is the program counter.
	*   This information came from this file on my Gentoo linux
	*   amd64 computer:
	*   /usr/include/gento-multilib/amd64/bits/setjmp.h
	*   Which was ultimatly included from setjmp.h in /usr/include. */

	self->env[0].__jmpbuf[6] = ((unsigned long)(Coro_stack(self)));
	self->env[0].__jmpbuf[7] = ((long)Coro_Start);
}
コード例 #4
0
ファイル: Coro.c プロジェクト: doublec/io
void Coro_setup(Coro *self, void *arg)
{
	setjmp(buf);
	buf[7] = (long)(Coro_stack(self) + Coro_stackSize(self) - 16);
	buf[8] = (long)Coro_Start;
	globalCallbackBlock.context=((CallbackBlock*)arg)->context;
	globalCallbackBlock.func=((CallbackBlock*)arg)->func;
}
コード例 #5
0
ファイル: Coro.c プロジェクト: doublec/io
void Coro_setup(Coro *self, void *arg)
{
	void *stack = Coro_stack(self);
	size_t stacksize = Coro_stackSize(self);
	void *func = (void *)Coro_Start;

	setjmp(buf);

	buf->_jb[2] = (long)(stack + stacksize);
	buf->_jb[0] = (long)func;
	return;
}
コード例 #6
0
ファイル: Coro.c プロジェクト: asymmetric/io
void Coro_setup(Coro *self, void *arg)
{
  void *stack = Coro_stack(self);
  size_t stacksize = Coro_stackSize(self);
  void *func = (void *)Coro_Start;
  
  setjmp(buf);
  
  buf[2] = (long)(stack + stacksize);
  buf[0] = (long)Coro_Start;
  // it would seem this needs to have some value??
  globalCallbackBlock.context=((CallbackBlock*)arg)->context;
  globalCallbackBlock.func=((CallbackBlock*)arg)->func;
  return;
}
コード例 #7
0
ファイル: Coro.c プロジェクト: doublec/io
void Coro_setup(Coro *self, void *arg)
{
	/*
	setjmp/longjmp is flakey under Symbian.
	If the setjmp is done inside the call then a crash occurs.
	Inlining it here solves the problem
	*/

	setjmp(self->env);
	self->env[0] = 0;
	self->env[1] = 0;
	self->env[2] = 0;
	self->env[3] = (unsigned long)(Coro_stack(self))
		+ Coro_stackSize(self) - 64;
	self->env[9] = (long)Coro_Start;
	self->env[8] =  self->env[3] + 32;
}
コード例 #8
0
ファイル: Coro.c プロジェクト: dru/io
void Coro_setup(Coro *self, void *arg)
{
	size_t *sp = (size_t *)(((intptr_t)Coro_stack(self)
						+ Coro_stackSize(self) - 64 + 15) & ~15);

	setjmp(buf);

	//printf("self = %p\n", self);
	//printf("sp = %p\n", sp);
	buf[0]  = (long)sp;
	buf[21] = (long)Coro_Start;
	//sp[-4] = (size_t)self; // for G5 10.3
	//sp[-6] = (size_t)self; // for G4 10.4

	//printf("self = %p\n", (void *)self);
	//printf("sp = %p\n", sp);
}
コード例 #9
0
ファイル: Coro.c プロジェクト: doublec/io
void Coro_setup(Coro *self, void *arg)
{
	// If this coro was recycled and already has a fiber, delete it.
	// Don't delete the main fiber. We don't want to commit suicide.

	if (self->fiber && !self->isMain)
	{
		DeleteFiber(self->fiber);
	}

	self->fiber = CreateFiber(Coro_stackSize(self),
							  (LPFIBER_START_ROUTINE)Coro_StartWithArg,
							 (LPVOID)arg);
	if (!self->fiber) {
		DWORD err = GetLastError();
		exit(err);
	}
}
コード例 #10
0
ファイル: Coro.c プロジェクト: ADTSH/io
void Coro_setup(Coro *self, void *arg)
{
	uintptr_t stackend = Coro_stackSize(self) + (uintptr_t)Coro_stack(self);
	uintptr_t start = (uintptr_t)Coro_Start;
	/* since ucontext seems to be broken on amd64 */
	globalCallbackBlock.context=((CallbackBlock*)arg)->context;
	globalCallbackBlock.func=((CallbackBlock*)arg)->func;

	setjmp(self->env);

#if defined(__x86_64__)
        *(uintptr_t*)(self->env+4) = stackend - 8;
        *(uintptr_t*)(self->env+14) = start;
#else
        *(uintptr_t*)(self->env+9) = stackend - 4;
        *(uintptr_t*)(self->env+12) = start;
#endif
}
コード例 #11
0
ファイル: Coro.c プロジェクト: doublec/io
void Coro_setup(Coro *self, void *arg)
{
	size_t *sp = (size_t *)(((intptr_t)Coro_stack(self)
						+ Coro_stackSize(self) - 64 + 15) & ~15);

	setjmp(buf);

	//printf("self = %p\n", self);
	//printf("sp = %p\n", sp);
	buf[0]  = (long)sp;
	buf[21] = (long)Coro_Start;
	globalCallbackBlock.context=((CallbackBlock*)arg)->context;
	globalCallbackBlock.func=((CallbackBlock*)arg)->func;
	//sp[-4] = (size_t)self; // for G5 10.3
	//sp[-6] = (size_t)self; // for G4 10.4

	//printf("self = %p\n", (void *)self);
	//printf("sp = %p\n", sp);
}
コード例 #12
0
ファイル: Coro.c プロジェクト: doublec/io
void Coro_setup(Coro *self, void *arg)
{
	ucontext_t *ucp = (ucontext_t *) &self->env;

	getcontext(ucp);

	ucp->uc_stack.ss_sp    = Coro_stack(self);
	ucp->uc_stack.ss_size  = Coro_stackSize(self);
#if !defined(__APPLE__)
	ucp->uc_stack.ss_flags = 0;
	ucp->uc_link = NULL;
#endif

#if defined(__x86_64__)
	unsigned int hiArg = (unsigned int)((long long)arg >> 32);
	unsigned int loArg = (unsigned int)((long long)arg & 0xFFFFFFFF);
	makecontext(ucp, (makecontext_func)Coro_StartWithArg, 2, hiArg, loArg);
#else
	makecontext(ucp, (makecontext_func)Coro_StartWithArg, 1, arg);
#endif
}
コード例 #13
0
ファイル: Coro.c プロジェクト: doublec/io
void Coro_setup(Coro *self, void *arg)
{
	setjmp(buf);
	buf[8] = (int)Coro_stack(self) + (int)Coro_stackSize(self) - 16;
	buf[9] = (int)Coro_Start;
}
コード例 #14
0
ファイル: Coro.c プロジェクト: dru/io
void Coro_setup(Coro *self, void *arg)
{
	setjmp(buf);
	buf[7] = (long)(Coro_stack(self) + Coro_stackSize(self) - 16);
	buf[8] = (long)Coro_Start;
}