IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 系统运维 -> Linux Ftrace介绍与原理 -> 正文阅读

[系统运维]Linux Ftrace介绍与原理

Ftrace介绍

荣涛
2021年10月19日

文档修改日志

日期修改内容修改人备注
2021年10月19日创建荣涛

1. debugfs

默认情况下,debugfs挂载在:

/sys/kernel/debug

当然,你可以重新挂在:

mkdir /debug
sudo mount -t debugfs nodev /debug

2. tracing

2.1. /sys/kernel/debug/

# ls /sys/kernel/debug/
acpi             clk               error_injection     intel_powerclamp  pkg_temp_thermal  sleep_time        usb
asoc             device_component  extfrag             iwlwifi           pmc_core          soundwire         wakeup_sources
bdi              devices_deferred  fault_around_bytes  kprobes           pm_genpd          split_huge_pages  x86
block            dma_buf           frontswap           kvm               pwm               sunrpc            zsmalloc
bluetooth        dmaengine         gpio                mce               ras               suspend_stats     zswap
cec              dma_pools         hid                 mei0              regmap            swiotlb
cleancache       dri               ieee80211           mmc0              sched_debug       thunderbolt
clear_warn_once  dynamic_debug     intel_lpss          pinctrl           sched_features    tracing

2.2. available_tracers

# cat /sys/kernel/debug/tracing/available_tracers 
hwlat blk function_graph wakeup_dl wakeup_rt wakeup function nop

2.2.1. function|function_graph

开启函数追踪

echo function > /sys/kernel/debug/tracing/current_tracer
cat /sys/kernel/debug/tracing/trace

关闭函数追踪

echo nop > /sys/kernel/debug/tracing/current_tracer

2.2.2. irqsoff

echo irqsoff > /sys/kernel/debug/tracing/current_tracer
cat /sys/kernel/debug/tracing/trace

我的环境不支持

2.3. tracing_on

关闭函数追踪

echo 0 > /sys/kernel/debug/tracing/tracing_on

2.4. set_ftrace_filter

cat set_ftrace_filter 
#### all functions enabled ####
echo schedule > /sys/kernel/debug/tracing/set_ftrace_filter
echo function > /sys/kernel/debug/tracing/current_tracer
cat /sys/kernel/debug/tracing/trace
echo "" > /sys/kernel/debug/tracing/set_ftrace_filter
echo nop > /sys/kernel/debug/tracing/current_tracer

追加

echo schedule_tail >> /sys/kernel/debug/tracing/set_ftrace_filter
cat /sys/kernel/debug/tracing/set_ftrace_filter

可以使用正则表达式:

echo 'sched*' > /sys/kernel/debug/tracing/set_ftrace_filter
cat /sys/kernel/debug/tracing/set_ftrace_filter

2.5. set_ftrace_notrace

清空:

echo > /sys/kernel/debug/tracing/set_ftrace_filter
cat /sys/kernel/debug/tracing/set_ftrace_notrace 
#### no functions disabled ####

剔除:

echo '*lock*' > /sys/kernel/debug/tracing/set_ftrace_notrace

3. events

# ls /sys/kernel/debug/tracing/events
alarmtimer        devlink     hda             iomap        mdio     oom             regmap   sunrpc    wbt
asoc              dma_fence   hda_controller  iommu        mei      page_isolation  resctrl  swiotlb   workqueue
block             drm         hda_intel       irq          migrate  pagemap         rpm      syscalls  writeback
bpf_test_run      enable      header_event    irq_matrix   mmc      page_pool       rseq     task      x86_fpu
bpf_trace         exceptions  header_page     irq_vectors  module   percpu          rtc      tcp       xdp
bridge            fib         huge_memory     kmem         msr      power           sched    thermal   xen
cfg80211          fib6        hyperv          kvm          napi     printk          scsi     timer     xfs
cgroup            filelock    i2c             kvmmmu       neigh    qdisc           signal   tlb       xhci-hcd
clk               filemap     i915            kyber        net      random          skb      ucsi
compaction        fs_dax      initcall        libata       netlink  ras             smbus    udp
context_tracking  ftrace      intel_iommu     mac80211     nmi      raw_syscalls    sock     vmscan
cpuhp             gvt         intel-sst       mce          nvme     rcu             spi      vsyscall

events/sched

# ls /sys/kernel/debug/tracing/events/sched/
enable                  sched_pi_setprio    sched_process_wait  sched_stick_numa             sched_wakeup_new
filter                  sched_process_exec  sched_stat_blocked  sched_swap_numa              sched_waking
sched_kthread_stop      sched_process_exit  sched_stat_iowait   sched_switch
sched_kthread_stop_ret  sched_process_fork  sched_stat_runtime  sched_wait_task
sched_migrate_task      sched_process_free  sched_stat_sleep    sched_wake_idle_without_ipi
sched_move_numa         sched_process_hang  sched_stat_wait     sched_wakeup

