用qemu+gdb tcp server+CDT调试linux内核启动-起步

说明: 环境信息与 用virtualbox+模拟串口+CDT调试linux内核 TCP IP协议栈-起步 提到的一样,并且本文中会有很多个步骤与之相同,请参考。

S1. 开发机:我是将一个老的索尼的笔记本装了Ubuntu桌面版本作为开发环境,版本号是Ubuntu 16.04.4 LTS,后面在某些步骤中也会称之为host。

S2. JDK使用的是java version "1.7.0_80"。 官网也有下载。后面CDT开发工具要用。

S3. Eclipse版本 Mars.2 Release (4.5.2),CDT(8.8.1)使用的插件的方式安装的。 相关软件在eclipse官网均可以获得。至于怎么装插件,请网上搜索。

S4. 开发机安装build工具链。

sudo apt-get install gcc
sudo apt-get install build-essential

S5. 开发机安装qemu sudo apt-get install qemu

创建虚拟磁盘

创建rootfs

dd if=/dev/zero of=rootfs.img bs=1M count=10
mkfs.ext3 rootfs.img
mkdir rootfs
sudo mount -t ext3 -o loop rootfs.img rootfs
cd rootfs/
sudo mkdir dev proc sys

S6. 编译安装busybox到rootfs

cd ~
mkdir 04.busybox
cd 04.busybox/
wget https://busybox.net/downloads/busybox-1.25.1.tar.bz2
tar -xjvf busybox-1.25.1.tar.bz2
cd busybox-1.25.1 make menuconfig
配置编译采用静态链接
BusyboxSettings->Build options->BuildBusybox as a static binary
sudo make install CONFIG_PREFIX=/home/simon/005.vm/01.qemu/rootfs
cd 005.vm/01.qemu
sudo umount rootfs
```shell S7. 在开发机上准备内核代码。
到[内核官网](https://mirrors.edge.kernel.org/pub/linux/kernel/v4.x/)下载你要用的内核,我的用的是[4.4.19]版本(https://mirrors.edge.kernel.org/pub/linux/kernel/v4.x/linux-4.4.19.tar.gz)。可以用wget xxx内核链接地址的办法下载,我的是:
```shell
cd ~
mkdir 004.code
cd 004.code
wget https://mirrors.edge.kernel.org/pub/linux/kernel/v4.x/linux-4.4.19.tar.gz
tar -xzvf linux-4.4.19.tar.gz
cd linux-4.4.19 S8. 在开发机上准备编译安装内核。
修改Makefile文件(linux-4.4.19目录下),将其中的O2字样修改成O1,目前不支持O0编译。但是[有个文章](https://github.com/figozhang/runninglinuxkernel_4.0)说可以通过修改内核代码达到使用O0编译的目的。我试了试,没成功。如果谁成功了,可以告诉我,谢谢。
安装必要的依赖:
```shell
sudo apt-get install libncurses5-dev
sudo apt-get install libssl-dev
sudo apt-get install bc

调试目标机安装build工具链。

sudo apt-get install gcc
sudo apt-get install build-essential

配置内核选项,其实只需要执行这步生成config文件,配置项不用修改,我们要的都有。

make menuconfig

然后选择 exit 然后选择yes 生成config文件。

make CONFIG_DEBUG_SECTION_MISMATCH=y -j2

此步骤需要很长时间,2-5小时不等,正常可以在睡觉前执行,第二天早上起来看结果。

编译成功后,在你的linux-4.4.19目录/arch/x86_64/boot/bzImage 这个文件,后面启动会用

S9. 验证

qemu-system-x86_64 -kernel 004.code/linux-source-4.4.19/arch/x86_64/boot/bzImage -hda ~/005.vm/01.qemu/rootfs.img -append "root=/dev/sda"

能成功启动即可。

S10. 创建CDT工程

打开装了CDT插件的eclipse。

window-->preferences-->General-->Workspace 去掉勾选 Build Automatically。

window-->preferences-->C/C++-->indexer 去掉勾选 Enable indexer。

file-->new-->c project-->project name填写你自己合意的,比如linux-kernel-study / 去掉use default location,location输入框中选择你的linux-4.4.19路径。 / project type 选择 Makefile project-Empty project / Toolschains选择Linux GCC-->next-->Advanced Setting-->C/C++ Build-->去掉勾选use default build command, build command输入框内写上 make CONFIG_DEBUG_SECTION_MISMATCH=y -j2,build directory选择你的linux-4.4.19路径。 / Behavior页签 Build(Increament build) 输入框中输入一个空格即可。然后完成工程创建即可。

点击工具栏中的绿色小虫子右边的箭头,选择Debug Configurations-->C/C++ Remote Application(双击)-->proiect选择你刚创建的project / C/C++ Application选择你的linux-4.4.19路径下的vmlinux。 / 选中 Disable auto build 点击select other换一个启动器 选择 GDB(DSF)Manual Remote Debugging...

点击debugger页签 stop on startup at 填写start_kernel,点击connection子页签,type选择TCP,hostname填写localhost,prort number填写1234 。此处标志为待填13.1。

点击apply close即可。

S11. 修复GDB问题

后面步骤用gdb远程调试时会报错: Remote ‘g’ packet reply is too long

先看下您的gdb的版本,然后下载相同版本进行修复并并编译。

gdb -version
wget http://ftp.gnu.org/gnu/gdb/gdb-7.11.1.tar.gz
tar -xzvf gdb-7.11.1.tar.gz
cd gdb-7.11.1
vi gdb/remote.c

将下面两行注释掉

//  if (buf_len > 2 * rsa->sizeof_g_packet)
// error (_("Remote 'g' packet reply is too long: %s"), rs->buf);
sudo ./configure
sudo make
sudo make install

S12. 启动调试目标机并调试

qemu-system-x86_64 -s -S -kernel 004.code/linux-source-4.4.19/arch/x86_64/boot/bzImage -hda ~/005.vm/01.qemu/rootfs.img -append "root=/dev/sda"

cd 你的linux-4.4.19路径

gdb vmlinux

target remote localhost:1234

此时就应该连接上目标机器了。

b start_kernel

按gdb的c指令便可以使得调试目标机继续启动下去。

执行到内核启动时,断点便会被命中。

S13. 在开发机用CDT调试。

重新启动调试目标机,这次不用gdb命令行的方式,用CDT可视化界面。

点击CDT工具栏中的绿色小虫子右边的箭头,选择1New_configuration,如果有什么错误提示不用理会,继续proceed。 连接成功后,控制台会有输出,也可以在控制台输入gdb调试指令,也可以在CDT上直接加断点。

这时你会发现在 start_kernel处停了下来。

F5 F6这些快捷键都可以用。

用qemu+gdb tcp server+CDT调试linux内核启动-起步的更多相关文章

  1. 用virtualbox+模拟串口+CDT调试linux内核 TCP/IP协议栈-起步

    经常有人问一台机器如何将hello经网络发送给另一台机器,我确实是不知道,只能看代码了. 说明:本人对内核的研究学习也是刚刚起步,有很多不了解的,所以文中可能会有一些"一本正经的胡扯&quo ...

  2. qemu通过命令行直接引导linux内核启动

    qemu -kernel vmlinuz-3.14.0 -hda img_custom -append root=/dev/sda1

  3. 在qemu环境中用gdb调试Linux内核

    简介 对用户态进程,利用gdb调试代码是很方便的手段.而对于内核态的问题,可以利用crash等工具基于coredump文件进行调试.其实我们也可以利用一些手段对Linux内核代码进行gdb调试,qem ...

  4. Gdb远程调试Linux内核遇到的Bug

    知识共享许可协议本作品采用知识共享署名 4.0 国际许可协议进行许可.转载保留声明头部与原文链接https://luzeshu.com/blog/gdb-bug 本博客同步在http://www.cn ...

  5. 使用QEMU调试Linux内核代码

    http://blog.chinaunix.net/uid-20729583-id-1884617.html http://www.linuxidc.com/Linux/2014-08/105510. ...

  6. 学习构建调试Linux内核网络代码的环境MenuOS系统

    构建调试Linux内核网络代码的环境MenuOS系统 一.前言 这是网络程序设计的第三次实验,主要是学习自己编译linux内核,构建一个具有简易功能的操作系统,同时在系统上面进行调试linux内核网络 ...

  7. TCP/IP协议栈在Linux内核中的运行时序分析

    网络程序设计调研报告 TCP/IP协议栈在Linux内核中的运行时序分析 姓名:柴浩宇 学号:SA20225105 班级:软设1班 2021年1月 调研要求 在深入理解Linux内核任务调度(中断处理 ...

  8. 用 kGDB 调试 Linux 内核

    简介 这个文档记录了用kGDB调试Linux内核的全过程,都是在前人工作基础上的一些总结.以下操作都是基于特定板子来进行,但是大部分都能应用于其他平台. 要使用KGDB来调试内核,首先需要修改conf ...

  9. VELT-0.1.5开发:使用kgdb调试Linux内核【转】

    转自:http://demo.netfoucs.com/lights_joy/article/details/44106589 VELT的全称是Visual EmbedLinuxTools,它是一个与 ...

随机推荐

  1. cas实现单点登录原理

    1.基于Cookie的单点登录的回顾        基于Cookie的单点登录核心原理: 将用户名密码加密之后存于Cookie中,之后访问网站时在过滤器(filter)中校验用户权限,如果没有权限则从 ...

  2. pixhawk 固件Firmware内执行make px4fmu-v2_default 编译报错解决办法

    执行下列指令报错 make px4fmu-v2_default /bin/sh: 1: Tools/check_cmake.sh: Permission denied Makefile:44: Not ...

  3. CF713C Sonya and Problem Wihtout a Legend & hihocoder1942 单调序列

    这两个题是一样的,不过数据范围不同. 思路1: 在CF713C中,首先考虑使生成序列单调不下降的情况如何求解.因为单调上升的情况可以通过预处理将a[i]减去i转化成单调不下降的情况. 首先,生成的序列 ...

  4. jsp-简单的猜数小游戏

    <%@ page language="java" import="java.util.*" pageEncoding="utf-8"% ...

  5. Appium基础五:appium相关API

    1.获取信息类: 1.1 获取当前界面的组件: driver.currentActivity(); //获取当前界面的activity,可用于断言是否跳转到预期的activity 1.2 获取当前页面 ...

  6. filter和map的使 使得数组对象变数组

    let UnitList = this.paytypeData.filter( item => item.CheckBox === true ).map(axis => axis.Unit ...

  7. 如何在Android Studio中导入JNI生成的.so库

    由于在原来的ADT的Eclipse环境中,用ndk_build工具生成了相应的各个.so库文件之后,eclipse工具就会自动把这些库导入到apk中.而Android Studio目前为止(0.86版 ...

  8. [Java]获取byte数组的实际使用长度

    背景:byte.length只能获取到初始化的byte数组长度,而不是实际使用的长度,因此想要获取到实际的使用长度只能靠其他方法实现. 方法一: public class ByteActualLeng ...

  9. 【虚拟机-磁盘管理】理解及快速测定 Azure 虚拟机的磁盘性能

    随着越来越多的用户将生产系统迁移到 Azure 平台的虚拟机服务中,Azure 虚拟机的性能愈发被关注.传统的数据中心中,我们通常使用 CPU,内存,存储和网络的性能来衡量生产压力.特别是对于 IO ...

  10. SQL server的一个分割表值函数

    CREATE FUNCTION [dbo].[Fn_Split] ( @SplitString text, -- 如果要传入NText类型,下面需要相应的修改,注释行为NText下同 ) = ','- ...