【发布时间】:2021-06-17 02:29:30
【问题描述】:
所以这是我的代码的一小部分。本质上,我正在从一个方法启动另一个线程,但是当我将整数传递给 pthread 时,我无法访问结构成员,就像我在调用线程之前只能访问两行一样。自从我通过这个参数并运行一个新线程后发生了什么?
请注意,我的程序总是在 printf("1\n"); 之后立即崩溃,当我意识到 FD_ZERO 不起作用时,我发现了这个错误。
结构定义(全局区域):
typedef struct {
fd_set read_set, write_set;
unsigned int room_id;
char room_name[16];
} room;
调用方法:
void create_new_room(int cli_index, char buffer[]) {
pthread_mutex_lock(&mutex);
char room_name[16], password[16];
int capacity, r_index;
room *new_room = malloc(sizeof(room));
pthread_t tid;
FILE *room_file = NULL;
if((room_file = fopen("room-info.txt", "a")) == NULL) {
perror("Failed to open file.");
exit(-1);
}
// Split command data into separate strings ready to assign as room struct members
strtok(buffer, " ");
strcpy(room_name, strtok(NULL, " "));
capacity = atoi(strtok(NULL, " "));
strcpy(password, strtok(NULL, " "));
// Initialise room struct
// --Zero write set
FD_ZERO(&(new_room->write_set));
// --Set room name
strcpy(new_room->room_name, room_name);
// --Set room id
new_room->room_id = ++natural_id;
// --Add room to room_list[] and get its index in the array
for(r_index = 0; r_index < 10000; ++r_index) {
if(!room_list[r_index]) {
room_list[r_index] = new_room;
break;
}
}
// Write data to file
fprintf(room_file, "%s\n", room_name);
fprintf(room_file, "id=%u\n", natural_id);
fprintf(room_file, "owner=%s\n", client_list[cli_index]->name);
fprintf(room_file, "capacity=%d\n", capacity);
fclose(room_file);
printf("about to test\n");
printf("Testing room struct:\n");
printf("--room name = %s\n", room_list[r_index]->room_name);
printf("--room id = %u\n", room_list[r_index]->room_id);
printf("post-test.....................\n");
// Run new thread as active room
printf("Starting new room: %s\n", room_name);
pthread_create(&tid, NULL, (void *) &active_room, &r_index);
pthread_mutex_unlock(&mutex);
}
开始新的 pthread 方法:
void active_room(void *index) {
char storage_buffer[BSIZE], output_buffer[BSIZE+32];
struct timeval timeout;
int r_index = *(int *) index;
while(1) {
// debugging lines.
printf("1\n");
printf("room name: %s\n", room_list[r_index]->room_name);
printf("room id: %u\n", room_list[r_index]->room_id);
FD_ZERO(&(room_list[r_index]->read_set));
read_set = write_set;
timeout.tv_sec = 5;
printf("2\n");
【问题讨论】:
-
我们需要查看更多代码。请使用minimal reproducible example 更新您的问题。
-
pthread_create(&tid, NULL, (void *) &active_room, &r_index);不要让我们保持悬念。我们不必猜测r_index是什么,以及它在哪里声明,这两个问题都将在之前用正确的minimal reproducible example 回答。room_list也是如此。事实上,我高度怀疑将room_list + r_index作为线程可选参数传递,并且仅在线程 proc 中使用该地址的恢复就可以解决您的问题,但这纯粹是猜测,因为如果没有 minimal reproducible example,我将无法验证它。跨度> -
如果
r_index是调用函数中的局部变量,它可能会在active_room()取消引用指针之前被销毁。 -
尝试在调用者和线程函数中打印
r_index,你可能会发现它们是不同的。 -
不是将
&r_index传递给函数,而是传递&room_list[r_index]。这显然是一个全局变量,因此跨线程有效。