我正在尝试创建用户级线程。这是我的代码示例。任何人都可以帮助我解决这个程序中的问题。
#include<stdio.h>
#include<ucontext.h>
int thread_counter = 0;
int thread1, thread2;
int who_am_i;
struct TCB {
ucontext_t context;
void (* fun_ptr)();
};
struct TCB tcb[3];
char stack[2][8192];
//----------------------
int thread_create(void (*fun)()) {
static volatile int s;
thread_counter++;
s = 0;
getcontext(&tcb[thread_counter].context);
if(!s) {
tcb[thread_counter].context.uc_stack.ss_sp = stack[thread_counter];
tcb[thread_counter].context.uc_stack.ss_size = sizeof(stack[thread_counter]);
tcb[thread_counter].context.uc_link = &tcb[0].context;
tcb[thread_counter].fun_ptr = fun;
s = 1;
}
else {
tcb[who_am_i].fun_ptr();
}
return thread_counter;
}
void thread_yield(int next_thread) {
static volatile int switched;
switched = 0;
getcontext(&tcb[who_am_i].context);
if(!switched) {
switched = 1;
who_am_i = next_thread;
setcontext(&tcb[next_thread].context);
}
}
//----------------------
void f1() {
printf("start f1\n");
thread_yield(thread2);
printf("finish f1:\n");
}
void f2() {
printf("start f2\n");
thread_yield(thread1);
printf("finish f2\n");
}
//----------------------
int main() {
thread1 = thread_create(f1);
thread2 = thread_create(f2);
who_am_i = 0;
thread_yield(thread1);
return 0;
}
线程未正确切换。当我运行它时,它给出以下输出:
start f1
start f2
finish f2
谢谢
答案 0 :(得分:0)
您有未定义的行为情况。
在thread_create
中,您首先要增加thread_counter
。因此,当您创建第二个帖子时,thread_counter
将为2
。然后,您访问stack[2]
,这将为您提供未定义的行为。
您还要将上下文的uc_link
成员硬编码为&tcb[0].context
,由于thread_counter
的“过早”增量,该成员从未初始化。
但主要问题是你实际上没有创建新的上下文,你只需获取当前线程的上下文。您应该为每个线程使用makecontext
。