Exemple #1
0
int u_green_init() {

	static int i;

	if (!ug.ugreen) {
		return 0;
	}

	ug.u_stack_size = UGREEN_DEFAULT_STACKSIZE;

	if (ug.stackpages > 0) {
		ug.u_stack_size = ug.stackpages * uwsgi.page_size;
	}

	uwsgi_log("initializing %d uGreen threads with stack size of %lu (%lu KB)\n", uwsgi.async, (unsigned long) ug.u_stack_size,  (unsigned long) ug.u_stack_size/1024);


	ug.contexts = uwsgi_malloc( sizeof(ucontext_t) * uwsgi.async);


	for(i=0;i<uwsgi.async;i++) {

		getcontext(&ug.contexts[i]);

		ug.contexts[i].uc_stack.ss_sp = mmap(NULL, ug.u_stack_size + (uwsgi.page_size*2) , PROT_READ | PROT_WRITE | PROT_EXEC, MAP_ANON | MAP_PRIVATE, -1, 0) + uwsgi.page_size;

		if (!ug.contexts[i].uc_stack.ss_sp) {
			uwsgi_error("mmap()");
			exit(1);
		}
		// set guard pages for stack
		if (mprotect(ug.contexts[i].uc_stack.ss_sp - uwsgi.page_size, uwsgi.page_size, PROT_NONE)) {
			uwsgi_error("mprotect()");
			exit(1);
		}
		if (mprotect(ug.contexts[i].uc_stack.ss_sp + ug.u_stack_size, uwsgi.page_size, PROT_NONE)) {
			uwsgi_error("mprotect()");
			exit(1);
		}

		ug.contexts[i].uc_stack.ss_size = ug.u_stack_size;

	}


	uwsgi.schedule_to_main = u_green_schedule_to_main;
	uwsgi.schedule_to_req = u_green_schedule_to_req;

	return 0;

}
Exemple #2
0
int create_client(int ls, int s, CLI *arg, void *(*cli)(void *)) {
    CONTEXT *context;

    (void)ls; /* this parameter is only used with USE_FORK */
    
    s_log(LOG_DEBUG, "Creating a new context");
    context=new_context();
    if(!context) {
        if(arg)
            str_free(arg);
        if(s>=0)
            closesocket(s);
        return -1;
    }

    /* initialize context_t structure */
    if(getcontext(&context->context)<0) {
        str_free(context);
        if(arg)
            str_free(arg);
        if(s>=0)
            closesocket(s);
        ioerror("getcontext");
        return -1;
    }
    context->context.uc_link=NULL; /* stunnel does not use uc_link */

    /* create stack */
    context->stack=str_alloc(arg->opt->stack_size);
    if(!context->stack) {
        str_free(context);
        if(arg)
            str_free(arg);
        if(s>=0)
            closesocket(s);
        s_log(LOG_ERR, "Unable to allocate stack");
        return -1;
    }
    str_detach(context->stack);
#if defined(__sgi) || ARGC==2 /* obsolete ss_sp semantics */
    context->context.uc_stack.ss_sp=context->stack+arg->opt->stack_size-8;
#else
    context->context.uc_stack.ss_sp=context->stack;
#endif
    context->context.uc_stack.ss_size=arg->opt->stack_size;
    context->context.uc_stack.ss_flags=0;

    makecontext(&context->context, (void(*)(void))cli, ARGC, arg);
    s_log(LOG_DEBUG, "New context created");
    return 0;
}
int main()
{
    getcontext(&uctx_main);  //AMJAD: Added uctx_main
    int thread_num = 10;
    int j;
    char* thread_names[] = {
        "thread 0",
        "thread 1",
        "thread 2",
        "thread 3",
        "thread 4",
        "thread 5",
        "thread 6",
        "thread 7",
        "thread 8",
        "thread 9"
    };

    /* Initialize MyThreads library. */
    mythread_init();

    /* 250 ms */
    set_quantum_size(250);

    counter_mutex = create_semaphore(1);

    for(j=0; j<thread_num; j++)
    {
        mythread_create(thread_names[j], (void *) &handler, 6004);
    }

    /* Print threads informations before run */
    mythread_state();

    /* When this function returns, all threads should have exited. */
    runthreads();
    
    destroy_semaphore(counter_mutex);

    /* Print threads informations after run */
    mythread_state();

    printf("The counter is %d\n", counter);
    printf("The result is %f\n", result);

    if (counter == 50 &&
	(result - 151402.656521) < 0.000001)
      printf(">>> Thread library PASSED the Test 1\n");

    exit(0);
}
Exemple #4
0
bool Cothread::resume(CothreadId id)
{
    auto schedule = getScheduleBlock();
    CothreadBlock *block = getCothreadBlock(id);
    bool ret = true;
    if(block == NULL || block->status == RunningStatus::Shutdown)
        return (ret = false);
    //
    switch(block->status)
    {
        case RunningStatus::Ready:
            getcontext(&block->ctx);
            //
            block->stack = new char[COTHREAD_STACK_SIZE];
            if(block->stack == NULL)
            {
                ret = false;
                break;
            }
            //init stack
            block->ctx.uc_stack.ss_sp = block->stack;
            block->ctx.uc_stack.ss_size = COTHREAD_STACK_SIZE;
            block->ctx.uc_stack.ss_flags = 0;
            block->ctx.uc_link = &schedule->ctx;
            //create a new running environment
            //a 64bit os may cause problem here?
            makecontext(&block->ctx, 
                (void (*)())Cothread::schedule, 
                1, 
                this
            );

        case RunningStatus::Suspend:
            schedule->runningId = block->id;
#ifdef DEBUG
            cout << "Cothread begin to start/resume" << endl;
#endif
            swapcontext(&schedule->ctx, &block->ctx);
            //after swap back, it is necessary to check if the thread exited
            if(block->status == RunningStatus::Shutdown)
            {
                freeCothreadBlock(id);
                ret = false;
            }
            break;

        default:
            ;//do nothing
    }
    return ret;
}
Exemple #5
0
G*
__go_go(void (*fn)(void*), void* arg)
{
	byte *sp;
	size_t spsize;
	G * volatile newg;	// volatile to avoid longjmp warning

	schedlock();

	if((newg = gfget()) != nil){
#ifdef USING_SPLIT_STACK
		sp = __splitstack_resetcontext(&newg->stack_context[0],
					       &spsize);
#else
		sp = newg->gcinitial_sp;
		spsize = newg->gcstack_size;
		newg->gcnext_sp = sp;
#endif
	} else {
		newg = runtime_malg(StackMin, &sp, &spsize);
		if(runtime_lastg == nil)
			runtime_allg = newg;
		else
			runtime_lastg->alllink = newg;
		runtime_lastg = newg;
	}
	newg->status = Gwaiting;
	newg->waitreason = "new goroutine";

	newg->entry = (byte*)fn;
	newg->param = arg;
	newg->gopc = (uintptr)__builtin_return_address(0);

	runtime_sched.gcount++;
	runtime_sched.goidgen++;
	newg->goid = runtime_sched.goidgen;

	if(sp == nil)
		runtime_throw("nil g->stack0");

	getcontext(&newg->context);
	newg->context.uc_stack.ss_sp = sp;
	newg->context.uc_stack.ss_size = spsize;
	makecontext(&newg->context, kickoff, 0);

	newprocreadylocked(newg);
	schedunlock();

	return newg;
//printf(" goid=%d\n", newg->goid);
}
      ucontext_thread_group(int num_threads, Function f)
        : thread_group()
    {
      if(num_threads)
      {
        // make a copy of the parameters for each thread
        // for arguments to makecontext
        typedef std::pair<ucontext_thread_group*,Function> exec_parms_t;
        void (*exec)(exec_parms_t *) = exec_thread<Function>;
        std::vector<exec_parms_t> exec_parms(num_threads, std::make_pair(this,f));

        // save the return state
        state join_state;
        getcontext(&join_state);
        if(thread_state.empty())
        {
          thread_state.resize(num_threads);

          for(int i = 0; i < thread_state.size(); ++i)
          {
            getcontext(&thread_state[i]);
            thread_state[i].uc_link = &join_state;
            thread_state[i].uc_stack.ss_sp = thread_state[i].stack;
            thread_state[i].uc_stack.ss_size = sizeof(thread_state[i].stack);
            makecontext(&thread_state[i], (void(*)())exec, 1, &exec_parms[i]);
          }

          // start thread 0
          set_current_thread_id(0);
          setcontext(&thread_state[0]);
        }

        // when we've reached this point, all the threads in the group have terminated
      } // end if

      // null the current thread_group
      this_thread_group::__singleton = 0;
    }
