Howdy, Stranger!

It looks like you're new here. If you want to get involved, click one of these buttons!

Categories

Thread Simul

I hope this is not too much to read. I have to simulate a preemptive thread scheduler in C with setjmp and longjmp. I cannot for the life of me figure out what is wrong.


#define ALARM_INTERVAL 2
typedef int (*fptr_t)();
sigjmp_buf main;
list_t Q;

void yield(int sig)
{
sigjmp_buf *B;
B = (sigjmp_buf *)alloca(sizeof(sigjmp_buf));
list_remove(Q); //remove current and go to next element
if(sigsetjmp(*B,1) == 0)
{
list_insert(Q,B);
B = list_curr(Q);
alarm(ALARM_INTERVAL);
siglongjmp(*B,sig); //execute next thread
}
else
{
//resume thread that was alarmed
}
}

int func1()
{
signal(SIGALRM, yield);
printf("Running Thread: 1
");
sleep(ALARM_INTERVAL);
printf("Finishing Thread: 1
");
thread_exit(); //remove from queue
return 0;
}

int Thread_Init()
{
Q = list_init(); //pointer to Q
list_insert(Q,NULL); //dummy main() thread
return 0;
}

int Thread_Create(int (*fptrThread)(),
char *strName, int iStackIndex)
{
sigjmp_buf *B;
B = (sigjmp_buf *)alloca(sizeof(sigjmp_buf));
if(sigsetjmp(*B,1) == 0) //execute function
{
// fptrThread=(fptr_t)iStackIndex
(*fptrThread)();
}
else //schedule thread
{
list_insert(Q,*B);
siglongjmp(main,1); //go back to main
}
//thread done
return 0;
}

int main()
{
Thread_Init();
if(!sigsetjmp(main,1)) //schedule Thread 1
Thread_Create(&func1, NULL, (int)func1);
signal(SIGALRM, yield);
alarm(ALARM_INTERVAL); //start simulation
while(1) //do nothing, illustrate switching
{
printf("Running Thread: 0
");
sleep(ALARM_INTERVAL);
}
return 0;
}


There are two problems:
I call Thread_Create to schedule a thread and when I return strname and fptrThread are no longer their old values. The scope of these variables is local so I don't see why this is the case. However, the value of iStackindex is "correct" (I will explain "correct" later if I can get the initial problem solved). So with this hack I can run the "thread" func1 just fine.

The queue 100% works and steps through the list perfectly, always giving me the right values. However, when I get back around the list to continue the main() thread, it segfaults. Anyone know why?

Comments

  • void_tvoid_t Member Posts: 2
    I solved the problem and figured I'd post here for completeness. The problem was I wasn't using alloca in main so that every thread would have its own stack. If you call alloca with like 10000 every time then it will work correctly. I just have to figure out how to calculate the actual size I need to pass into alloca now. No worries though as I will figure this out tomorrow.
Sign In or Register to comment.