QSqlQuery 可以让你的程序崩溃

原创
2015/02/24 23:03
阅读数 1.9W

  linux平台下。

  一个程序总是运行个两三天,或者一两天的时候突然崩溃了,以前发过一个讨论但是也没找到解决办法,使用的数据库是SQLITE

  使用GDB跟踪程序,结果找到了崩溃的地方却显示栈被破坏显示不出调用的具体方法,运行了好几次都是这样。定位到了 __memmove_ssse3在libc里面。

 为了恢复完整的栈信息在国外大牛那里找来两句话

(gdb)set $pc=*(void **)$esp
(gdb)set $esp=$esp+4

执行完就可以查看堆栈了(32位平台)。注意这个不能由core文件进入gdb,必须只能是运行着的程序崩溃被gdb捕捉到才行。

  查看堆栈看到了出错了地点

void xxx::execsql(QString sql)
{
   QMutexLocker locker(&this->readlock);
   QSqlQuery query(this->database);  //运行到这里崩溃了
   if(query.exec(sql)) ...
   ...
}

程序多线程向数据库插入数据,尽管我已经很小心地处理线程了,但是运行到未来某一时刻还是会崩溃。

  直到我又等了两三天测试,测试要看机缘啊,有时候它完全正常工作啊,有时候会崩溃。 结果就是这个方法执行的很频繁,而且同一时刻只有一个线程在访问数据库,但是这句话会崩溃。原因我还没有具体知道,我的推测: 因为在堆栈里面显示QSqlQuery里有数据库资源的申请与释放,在申请资源的时候出错了直接崩溃了。

  然后我就将query提升为类成员,代码变成如下了。


void xxx::execsql(QString sql)
{
   QMutexLocker locker(&this->readlock);
   if(this->query->exec(sql))
   ...
   ...
}
 

  再运行,好了。

  这个问题仅在多线程(即使加了锁)且操作数据库频繁的时候才会出现,其他情况下则运行良好。

展开阅读全文
打赏
3
21 收藏
分享
加载中
quanwei9958博主

引用来自“朝闻道”的评论

我也多线程操作数据库,从来没有问题。我觉得还是你自己的问题。如果你愿意,你把整个.h .cpp内容贴出来,我帮你找bug
你的程序运行多久?
2015/02/27 17:22
回复
举报
我也多线程操作数据库,从来没有问题。我觉得还是你自己的问题。如果你愿意,你把整个.h .cpp内容贴出来,我帮你找bug
2015/02/27 17:19
回复
举报
大哥我也有这个问题
04/01 14:11
回复
举报
quanwei9958博主
多少年了还在回复。。 以现在的眼光来看,不要用多线程。
04/01 14:50
回复
举报
quanwei9958博主

引用来自“朝闻道”的评论

你的代码好像没写解锁?
QMutexLocker构造方法里会对一个QMutex加锁,析构方法里unlock这个QMutex,这样可以安全地加锁与解锁,即使异常退出
2015/02/27 17:14
回复
举报
你的代码好像没写解锁?
2015/02/27 17:06
回复
举报
最好保证每个线程使用一个单独的数据库连接(connection name不一样)
2015/02/26 10:50
回复
举报
感觉略吊
2015/02/25 10:22
回复
举报
更多评论
打赏
8 评论
21 收藏
3
分享
返回顶部
顶部