代码本来在Windows上开发的,功能基本完毕迁移到Linux上,结果一跑,乱象重重。这里只列出两个。
 
一崩溃:
 /mnt/diskc/db/app/bin/mysqld: double free or corruption (out): 0x00007f09cc00c900 ***
======= Backtrace: =========
/lib64/libc.so.6[0x31434760e6]
/lib64/libc.so.6[0x3143478c13]
/lib64/libc.so.6(fclose+0x14d)[0x314346674d]
/mnt/diskc/db/app/bin/mysqld(……内部代码……)[0x781d59] …… /lib64/libpthread.so.0[0x3143c07851]
/lib64/libc.so.6(clone+0x6d)[0x31434e890d]

二挂死:

查询一张表时正常返回结果,然后正常shutdown关闭程序,就挂住了。用pstack可以打出调用栈来。
Thread 2 (Thread 0x7f8a6c074700 (LWP 1506)):
#0 0x00000031434f806e in __lll_lock_wait_private () from /lib64/libc.so.6
#1 0x0000003143466815 in _L_lock_36 () from /lib64/libc.so.6
#2 0x0000003143466652 in fclose@@GLIBC_2.2.5 () from /lib64/libc.so.6
#3 0x00000000007828f6 in …………内部代码………… ()
#5 0x00000000005e9e7d in closefrm(TABLE*, bool) ()
#6 0x0000000000543122 in free_cache_entry(TABLE*) ()
#7 0x000000000054be7c in close_cached_tables(THD*, TABLE_LIST*, bool, unsigned long) ()
#8 0x000000000054c1a4 in table_def_start_shutdown() ()
#9 0x0000000000512f6c in clean_up(bool) ()
#10 0x00000000005131ee in unireg_end() ()
#11 0x0000000000514b82 in kill_server ()
#12 0x0000000000514c3e in kill_server_thread ()
#13 0x0000003143c07851 in start_thread () from /lib64/libpthread.so.0
#14 0x00000031434e890d in clone () from /lib64/libc.so.6
一头乱麻,索性就从最容易重现的第二个挂死现象查起了。
谷歌一搜fclose __lll_lock_wait_private ,神啊,多是说程序clone之后再fclose有过这样的问题,有的还提供了对glibc的patch,确认了一下,我们的glibc库已经很新了。而且我们的程序虽然有多线程,也对一个文件打开过两次,但这两次操作是在一个线程内部的,所以跟网上的信息不太相符。
 
后来自己写了一个测试程序,在一个程序内两次fopen,再依次关闭,也都正常。又改成主线程里开一次,子线程里开一次,再关,仍都正常。
 
最后没办法仔细查代码,发现关于文件打开我们的流程是:
 
OpenFile(FILE* fp)
{
if (fp != NULL)
fclose(fp); fopen(fp,,,,,);
}

而在某些处理后需要关闭时,操作为:

fclose(fp);
虽然不太确定,但做事总要干净些,于是把关闭操作改为:
fclose(fp);
fp = NULL;
搞完了,一切正常了。说明我们有良好的编码习惯是多么重要。另外出Bug时还是要多查自己的代码,基础库的问题没那么容易被我们撞上的。
 
查查man fclose,说了两次关闭的结果然是不确定的。
RETURN VALUE
Upon successful completion 0 is returned. Otherwise, EOF is returned and errno is
set to indicate the error. In either case any further access (including
another call to fclose()) to the stream results in undefined behavior.
再附上我自己的测试多次fopen的代码。
#include <stdio.h>
#include <pthread.h> char szPath[312] = {0};
char readbuf[312] = {0}; void* thread_func(void* p)
{
printf("\n\n....hello from son thread %d\n", pthread_self());
FILE *fp_r = NULL;
fp_r = fopen(szPath, "rb+");
printf("fp_r=%d after fopen rb+ \n", fp_r); if (fp_r == NULL)
return NULL; if (fread(readbuf, 10, 1, fp_r) < 0 )
{
printf("read fp_r error!!\n");
return NULL;
}
printf("read fp_r ok!!\n");
sleep(10); fclose(fp_r);
printf("close fp_r ok!!\n"); pthread_exit(NULL);
} int main()
{
FILE *fp_w = NULL; pthread_t t_id ; sprintf(szPath, "/disk1/tmp"); fp_w = fopen(szPath, "wb+");
printf("fp_w=%d after fopen wb+ \n", fp_w); if (fp_w == NULL)
{
return 0;
} if (fwrite(szPath, sizeof(szPath), 1, fp_w) != 1)
{
return -1;
} fclose(fp_w);
printf("fp_w=%d after fclose wb+ \n", fp_w);
fp_w = NULL; fp_w = fopen(szPath, "rb+");
printf("fp_w=%d after fopen rb+ \n", fp_w); if (fp_w == NULL)
return -1; if (fread(readbuf, 10, 1, fp_w) < 0)
{
printf("read fp_w error!!\n");
return -1;
}
printf("read fp_w ok!!\n"); if (pthread_create(&t_id, NULL, &thread_func, (void*)&t_id) != 0)
{
printf(" pthread_create fail!! \n");
return -1;
}
printf("create thread done.\n");
sleep(3); fclose(fp_w);
printf("close fp_w ok!!\n");
pthread_join(t_id,NULL);
printf("-----------------------\n"); return 0;
}