Exemple #7
0
/*
  The gtthread_init() function does not have a corresponding pthread equivalent.
  It must be called from the main thread before any other GTThreads
  functions are called. It allows the caller to specify the scheduling
  period (quantum in micro second), and may also perform any other
  necessary initialization.  If period is zero, then thread switching should
  occur only on calls to gtthread_yield().

  Recall that the initial thread of the program (i.e. the one running
  main() ) is a thread like any other. It should have a
  gtthread_t that clients can retrieve by calling gtthread_self()
  from the initial thread, and they should be able to specify it as an
  argument to other GTThreads functions. The only difference in the
  initial thread is how it behaves when it executes a return
  instruction. You can find details on this difference in the man page
  for pthread_create.
 */
void gtthread_init(long period){
  gtthread_int_t *mainthread;

  /* Malloc for this thread */
  if ((mainthread = malloc(sizeof(gtthread_int_t))) != NULL){

    /* Initialize queues */
    steque_init(&threads);
    steque_init(&run_queue);

    /* Set up mainthread */
    mainthread->id = next_id++;
    mainthread->cancelreq = 0;
    mainthread->completed = 0;
    steque_init(&mainthread->join_queue);

    /* Set up the context */
    getcontext(&mainthread->context);
    mainthread->context.uc_stack.ss_sp = (char *) malloc(SIGSTKSZ);
    mainthread->context.uc_stack.ss_size = SIGSTKSZ;

    steque_enqueue(&threads, mainthread);
    steque_enqueue(&run_queue, mainthread);

    /* Initialize the scheduling quantum */
    quantum = period;

    if (quantum != 0) {
      /* Setting up the signal mask */
      sigemptyset(&vtalrm);
      sigaddset(&vtalrm, SIGVTALRM);

      /* Setting up the alarm */
      timer = (struct itimerval*) malloc(sizeof(struct itimerval));
      timer->it_value.tv_sec = timer->it_interval.tv_sec = 0;
      timer->it_value.tv_usec = timer->it_interval.tv_usec = quantum;

      /* Setting up the handler */
      memset(&act, '\0', sizeof(act));
      act.sa_handler = &alrm_handler;
      if (sigaction(SIGVTALRM, &act, NULL) < 0) {
        printf("sigaction");
      }

      setitimer(ITIMER_VIRTUAL, timer, NULL);
      sigprocmask(SIG_UNBLOCK, &vtalrm, NULL);
    }
  }
  // FIXME: what about the error case?
}
Exemple #8
0
void mythread_init() {
   
    tcb *thread = new tcb(next_id);
    next_id++;
    thread_list[thread->id] = thread;

    ucontext_t main;
    getcontext(&thread->context);
    thread->context.uc_stack.ss_sp = thread->stack;
    thread->context.uc_stack.ss_size = stackSize;
    thread->context.uc_link = NULL;
    this_th_th=thread->id;
  
}
Exemple #9
0
void
__sigcleanup(struct sigcontext *scp)
{
	ucontext_t uc, *ucp;
	int sig;

	/*
	 * If there's a pointer to a ucontext_t hiding in the sigcontext,
	 * we *must* use that to return, since it contains important data
	 * such as the original "out" registers when the signal occurred.
	 */
	if (scp->sc_wbcnt == sizeof (*ucp)) {
		sig = (int)(uintptr_t)scp->sc_spbuf[0];
		ucp = (ucontext_t *)scp->sc_spbuf[1];
	} else {
		/*
		 * Otherwise, use a local ucontext_t and
		 * initialize it with getcontext.
		 */
		sig = 0;
		ucp = &uc;
		(void) getcontext(ucp);
	}

	if (scp->sc_onstack) {
		ucp->uc_stack.ss_flags |= SS_ONSTACK;
	} else
		ucp->uc_stack.ss_flags &= ~SS_ONSTACK;
	mask2set(scp->sc_mask, &ucp->uc_sigmask);

	ucp->uc_mcontext.gregs[REG_SP] = scp->sc_sp;
	ucp->uc_mcontext.gregs[REG_PC] = scp->sc_pc;
	ucp->uc_mcontext.gregs[REG_nPC] = scp->sc_npc;
#if defined(__sparcv9)
	ucp->uc_mcontext.gregs[REG_CCR] = scp->sc_psr;
#else
	ucp->uc_mcontext.gregs[REG_PSR] = scp->sc_psr;
#endif
	ucp->uc_mcontext.gregs[REG_G1] = scp->sc_g1;
	ucp->uc_mcontext.gregs[REG_O0] = scp->sc_o0;

	if (sig == SIGFPE) {
		if (ucp->uc_mcontext.fpregs.fpu_qcnt > 0) {
			ucp->uc_mcontext.fpregs.fpu_qcnt--;
			ucp->uc_mcontext.fpregs.fpu_q++;
		}
	}
	(void) setcontext(ucp);
	/* NOTREACHED */
}
/*
  The gtthread_create() function mirrors the pthread_create() function,
  only default attributes are always assumed.
 */
