GDB调试

前言

C++聊天服务器项目加上数据库连接池时出了bug。可我不会在Linux环境下调试,浪费了很多时间。虽然最后将这个bug解决了,但是这给了我一个警钟:必须要会GDB的简单使用
我将复现bug,使用GDB一步步地将bug揪出来。
其实这个bug,我事后回想了下,并不离谱,稍微推理下就应该知道大概在哪里出了岔子。

1、bug 复现

mysql Commands out of sync; you can’t run this command now

数据库连接池在并发环境下,执行select后出错(用户登录)(insert随便用)(第一条select就报错)。当时的解决方向跑到了数据库的锁(被网上搜到的指偏了):读的时候对表加了独占锁。

现在给出不需要调试的找bug思路:第一条select就报错,但是在此之前数据库并没有读表!所以大概率不是锁的问题,而是登录模块出了问题。

当时的bug是这样的:处理登录功能会跳转到usermodel.cpp里面执行这个函数(未修改版):

// 根据用户号码查询用户信息
User UserModel::query(int id)
{
    // 1.组装sql语句
    char sql[1024] = {0};
    sprintf(sql, "select * from user where id = %d", id);

    MySQL mysql;
    MYSQL_RES *res = mysql.query(sql);
    if (res != nullptr)
    {
        MYSQL_ROW row = mysql_fetch_row(res);
        if (row != nullptr)
        {
            User user;
            user.setId(atoi(row[0]));
            user.setName(row[1]);
            user.setPwd(row[2]);
            user.setState(row[3]);
            mysql_free_result(res);
            return user;
        }
    }

    return User();
}

我是在已经写好的代码上改的,向线程池申请资源时不需要再连接,所以我把所有的connect()删了,但是这个角落的删了连接、且不是向池申请,所以是空连接。

ConnectionPool* cp = ConnectionPool::getConnectionPool();
shared_ptr<MySQL>mysql = cp->getConnection();
MYSQL_RES *res = mysql->query(sql);

那么,如果我当时会gdb调试的话,情况会怎样呢?

2、GDB

请添加图片描述
请添加图片描述
请添加图片描述

请添加图片描述
设置断点 b chatservice.cpp:67 之后使用 run运行到断点,再 n/s/finish 交替看运行过程。

比cout加ctrl点击还是要方便许多的。可以看到执行过程,将排查范围精准下来。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
FreeRTOS是一个开源的实时操作系统,它提供了一套用嵌入式系统的任务调度和管理机制。GDB(GNU Debugger)是一个功能强大的调试工具,可以用于调试C/C++程序。在使用FreeRTOS进行开发时,可以结合GDB进行调试。 要在FreeRTOS中使用GDB进行调试,需要进行以下几个步骤: 1. 配置编译器:首先,需要确保你的编译器支持GDB调试功能。常用的编译器如GCC和Keil都支持GDB调试。 2. 编译选项:在编译FreeRTOS应用程序时,需要添加一些编译选项以支持GDB调试。例如,在GCC中,可以使用"-g"选项来生成调试信息。 3. 连接器脚本:在链接应用程序时,需要使用连接器脚本来指定调试信息的位置。连接器脚本可以告诉GDB在哪里找到符号表和调试信息。 4. 启动GDB调试:在编译和链接完成后,可以使用GDB启动调试会话。可以通过命令行输入"gdb"命令来启动GDB,并使用"target remote"命令连接到目标设备。 5. 设置断点:在GDB中,可以使用"break"命令设置断点。可以设置函数断点、行号断点或地址断点等。 6. 执行调试:一旦设置好断点,可以使用GDB的调试命令来执行程序。可以使用"run"命令来运行程序,使用"step"命令逐行执行,使用"next"命令执行下一行,使用"continue"命令继续执行等。 7. 查看变量:在调试过程中,可以使用GDB的"print"命令来查看变量的值。可以使用"info locals"命令查看局部变量,使用"info global"命令查看全局变量等。 8. 结束调试:当调试完成后,可以使用GDB的"quit"命令退出调试会话。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值