编译命令为:gcc tfclose.c -lpthread

两次fclose引发的血案的更多相关文章

  1. dubbox微服务实例及引发的“血案”

    Dubbo 是阿里巴巴公司开源的一个高性能优秀的服务框架,使得应用可通过高性能的 RPC 实现服务的输出和输入功能,可以和 Spring框架无缝集成. 主要核心部件: Remoting: 网络通信框架 ...

  2. Replication的犄角旮旯(七)-- 一个DDL引发的血案(下)(聊聊logreader的延迟)

    <Replication的犄角旮旯>系列导读 Replication的犄角旮旯(一)--变更订阅端表名的应用场景 Replication的犄角旮旯(二)--寻找订阅端丢失的记录 Repli ...

  3. 转:一个Sqrt函数引发的血案

    转自:http://www.cnblogs.com/pkuoliver/archive/2010/10/06/1844725.html 源码下载地址:http://diducoder.com/sotr ...

  4. 一个Sqrt函数引发的血案(转)

    作者: 码农1946  来源: 博客园  发布时间: 2013-10-09 11:37  阅读: 4556 次  推荐: 41   原文链接   [收藏]   好吧,我承认我标题党了,不过既然你来了, ...

  5. 一个字母引发的血案 java.io.File中mkdir()和mkdirs()

    一个字母引发的血案 明天开始放年假了,临放假前有个爬虫的任务,其中需要把网络图片保存到本地,很简单,马上写完了代码: //省略部分代码... Long fileId= (Long) data.get( ...

  6. form表单提交引发的血案

    最近,公司某条产品线上的一个功能出了问题:点击查询的时候,该页面在IE上直接卡死,chrome上会卡顿一段时间候提交表单进行查询.拿到这个bug单子以后,简单重现了下,基本上定位到是查询操作中的问题, ...

  7. elasticsearch5.0.1集群一次误删除kibana索引引发的血案

    elasticsearch集群中一次删除kibana索引引发的血案 1.问题发生的过程: 早上的时候有某个索引无法看到报表数据,于是就点该报表多次,估计集群被点挂了,报错:Elasticsearch ...

  8. 一个无锁消息队列引发的血案(六)——RingQueue(中) 休眠的艺术 [续]

    目录 (一)起因 (二)混合自旋锁 (三)q3.h 与 RingBuffer (四)RingQueue(上) 自旋锁 (五)RingQueue(中) 休眠的艺术 (六)RingQueue(中) 休眠的 ...

  9. 一个无锁消息队列引发的血案(五)——RingQueue(中) 休眠的艺术

    目录 (一)起因 (二)混合自旋锁 (三)q3.h 与 RingBuffer (四)RingQueue(上) 自旋锁 (五)RingQueue(中) 休眠的艺术 (六)RingQueue(中) 休眠的 ...

随机推荐

  1. TCP/IP协议栈源码图解分析系列10:linux内核协议栈中对于socket相关API的实现

    题记:本系列文章的目的是抛开书本从Linux内核源代码的角度详细分析TCP/IP协议栈内核相关技术 轻松搞定TCP/IP协议栈,原创文章欢迎交流, byhankswang@gmail.com linu ...

  2. 高版本jQuery设置checkbox状态注意事项

    jQuery 1.9 以后, 使用 .attr(“checked”, true) 或  attr(“checked”, “checked”) 将无法正确设置 checkbox的状态, 同样的, 使用 ...

  3. Quartz时间配置

    格式: [秒] [分] [小时] [日] [月] [周] [年]  序号 说明  是否必填  允许填写的值 允许的通配符  1  秒  是  0-59    , - * /  2  分  是  0-5 ...

  4. 深入理解java虚拟机系列(一):java内存区域与内存溢出异常

    文章主要是阅读<深入理解java虚拟机:JVM高级特性与最佳实践>第二章:Java内存区域与内存溢出异常 的一些笔记以及概括. 好了開始.假设有什么错误或者遗漏,欢迎指出. 一.概述 先上 ...

  5. crashRpt用法

    从官网上下载crashRpt的源代码,按说明编译出对应的lib和dll 1 在编译crashRpt的时候,在环境变量中设置  crashrptDir=D:\work\AIW\WebMicaps\Web ...

  6. core graphics path

    当UIKit无法满足画图需求的时候.就须要用到Core Graphics API.当中最普遍的就是path. 一些重要的概念 graphics context 能够理解成canvas.在ios里相应C ...

  7. 数据结构 《18》----RMQ 与 LCA 的等价性 (一)

    前言     RMQ: 数组 a0, a1, a2,..., an-1, 中求随意区间 a[i+1], a[i+2], ..., a[i+k] 的最小值     LCA: 求二叉树中两个节点的最低公共 ...

  8. SQL Server :理解BCM页

    原文:SQL Server :理解BCM页 今天我们来讨论下批量更改映射(Bulk Changed Map:BCM)页,还有大容量日志恢复模式( bulk logged recovery model  ...

  9. javascript - 浏览TOM大叔博客的学习笔记

    part1 ---------------------------------------------------------------------------------------------- ...

  10. Java EE (4) -- Java EE 6 Java Persistence API Developer Certified Expert(1z0-898)

    Overview of the Java Persistence API Describe the basics of Object Relational Mapping (ORM) Define t ...