int gtthread_create(gtthread_t *thread,
        void *(*start_routine)(void *),
        void *arg){

  ucontext_t uctx;
  gtthread_blk_t *th_blk;

  DEBUG_MSG("gtthread_create\n"); 

  //sigprocmask(SIG_BLOCK, &vtalrm, NULL);                          // disable alarm signal

  /************************* Initialize the context *************************************/


  if(getcontext(&uctx) == -1) 
    return FAIL;

  uctx.uc_stack.ss_sp = (char*) malloc(SIGSTKSZ);
  uctx.uc_stack.ss_size = SIGSTKSZ;
  uctx.uc_link = NULL;

  makecontext(&uctx, (void (*) (void))(thread_handler), 2, start_routine, arg);      // modify the context 


  /************************** Initialize the thread block *************************************/

  th_blk = (gtthread_blk_t *)malloc(sizeof(gtthread_blk_t));
  if(th_blk == NULL)
    return FAIL;

  th_blk->tID = thread_ID++;
  th_blk->state = READY;
  th_blk->uctx = uctx;

  if(th_blk->uctx.uc_stack.ss_size == SIGSTKSZ)
    DEBUG_MSG("Correct assign\n"); 

  /********************************************************************************************/

  steque_enqueue(&thread_queue, th_blk);                          // add the thread to the scheduler queue

  //sigprocmask(SIG_UNBLOCK, &vtalrm, NULL);                        // enable alarm signal

  *thread = th_blk->tID;

  //list_thread();
  gtthread_yield();

  return SUCCESS;
}
Exemple #11
0
int swapcontext(ucontext_t * oucp, const ucontext_t * ucp) 
{
  int ret;
  if ((oucp == NULL) || (ucp == NULL)) {
    
        /*errno = EINVAL; */ 
        return -1;
  }
  ret = getcontext(oucp);
  if (ret == 0) {
    ret = setcontext(ucp);
  }
  return ret;
}
Exemple #12
0
struct thread* initializeThread() {
  ucontext_t *ucp;
  ucp = (ucontext_t*)malloc(sizeof(ucontext_t));
  getcontext(ucp);