events/sched/sched_wakeup

# ls /sys/kernel/debug/tracing/events/sched/sched_wakeup
enable  filter  format  hist  id  trigger

3.1. 使能sched_wakeup event

echo nop > /sys/kernel/debug/tracing/current_tracer
echo 1 > /sys/kernel/debug/tracing/events/sched/sched_wakeup/enable
cat trace

3.2. 使能全部sched events

echo 1 > /sys/kernel/debug/tracing/events/sched/enable

3.3. 使能全部events

echo 1 > /sys/kernel/debug/tracing/events/enable

4. 参考

  • Slice: Ftrace: Latency Tracing, Steven Rostedt

Copyright (C) CESTC Com.
Ftrace原理

荣涛
2021年10月19日

文档修改日志

日期修改内容修改人备注
2021年10月19日新建荣涛

1. ftrace原理

asmlinkage __visible void __sched schedule(void)
{
    struct task_struct *tsk = current;
    sched_submit_work(tsk);
    __schedule();
}

反汇编:

<schedule>:
    55                     push %rbp
    48 8b 04 25 80 c0 0e   mov 0xffffffff810ec080,%rax
    81
    48 89 e5               mov %rsp,%rbp
    48 8b 00               mov (%rax),%rax
    5d                     pop %rbp
    e9 db fa ff ff         jmpq ffffffff810bb100 <__schedule>
    66 66 2e 0f 1f 84 00   data16 nopw %cs:0x0(%rax,%rax,1)
    00 00 00 00

添加-pg选项的反汇编

<schedule>:
    55                     push %rbp
    48 89 e5               mov %rsp,%rbp
    e8 37 2e 00 00         callq ffffffff810f7430 <mcount>
    5d                     pop %rbp
    48 8b 04 25 80 d0 15   mov 0xffffffff8115d080,%rax
    81
    48 8b 00               mov (%rax),%rax
    e9 96 fa ff ff         jmpq ffffffff810f40a0 <__schedule>
    66 0f 1f 44 00 00      nopw 0x0(%rax,%rax,1)

在这里插入图片描述

简化schedule函数

<schedule>:
    push %rbp
    mov %rsp,%rbp
    callq <mcount>
    pop %rbp

调用mcount

<mcount>:
    retq

在这里插入图片描述

1.1. 内核中mcount实现

以内核为例,内核里有源码和脚本scripts/recordmcount。整体步骤如下:

  1. 查找所有调用mcount的位置
  2. 创建table
  3. 链接table到目标文件
  4. 新的section为__mcount_loc
<schedule>:
    push %rbp
    mov %rsp,%rbp
    callq <mcount>
    pop %rbp
    []
<preempt_schedule_irq>:
    push %rbp
    mov %rsp,%rbp
    push %rbx
    callq <mcount>
    pop %rbp
    []
<_cond_resched>:
    push %rbp
    mov %rsp,%rbp
    push %rbx
    callq <mcount>
    pop %rbp
    []
<yield>:
    push %rbp
    mov %rsp,%rbp
    push %rbx
    callq <mcount>
    pop %rbp
    []

__mcount_loc表:

<__mcount_loc>:
    &schedule + 0x4
    &preempt_schedule_irq + 0x4
    &_cond_resched + 0x4
    &yield + 0x4

在这里插入图片描述

并把__mcount_loc表加入到对应的目标文件中:

在这里插入图片描述

kernel/sched/core.o

<__mcount_loc>:
    &schedule + 0x4
    &preempt_schedule_irq + 0x4
    &_cond_resched + 0x4
    &yield + 0x4

mm/swap.o:

<__mcount_loc>:
    &put_page + 0x4
    &__get_page_tail + 0x4
    &put_pages_list + 0x4
    &get_kernel_pages + 0x4

fs/read_write.o

<__mcount_loc>:
    &new_sync_read + 0x4
    &vfs_setpos + 0x4
    &fixed_size_llseek + 0x4
    &default_llseek + 0x4

在编译vmlinux过程,如下:

在这里插入图片描述

然后将所有__mcount_loc表加入vmLinux中:

<__start_mcount_loc>:
    &schedule + 0x4
    &preempt_schedule_irq + 0x4
    &_cond_resched + 0x4
    &yield + 0x4
    &put_page + 0x4
    &__get_page_tail + 0x4
    &put_pages_list + 0x4
    &get_kernel_pages + 0x4
    &new_sync_read + 0x4
    &vfs_setpos + 0x4
    &fixed_size_llseek + 0x4
    &default_llseek + 0x4
    [...]
<___end_mcount_loc>:

在这里插入图片描述

而mcount中实际上都是地址:

