当前位置 : 主页 > 网络编程 > 其它编程 >

c++多线程死锁调试

来源:互联网 收集:自由互联 发布时间:2023-07-02
c多线程死锁调试文章目录c多线程死锁调试c标准库中的锁RAIIstd::mutexstd::timed_mutex死锁调试Linux调试思路 多线程死锁调试 文章目录 c 多线程死锁调试 c标准库中的锁 RAII std::mutex std::timed_
c多线程死锁调试文章目录c多线程死锁调试c标准库中的锁RAIIstd::mutexstd::timed_mutex死锁调试Linux调试思路 多线程死锁调试

文章目录

    • c 多线程死锁调试
      • c标准库中的锁
        • RAII
        • std::mutex
        • std::timed_mutex
      • 死锁调试Linux
        • 调试思路4.4.2
      • 死锁条件
      • 解决办法

c标准库中的锁

  • std::mutex最基本的互斥对象
  • std::recursive_mutex可以递归使用重入的互斥对象递归调用不会导致死锁
  • std::timed_mutex带有超时功能可以提供一个等待时间如果超过这个时间则不会继续等待返回失败
  • std::recursive_timed_mutex超时可重入互斥对象
  • RAII

    • std::lock_gurad
    • std::unique_lock
    • std::shared_lock

    std::mutex

    std::mutex _mutex;std::lock_guard lock1(_mutex);std::lock_guard lock2(_mutex);

    std::timed_mutex

    如果使用超时功能需要调用try_lock_for方法

    std::timed_mutex _mutex;int get(){if(_mutex.try_lock_for(std::chrono::milliseconds(2000))){_mutex.unlock();}}void get(int data){if(_mutex.try_lock_for(std::chrono::milliseconds(2000))){_mutex.unlock();}}

    recursive_mutex和recursive_timed_mutex的使用方法与前面的mutex和timed_mutex一一对应只是recursive版本可以重入可以递归调用。只需要将mutex替换成recursive_mutex将timed_mutex替换成recursive_timed_mutex即可。

    死锁调试Linux

    /*test.cpp*/#include #include #include using namespace std;mutex _mutex1;mutex _mutex2;int data1;int data2;intdo_work_1(){std::cout <<"线程函数do_work_1开始\n" <调试思路4.4.2

    gdb ./test(gdb) r #程序卡住(gdb) ctrl c #使程序中断(gdb) bt #查看当前调用栈情况(gdb) f 3 #将栈帧切换到main函数#初步预测是死锁接下来查看线程执行了什么操作(gdb) i threads #查看当前进程中包含哪些线程(gdb) t 2 #切换到2号线程(gdb) bt #查看2号线程的堆栈信息找到代码所在的栈帧(gdb) f 5 #切换到代码所在栈帧(gdb) l #查看源码#确实发生死锁需要看其它线程进一步确认(gdb) t 3(gdb) bt(gdb) f 5(gdb) l

    死锁条件

    • 互斥条件
    • 保持和请求条件
    • 不可剥夺条件
    • 循环等待条件

    解决办法

    • 多个线程按照相同的顺序来使用锁
    • 减少锁的使用范围尽量把锁的使用范围局限于最小作用域中
    • 使用超时机制
    • 使用RAII机制
    【本文由:盐城网页开发公司 http://www.1234xp.com/yancheng.html 复制请保留原URL】
    网友评论