  struct thread* temp = (struct thread*)malloc(sizeof(struct thread));
  temp->context = ucp;
  temp->context->uc_stack.ss_sp = malloc(16384);
  temp->context->uc_stack.ss_size = 16384;
  temp->next = NULL;
  temp->prev = NULL;

  return temp;
}
Exemple #13
0
thread_t *thread_create(thread_context_t *ctx, thread_fn *start, void *user) {
    thread_t *t;

    t = calloc(1, sizeof(*t));
    t->start = start;
    t->user = user;
    getcontext(&t->context);
    t->context.uc_stack.ss_sp = malloc(STACK_SIZE);
    t->context.uc_stack.ss_size = STACK_SIZE;
    t->context.uc_link = &ctx->poller;
    makecontext(&t->context, start_thread, 4, PTR(ctx), PTR(t));

    return t;
}
static void setExitContext()
{
    static int exitContextCreated;
    if(!exitContextCreated)
    {
        getcontext(&exitContext);
        exitContext.uc_link = 0;
        exitContext.uc_stack.ss_sp = malloc(STACKSIZE);
        exitContext.uc_stack.ss_size = STACKSIZE;
        exitContext.uc_stack.ss_flags= 0;
        makecontext(&exitContext, (void (*) (void))&executeExitContext, 0);
        exitContextCreated = 1;
    }
}
Exemple #15
0
int thread_create(char *id, int tickets, void (*rutina)(int, int), int arg, int idInt) {
	
        struct Thread *newThread = getNewThreadnoStack(tickets, id);
	ucontext_t context;
        getcontext(&(context));
        context.uc_stack.ss_sp = malloc(STACKSIZE);
        context.uc_stack.ss_size = STACKSIZE;
        context.uc_stack.ss_flags = 0;
        context.uc_link = &mainContext;
        makecontext (&(context), (void (*) (void))generalFunction, 3, rutina, arg, idInt);
     	scheduler->addTask(newThread, context);
	
	return 1;
}
Exemple #16
0
/*
===================================================================================================
spe_routine_create
===================================================================================================
*/
spe_routine_t*
spe_routine_create(void) {
  spe_routine_t* routine = calloc(1, sizeof(spe_routine_t));
  if (!routine) {
    SPE_LOG_ERR("routine calloc error");
    return NULL;
  }
  getcontext(&routine->context);
  routine->context.uc_stack.ss_sp   = routine->stack;
  routine->context.uc_stack.ss_size = sizeof(routine->stack);
  routine->handler                  = SPE_HANDLER_NULL;
  makecontext(&routine->context, (void(*)(void))routine_main, 1, routine);
  return routine;
}
Exemple #17
0
/*
 * Swap the current context for the context of the thread 
 * passed by this function. 
 *
 * If the thread is new ( !THREAD_IS_STARTED ) the the context
 * must be built.
 *
 * If the thread has already started then we simple resume the 
 * context
 *
 * Threads are set to return to the calling process when completed
 * or yeiled. 
 */