<__start_mcount_loc>:
    0xffffffff810f45f4
    0xffffffff810f4635
    0xffffffff810f4684
    0xffffffff810f4734
    0xffffffff81087ad4
    0xffffffff81087b14
    0xffffffff81087bd5
    0xffffffff81087c41
    0xffffffff810a7aa0
    0xffffffff810a7bd4
    0xffffffff810a7d34
    0xffffffff810a7d7d
    [...]
<___end_mcount_loc>:

最终的vmlinux为:

<schedule>:
    push %rbp
    mov %rsp,%rbp
    callq <mcount>
    pop %rbp
    []
<preempt_schedule_irq>:
    push %rbp
    mov %rsp,%rbp
    push %rbx
    callq <mcount>
    pop %rbp
    []
<_cond_resched>:
    push %rbp
    mov %rsp,%rbp
    push %rbx
    callq <mcount>
    pop %rbp
    []
<yield>:
    push %rbp
    mov %rsp,%rbp
    push %rbx
    callq <mcount>
    pop %rbp
    []
<__start_mcount_loc>:
    [...]
<___end_mcount_loc>:

在这里插入图片描述

1.2. tracing实现

  1. 需要一种方法,可以使能tracing
  2. 抛弃mcount section
  3. mcount section不够用
  4. tracing也需要保存状态

<ftrace_pages>如下

ip = 0xffffffff81087ad4
flags = 0
ip = 0xffffffff81087b14
flags = 0
ip = 0xffffffff81087bd5
flags = 0
ip = 0xffffffff81087c41
flags = 0
ip = 0xffffffff810a7aa0
flags = 0
ip = 0xffffffff810a7bd4
flags = 0
ip = 0xffffffff810a7d34
flags = 0
ip = 0xffffffff810a7d7d
flags = 0
ip = 0xffffffff810f45f4
flags = 0
ip = 0xffffffff810f4635
flags = 0
ip = 0xffffffff810f4684
flags = 0
ip = 0xffffffff810f4734
flags = 0
[]

上面的选项对应:

# cat available_filter_functions
put_page
__get_page_tail
put_pages_list
get_kernel_pages
new_sync_read
vfs_setpos
fixed_size_llseek
default_llseek
schedule
preempt_schedule_irq
_cond_resched
yield

开启tracing 过滤filter

# echo yield > set_ftrace_filter
# echo schedule >> set_ftrace_filter
# cat set_ftrace_filter
schedule
yield

在这里插入图片描述

  • First 29 bits are for counter
    • Every registered callback increments +1
  • bit 29 (starts from zero) – ENABLED
  • bit 30 – REGS
  • bit 31 – REGS_EN

那么ftrace_pagesflags被修改为:

ip = 0xffffffff81087ad4
flags = 0
ip = 0xffffffff81087b14
flags = 0
ip = 0xffffffff81087bd5
flags = 0
ip = 0xffffffff81087c41
flags = 0
ip = 0xffffffff810a7aa0
flags = 0
ip = 0xffffffff810a7bd4
flags = 0
ip = 0xffffffff810a7d34
flags = 0
ip = 0xffffffff810a7d7d
flags = 0
ip = 0xffffffff810f45f4
flags = 0x20000001
ip = 0xffffffff810f4635
flags = 0
ip = 0xffffffff810f4684
flags = 0
ip = 0xffffffff810f4734
flags = 0xa0000001
[]

那么,vmlinux被修改为:

<schedule>:
    push %rbp
    mov %rsp,%rbp
    call ftrace_caller
    pop %rbp
    []
<preempt_schedule_irq>:
    push %rbp
    mov %rsp,%rbp
    push %rbx
    nop
    pop %rbp
    []
<_cond_resched>:
    push %rbp
    mov %rsp,%rbp
    push %rbx
    nop
    pop %rbp
    []
<yield>:
    push %rbp
    mov %rsp,%rbp
    push %rbx
    call ftrace_regs_caller
    pop %rbp
    []

如下图:

在这里插入图片描述

2. 参考

  • Ftrace Kernel Hooks: More than just tracing, Steven Rostedt

Copyright (C) CESTC Com.
  系统运维 最新文章
配置小型公司网络WLAN基本业务(AC通过三层
如何在交付运维过程中建立风险底线意识,提
快速传输大文件,怎么通过网络传大文件给对
从游戏服务端角度分析移动同步(状态同步)
MySQL使用MyCat实现分库分表
如何用DWDM射频光纤技术实现200公里外的站点
国内顺畅下载k8s.gcr.io的镜像
自动化测试appium
ctfshow ssrf
Linux操作系统学习之实用指令(Centos7/8均
上一篇文章      下一篇文章      查看所有文章
加:2021-10-24 15:13:03  更:2021-10-24 15:14:09 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/15 21:10:48-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码