关于localtime()函数在多线程中的core问题

时间:2021-10-13 18:06:31

生产上的程序在某天运行的过程中忽然core掉,gdb显示的core文件的堆栈信息如下:

(gdb) where 
#0  0x0000003369832925 in raise () from /lib64/libc.so.6
#1  0x0000003369834105 in abort () from /lib64/libc.so.6
#2  0x0000003369870837 in __libc_message () from /lib64/libc.so.6
#3  0x0000003369876166 in malloc_printerr () from /lib64/libc.so.6
#4  0x000000336989dbe9 in tzset_internal () from /lib64/libc.so.6
#5  0x000000336989dd69 in __tz_convert () from /lib64/libc.so.6
#6  0x00000000004058a0 in getCurrDateTime (sCurrDateTime=0x2ab81c3f4930 "`\f@\034\270*") at StaticPub.cpp:27
#7  0x0000000000412716 in InitOrderInfo::InitServStateStr (this=0x2ab83c6a8010, nUserType=1, lServId=210001950603, 
    pstServStatAttr=0x2ab83c6ce150, nServStatAttrSize=1, pServStateStr=0x2ab83c778db8 "") at InitOrderInfo.cpp:1929
#8  0x0000000000411424 in InitOrderInfo::InitServBaseInfo (this=0x2ab83c6a8010) at InitOrderInfo.cpp:1536
#9  0x000000000040f5b9 in InitOrderInfo::process (this=0x2ab83c6a8010) at InitOrderInfo.cpp:655
#10 0x0000000000425156 in SI_WorkFlow::executor (this=0x2ab82c0008c0, pUser=0x2ab82dd31690) at WorkFlow.cpp:782
#11 0x0000000000408df4 in SI_ThreadFlow::run (this=0x33ea3f0) at SI_ThreadFlow.cpp:187
#12 0x00000000004086a5 in OpenThreads::DC_ThreadPrivateActions::StartThread (data=0x33ea3f0) at Thread.cpp:120
#13 0x000000336a0079d1 in start_thread () from /lib64/libpthread.so.0
#14 0x00000033698e8b6d in clone () from /lib64/libc.so.6

在StaticPub.cpp文件发现是core附近的代码为:

        time_t  tTime;

struct tm *localTime;

    time(&tTime);
    localTime=localtime(&tTime);

感到很不理解,在获取系统函数的时候程序竟然会core掉,后来在上网查阅之后发现,原来local_time()函数不是线程安全类型,函数在返回的时候返回的是一个指针,实际内存是localtime内部通过static申请的静态内存,所以在不加锁的情况下两个线程同时调用的时候就会出错.

在linux下有local_time_r()函数是线程安全的,把代码改成如下:

time_t tTime(NULL);

struct tm localTime={0};

time(&tTime);

localetime_r(&tTime,&localTime);;