Linux系统之debugfs详解

debugfs 是一个用于检查和修改 ext2/ext3/ext4 文件系统状态的交互式调试工具。它可以直接操作文件系统的底层结构,适合高级用户进行文件系统修复和数据恢复。

基本语法

debugfs [选项] [设备文件]

主要选项

选项 描述
-w 以读写模式打开文件系统(默认为只读)
-c 以灾难恢复模式打开(不读取位图,强制只读)
-i 指定设备为 e2image 创建的镜像文件
-d 配合 -i 使用,指定数据源设备
-b 指定块大小(代替自动检测)
-s 从指定块号读取超级块(需配合 -b
-f 从文件读取并执行命令
-D 使用直接 I/O 访问设备
-R 执行单个命令后退出
-V 显示版本信息

常用命令

文件系统信息

命令 描述
show_super_stats 显示超级块和块组描述符信息
feature 查看或修改文件系统特性
freefrag 报告空闲空间碎片情况

文件操作

命令 描述
ls [-d] [-l] 列出目录内容(-d显示已删除项)
stat 显示inode信息
cat 显示文件内容
dump 输出文件 导出文件内容
write 源文件 目标文件 写入新文件

inode操作

命令 描述
icheck 块号... 查找使用指定块的inode
ncheck inode号... 查找inode的路径名
list_deleted_inodes 列出已删除的inode
undel 恢复已删除的inode

块操作

命令 描述
testb 块号 测试块是否已分配
setb 块号 标记块为已分配
freeb 块号 释放块
zap_block 块号 擦除块内容

目录操作

命令 描述
htree_dump 显示哈希目录树结构
dirsearch 目录inode 文件名 在目录中搜索文件

日志操作

命令 描述
logdump 转储日志内容

使用示例

  1. 查看超级块信息:

    debugfs /dev/sda1
    debugfs: show_super_stats
    
  2. 恢复已删除文件:

    debugfs /dev/sda1
    debugfs: list_deleted_inodes
    debugfs: undel <1234> /recovered_file
    
  3. 导出文件内容:

    debugfs -R "dump <1234> /tmp/recovered" /dev/sda1
    
  4. 检查块分配:

    debugfs -R "testb 1000-2000" /dev/sda1
    
  5. 查找文件碎片情况:

    debugfs -R "filefrag -v /path/to/file" /dev/sda1
    

debugfs 的常见问题解答,结合 man 页面和知识库信息整理而成

1. 如何挂载 debugfs

命令

mount -t debugfs none /sys/kernel/debug

或在 /etc/fstab 中添加:

debugfs /sys/kernel/debug debugfs defaults 0 0

注意

  • 默认只有 root 用户有权限访问 /sys/kernel/debug
  • 若未挂载,内核模块无法通过 debugfs 导出调试信息。

2. 如何查看或修改文件系统的超级块信息?

步骤

  1. 进入交互式 debugfs
    sudo debugfs /dev/sdXX  # 替换为你的设备(如 /dev/sda1)
    
  2. debugfs 提示符下输入:
    dumpe2fs /dev/sdXX | grep superblock  # 查看超级块备份位置
    # 或直接查看当前超级块信息:
    debugfs:  stats  # 显示文件系统统计信息
    debugfs:  features  # 查看文件系统特性
    
  3. 修改超级块(需谨慎):
    debugfs:  set_super_value feature_incompat 0x...  # 修改特定标志
    

3. 如何通过 debugfs 查看文件的 inode 和块分配?

命令示例

  • 查看文件的 inode 号:
    debugfs:  Stat /path/to/file  # 注意路径相对文件系统根
    
  • 查看 inode 的块分配:
    debugfs:  blocks <inode_num>  # 输出该 inode 使用的所有数据块
    
  • 查找特定块对应的 inode:
    debugfs:  icheck <block_num>  # 查看哪个 inode 占用该块
    

4. 如何通过 debugfs 导出文件内容?

方法

debugfs:  dump /path/to/file outfile  # 将文件内容导出到本地文件

或非交互式:

sudo debugfs -R "dump /file outfile" /dev/sdXX

5. 如何在内核模块中使用 debugfs API 导出调试信息?

步骤

  1. 包含头文件
    #include 
    
  2. 创建目录和文件
    struct dentry *dbg_dir;
    dbg_dir = debugfs_create_dir("my_driver", NULL);  // 在 debugfs 根下创建目录
    debugfs_create_file("my_file", 0644, dbg_dir, NULL, &my_fops);  // 创建文件
    
  3. 实现文件操作(如读写):
    static ssize_t my_read(struct file *filp, char __user *ubuf, size_t count, loff_t *off) {
        return simple_read_from_buffer(ubuf, count, off, my_data, my_size);
    }
    static struct file_operations my_fops = {
        .read = my_read,
        .write = my_write,
    };
    
  4. 清理资源
    module_exit() {
        debugfs_remove_recursive(dbg_dir);
    }
    

6. debugfsprocfs/sysfs 的主要区别?

特性 debugfs procfs sysfs
用途 内核调试专用,无严格格式限制 系统和进程信息(只读为主) 设备和驱动配置(可读写)
结构规则 无强制规则,随意组织 固定路径(如 /proc/cpuinfo 标准化层次结构(按设备组织)
权限 默认仅 root 可访问 普通用户可读部分信息 按设备权限控制
稳定性 接口不保证稳定,可能随内核变化 核心接口稳定 标准化接口,需兼容性维护

7. 如何修复文件系统错误(如丢失块)?

步骤

  1. 进入 debugfs(需读写模式):
    sudo debugfs -w /dev/sdXX
    
  2. 标记块为未分配:
    debugfs:  freeb <block_num>  # 释放错误块
    
  3. 修复 inode 指向问题:
    debugfs:  clri <inode_num>  # 清除无效 inode
    

注意:操作前务必备份数据,错误操作可能导致数据丢失。

8. 如何通过 debugfs 查看日志(Journal)信息?

命令

sudo debugfs -R "logdump" /dev/sdXX  # 查看 ext3/ext4 日志内容

或交互式中:

debugfs:  logdump -i <journal_inode>  # 指定日志 inode 查看

9. 常见错误及解决方法

  • 错误:debugfs: couldn't mount device
    原因:未挂载 debugfs 或设备路径错误。
    解决:先挂载 /sys/kernel/debug,并确认设备存在。

  • 错误:debugfs: bad magic number in superblock
    原因:设备非 ext2/ext3/ext4 文件系统。
    解决:检查设备类型,使用 file -s /dev/sdXX 确认。

  • 错误:debugfs: No such file or directory
    原因:路径错误或文件不存在。
    解决:使用 lscd / 切换到根目录后重新定位。

10. 如何通过 debugfs 调试驱动程序?

步骤

  1. 在驱动模块中创建 debugfs 文件:
    debugfs_create_u32("register", 0644, dbg_dir, &my_register);  // 导出寄存器值
    
  2. 用户空间操作:
    echo 0x1234 > /sys/kernel/debug/my_driver/register  # 写入寄存器值
    cat /sys/kernel/debug/my_driver/register            # 读取寄存器值
    

你可能感兴趣的:(运维,linux,运维,debugfs)