C 从另一个线程访问主线程的局部变量
以下是本书中的一个示例程序,作者在其中演示了多线程程序中共享变量的用法:C 从另一个线程访问主线程的局部变量,c,multithreading,pthreads,posix,C,Multithreading,Pthreads,Posix,以下是本书中的一个示例程序,作者在其中演示了多线程程序中共享变量的用法: #include "csapp.h" #define N 2 void *thread(void *vargp); char **ptr; /* Global variable */ int main() { int i; pthread_t tid; char *msgs[N] = { "Hello from foo",
#include "csapp.h"
#define N 2
void *thread(void *vargp);
char **ptr; /* Global variable */
int main()
{
int i;
pthread_t tid;
char *msgs[N] = {
"Hello from foo",
"Hello from bar"
};
ptr = msgs;
for (i = 0; i < N; i++)
Pthread_create(&tid, NULL, thread, (void *)i);
Pthread_exit(NULL);
}
void *thread(void *vargp)
{
int myid = (int)vargp;
static int cnt = 0;
printf("[%d]: %s (cnt=%d)\n", myid, ptr[myid], ++cnt);
return NULL;
}
#包括“csapp.h”
#定义n2
void*螺纹(void*vargp);
字符**ptr;/*全局变量*/
int main()
{
int i;
pthread_t tid;
char*msgs[N]={
“foo你好”,
“酒吧里的你好”
};
ptr=msgs;
对于(i=0;i
可以看出,两个线程都访问全局变量ptr
,该变量指向调用pthread\u exit
的主线程的局部变量msgs
现在,根据以下文件:
线程终止后,访问线程的本地(自动)变量的结果是未定义的
那么,上面的代码正确吗
即使主线程调用pthread\u exit
,从另一个线程访问主线程的局部变量是否合法
即使主线程调用pthread_exit,从另一个线程访问主线程的局部变量是否合法
否。一旦主线程通过pthread\u exit
完成,任何局部变量的生存期(即自动存储持续时间)都将结束。任何来自另一个线程的进一步访问都是未定义的行为
那么,上面的代码正确吗
否。msgs
数组是一个局部变量,其生存期在调用pthread\u exit
后结束。因此,任何通过ptr
的进一步访问都是未定义的
通常,只要对象的生命周期没有结束,从另一个线程访问一个线程的局部变量是有效的。这是由以下方面保证的:
[…]其地址可由线程确定的任何内容,包括
但不限于静态变量,通过malloc()获得的存储,
通过定义的实现获得的直接可寻址存储
中的所有线程都可以访问函数和自动变量
同样的过程
另一件需要注意的事情是,如果您已将msgs[0]
或msgs[1]
传递给线程,则这是有效的。因为msgs[0]
和msgs[1]
指向字符串文本,其生存期仅在程序终止时结束(而不仅仅是有指针指向它的线程)
类似地,如果您通过malloc
(或其朋友)或任何具有静态存储持续时间的对象进行分配,并将其传递给线程函数,则它也是有效的
e、 g
#包括
#包括
void*thread_func(void*arg)
{
char*str=p;
printf(“%s\n”,str);
返回NULL;
}
内部主(空)
{
pthread_t tid;
char*p=“你好”;
pthread_create(&tid,NULL,thread_func,p);
pthread_exit(NULL);
}
这是完全正确的,因为p
指向一个字符串文本,该文本即使在main
通过pthread\u exit
返回后仍然存在
因此,这里需要注意的重要区别是,对另一个线程中变量的访问是否未定义取决于所述对象的生存期,而不仅仅是变量的定义位置。为什么
main
甚至调用pthread\u exit
?它应该调用pthread\u join
,然后您的问题就会得到解决。(1)这是书中的代码。(2) 从主线程调用pthread\u exit
是完全合法的,并且有这样的用例(例如,如果主线程只想生成其他分离的线程而不需要等待它们完成)。这是合法的,是的。还要注意,它基本上是传递的i
的值。线程从不解除对指向main
本地对象的任何引用。因此,您所考虑的问题并不存在。由于多种原因,此代码不应编译。如果你正在从一本提供此类代码的书中学习,请阅读勘误表,如果勘误表不能解决此问题,请丢弃该书。在C语言中,你根本不能保证能够访问另一个线程的自动存储,更不用说不同步或在其生命周期结束后。该行为未定义。
#include<stdio.h>
#include<pthread.h>
void *thread_func(void *arg)
{
char *str = p;
printf("%s\n", str);
return NULL;
}
int main(void)
{
pthread_t tid;
char *p = "Hello";
pthread_create(&tid, NULL, thread_func, p);
pthread_exit(NULL);
}