void _MyThreadRun( Thread* t ) { 
    if( t->flags & THREAD_IS_STARTED ) {
        swapcontext(&t->return_ctx, &t->ctx);
    } else {
        t->flags                |= THREAD_IS_STARTED;
        getcontext(&t->ctx); 
        t->ctx.uc_stack.ss_sp   = malloc(STACK_SIZE);
        t->ctx.uc_stack.ss_size = STACK_SIZE;
        t->ctx.uc_link          = &t->return_ctx; 
        if( t->func != NULL ) 
            makecontext(&t->ctx, t->func, 1,  t->args); 
        swapcontext(&t->return_ctx, &t->ctx);
    }
};
Exemple #18
0
void dump_img(void) {
	// 2. read /proc/self/maps to get section headers, then get memory dump
	create_memory_checkpoint();

	// 1. getcontext to save registers values
	ucontext_t mycontext;
	from_recover = 0;
    getcontext(&mycontext);
	// if this is not from recover, save the context and exit the program
	if (from_recover == 0) {
		write_context_to_ckpt_header(&mycontext, sizeof mycontext);
		exit(0);
	}
}
Exemple #19
0
void uctx_coro_makectx(struct coro_ctx *ctx, size_t ctx_size, void* (*f)(void*))
{
	if (getcontext(&ctx->uctx) < 0) {
		perror("getcontext");
		abort();
	}
	ctx->uctx.uc_stack.ss_sp = (void *)ctx + sizeof(struct coro_ctx);
	ctx->uctx.uc_stack.ss_size = ctx_size - sizeof(struct coro_ctx);
	ctx->uctx.uc_link = NULL;
	/* according to makecontext(3), to be portable we must pass pointer 
	   by a pair of int args */
	makecontext(&ctx->uctx, (void(*)())uctx_coro_main, 2, 
			(int)f, (int)((uintptr_t)f >> (sizeof(int)*8)));
}
void __asmSaveContextAndCallScheduler() {

	   /* Create new scheduler context */
	   getcontext(&signal_context);
	   signal_context.uc_stack.ss_sp = signal_stack;
	   signal_context.uc_stack.ss_size = STACKSIZE;
	   signal_context.uc_stack.ss_flags = 0;
	   sigemptyset(&signal_context.uc_sigmask);
	   makecontext(&signal_context, (void (*)())schedulerWrapper, 1,contextT);

	   /* save running thread, jump to scheduler */
	   swapcontext(contextT,&signal_context);

}
void init()
{
    head = NULL;

    act.sa_handler = sighandler;
    sigemptyset(&act.sa_mask);
    act.sa_flags = 0;
    sigaction(SIGALRM, &act, 0); 

    getcontext(&scheduler_context);
    scheduler_context.uc_stack.ss_sp = malloc(SZ);
    scheduler_context.uc_stack.ss_size = SZ;
    scheduler_context.uc_stack.ss_flags = 0;
    scheduler_context.uc_link = &main_context;
    makecontext(&scheduler_context, thread_run, 0);

    getcontext(&killer_context);
    killer_context.uc_stack.ss_sp = malloc(SZ);
    killer_context.uc_stack.ss_size = SZ;
    killer_context.uc_stack.ss_flags = 0;
    killer_context.uc_link = 0;
    makecontext(&killer_context, thread_kill, 0);
}
Exemple #22
0
/*
   Timer interrupt handler.
   Creates a new context to run the scheduler in, masks signals, then swaps
   contexts saving the previously executing thread and jumping to the
   scheduler.
   */
	void
timer_interrupt(int j, siginfo_t *si, void *old_context)
{
	/* Create new scheduler context */
	getcontext(&signal_context);
	signal_context.uc_stack.ss_sp = signal_stack;
	signal_context.uc_stack.ss_size = STACKSIZE;
	signal_context.uc_stack.ss_flags = 0;
	sigemptyset(&signal_context.uc_sigmask);
	makecontext(&signal_context, scheduler, 0);

	/* save running thread, jump to scheduler */
	swapcontext(cur_context,&signal_context);
}
Exemple #23
0
afs_int32
savecontext(void (*ep) (void), struct lwp_context *savearea, char *newsp)
{
#if defined(AFS_LINUX20_ENV)
    /* getcontext does not export stack info */
    int stackvar;
#endif

    PRE_Block = 1;

    savearea->state = 0;
    getcontext(&savearea->ucontext);
#if defined(AFS_LINUX20_ENV)
    savearea->topstack = &stackvar;
#else
    savearea->topstack = savearea->ucontext.uc_stack.ss_sp;
#endif
    switch (savearea->state) {
    case 0:
	if (newsp) {
	    ucontext_t thread;

	    getcontext(&thread);
	    thread.uc_stack.ss_sp =
		newsp - AFS_LWP_MINSTACKSIZE + sizeof(void *) +
		sizeof(void *);
	    thread.uc_stack.ss_size = AFS_LWP_MINSTACKSIZE - sizeof(void *);
	    makecontext(&thread, ep, 0);
	    setcontext(&thread);
	} else
	    (*ep) ();
	break;
    case 2:
	break;
    }
    return 0;
}
Exemple #24
0
int t_init (void (*fun_addr)(), int fun_arg)
{
    int i,j,k;
    //finds an empty slot
    for (i=1; i<N; i++)
    {
        if (t_state[i].state == FREE) break;
    }
    if (i == N) return(-1);
    
    if(getcontext(&t_state[i].run_env) == -1)
    {
        perror("getcontext in t_init");
        exit(5);
    }

    t_state[i].state = INIT;
    t_state[i].function = fun_addr;
    t_state[i].mystk.ss_sp = (void *)(malloc(STACKSIZE));
    if(t_state[i].mystk.ss_sp == NULL)
    {
        printf("thread failed to get stack space\n");
        exit(8);
    }
    t_state[i].mystk.ss_size = STACKSIZE;
    t_state[i].mystk.ss_flags = 0;
    t_state[i].run_env.uc_stack = t_state[i].mystk;
    t_state[i].run_env.uc_link = &t_state[i].rtn_env;
    //
    t_state[i].rtn_env.uc_stack = t_state[i].mystk;
    getcontext(&t_state[i].rtn_env); 
    makecontext(&t_state[i].rtn_env,returncontext,0);
    makecontext(&t_state[i].run_env, fun_addr, 1,fun_arg);

    return(i);

}
Exemple #25
0
// Called to start an M.
void*
runtime_mstart(void* mp)
{
	m = (M*)mp;
	g = m->g0;

	initcontext();

	g->entry = nil;
	g->param = nil;

	// Record top of stack for use by mcall.
	// Once we call schedule we're never coming back,
	// so other calls can reuse this stack space.
#ifdef USING_SPLIT_STACK
	__splitstack_getcontext(&g->stack_context[0]);
#else
	g->gcinitial_sp = &mp;
	// Setting gcstack_size to 0 is a marker meaning that gcinitial_sp
	// is the top of the stack, not the bottom.
	g->gcstack_size = 0;
	g->gcnext_sp = &mp;
#endif
	getcontext(&g->context);

	if(g->entry != nil) {
		// Got here from mcall.
		void (*pfn)(G*) = (void (*)(G*))g->entry;
		G* gp = (G*)g->param;
		pfn(gp);
		*(int*)0x21 = 0x21;
	}
	runtime_minit();

#ifdef USING_SPLIT_STACK
	{
	  int dont_block_signals = 0;
	  __splitstack_block_signals(&dont_block_signals, nil);
	}
#endif

	// Install signal handlers; after minit so that minit can
	// prepare the thread to be able to handle the signals.
	if(m == &runtime_m0)
		runtime_initsig();

	schedule(nil);
	return nil;
}
void myThreadInit(long pTimeInterval) 
{
    //DEBUGGING
    debuggingFile = fopen("DebuggingFile.txt", "w");
    //DEBUGGING

    if (threadsQueue == NULL && deadThreadsQueue == NULL) 
    {
        sigemptyset(&sigProcMask);
        sigaddset(&sigProcMask, SIGPROF);
        deadThreadsQueue = createDeadTheadsNodesQueue();
        threadsQueue = createTCBQueue();
        if (deadThreadsQueue == NULL || threadsQueue == NULL) 
        {
            return;
        }
        else
        {
            srand((unsigned) time(&randomTimeSeed));
            timeInterval = pTimeInterval * 1000;
            threadsQueue->quantum = pTimeInterval;
            TCB TCBMain = createNewTCB();
            getcontext(&(TCBMain->threadContext));
            setExitContext();
            TCBMain->threadContext.uc_link = &exitContext;
            //La linea de abajo indica que el thread principal es administrado por el scheduler RoundRobin.
            // TCBMain->roundRobin = 1;
            // roundRobinControl = 1;
            // Descomentar las lineas comentadas de abajo y comentar la linea de arriba si se quiere que el thread principal sea administrado por el scheduler Sort.
            TCBMain->sort = 1;
            int nextTicket = searchEndTicket(threadsQueue);
            TCBMain->initialTicket = nextTicket;
            TCBMain->finalTicket = nextTicket;
            sortControl = 1;
            //
            threadsQueue->currentThread = TCBMain;
            insertThread(threadsQueue, TCBMain);
            memset(&schedulerHandle, 0, sizeof (schedulerHandle));
            schedulerHandle.sa_handler = &realTime;
            sigaction(SIGPROF, &schedulerHandle, NULL);
            //printf("\nMyThread: Biblioteca MyThread Inicializada...\n");
            timeQuantum.it_value.tv_sec = 0;
            timeQuantum.it_value.tv_usec = timeInterval;
            timeQuantum.it_interval.tv_sec = 0;
            timeQuantum.it_interval.tv_usec = timeInterval;
            setitimer(ITIMER_PROF, &timeQuantum, NULL);
        }
    }
}
Exemple #27
0
/*++
Function:
  CONTEXT_GetRegisters

Abstract
  retrieve the machine registers value of the indicated process.

Parameter
  processId: process ID
  registers: reg structure in which the machine registers value will be returned.
Return
 returns TRUE if it succeeds, FALSE otherwise
--*/
BOOL CONTEXT_GetRegisters(DWORD processId, ucontext_t *registers)
{
#if HAVE_BSD_REGS_T
    int regFd = -1;
#endif  // HAVE_BSD_REGS_T
    BOOL bRet = FALSE;

    if (processId == GetCurrentProcessId()) 
    {
#if HAVE_GETCONTEXT
        if (getcontext(registers) != 0)
        {
            ASSERT("getcontext() failed %d (%s)\n", errno, strerror(errno));
            return FALSE;
        }
#elif HAVE_BSD_REGS_T
        char buf[MAX_PATH];
        struct reg bsd_registers;

        sprintf_s(buf, sizeof(buf), "/proc/%d/regs", processId);

        if ((regFd = PAL__open(buf, O_RDONLY)) == -1) 
        {
          ASSERT("PAL__open() failed %d (%s) \n", errno, strerror(errno));
          return FALSE;
        }

        if (lseek(regFd, 0, 0) == -1)
        {
            ASSERT("lseek() failed %d (%s)\n", errno, strerror(errno));
            goto EXIT;
        }

        if (read(regFd, &bsd_registers, sizeof(bsd_registers)) != sizeof(bsd_registers))
        {
            ASSERT("read() failed %d (%s)\n", errno, strerror(errno));
            goto EXIT;
        }

#define ASSIGN_REG(reg) MCREG_##reg(registers->uc_mcontext) = BSDREG_##reg(bsd_registers);
        ASSIGN_ALL_REGS
#undef ASSIGN_REG

#else
#error "Don't know how to get current context on this platform!"
#endif
    }
    else
    {
Exemple #28
0
void thread_init(long nquantum, int totalProcessInit, struct sched_t *schedulerIn) {
	
        scheduler = schedulerIn;
        sigemptyset(&sigsetMask);
        sigaddset(&sigsetMask,SIGPROF);
	getcontext(&mainContext);
	memset(&schedulerHandle,0,sizeof(schedulerHandle));
	schedulerHandle.sa_handler = timer_handler;
	sigaction(SIGPROF,&schedulerHandle,NULL);
	timeIntervalInMSec = nquantum;
	quantum.it_value.tv_sec = 0;// http://linux.die.net/man/2/setitimer
        quantum.it_value.tv_usec = timeIntervalInMSec;
        quantum.it_interval.tv_sec=0;
        quantum.it_interval.tv_usec = timeIntervalInMSec;

	states = (state*)malloc(sizeof(state) * totalProcessInit);
	
	int k;

	for( k  = 0; k < totalProcessInit; k++){
		state newState;;
		newState.id = k;
		newState.finish = 0;
		newState.percent = 0.0;
		newState.result = 0.0;
		newState.active = 0;
		states[k] = newState;
	}
	
	
        /*if(mode == EXPROPIATIVO)
            setitimer(ITIMER_PROF, &quantum, NULL);*/

          /*  sigemptyset(&sigsetMask);
            sigaddset(&sigsetMask, SIGPROF); //para mandar sennal cuando expire el timer
            timeIntervalInMSec = nquantum;
            schedulerHandle.sa_sigaction = timer_handler;
            schedulerHandle.sa_flags = SA_SIGINFO|SA_RESTART;
            sigemptyset(&schedulerHandle.sa_mask);
            sigaction(SIGRTMIN, &schedulerHandle, NULL);

            //inicializo el quantum
            quantum.it_value.tv_sec = 0;// http://linux.die.net/man/2/setitimer
            quantum.it_value.tv_usec = timeIntervalInMSec;
            quantum.it_interval.tv_sec=0;
            quantum.it_interval.tv_usec = timeIntervalInMSec;

            setitimer(ITIMER_PROF, &quantum, NULL);*/
}
MyThread MyThreadCreate (void(*start_funct)(void *), void *args) //Finalizes Create Thread Function
{
	MyThread* child = insertNode(ready_queue);
	getcontext(&(child->context));
	child->context.uc_stack.ss_sp=malloc(MEM);
 	child->context.uc_stack.ss_size=MEM;
 	child->context.uc_stack.ss_flags=0;
	child->id = threadCount++;
	child->parent = ready_queue->id;
	child->context.uc_link=&controller;
	makecontext(&(child->context), (void*)start_funct, 1, (int)args);
	//printf("\nHi, this is the %d thread getting created, my parent is: %d", child->id, ready_queue->id);
	//printQueues();
	return *child;
}
Exemple #30
0
static int co_set_context(co_ctx_t *ctx, void *func, char *stkbase, long stksiz)
{
	if (getcontext(&ctx->cc))
		return -1;

	ctx->cc.uc_link = NULL;

	ctx->cc.uc_stack.ss_sp = stkbase;
	ctx->cc.uc_stack.ss_size = stksiz - sizeof(long);
	ctx->cc.uc_stack.ss_flags = 0;

	makecontext(&ctx->cc, func, 1);

	return 0;
}