美文网首页
Linux I/O 性能分析 - 概念篇

Linux I/O 性能分析 - 概念篇

作者: 偏心念丶 | 来源:发表于2024-01-24 09:08 被阅读0次

Linux 文件系统原理

索引节点和目录项

在 Linux 中,一切皆文件,为了方便管理,Linux 文件系统为每个文件都分配两个数据结构,索引节点(index node)和目录项(directory entry)。它们主要用来记录文件的元信息和目录结构。

  • 索引节点,简称为 inode,用来记录文件的元数据,比如 inode 编号、文件大小、访问权限、修改日期、数据的位置等。索引节点和文件一一对应,它跟文件内容一样,都会被持久化存储到磁盘中。所以记住,索引节点同样占用磁盘空间。
  • 目录项,简称为 dentry,用来记录文件的名字、索引节点指针以及与其他目录项的关联关系。多个关联的目录项,就构成了文件系统的目录结构。不过,不同于索引节点,目录项是由内核维护的一个内存数据结构,所以通常也被叫做目录项缓存。
    如下图所示:


    image.png

    需要注意的是:

  • 目录项本身就是一个内存缓存,而索引节点则是存储在磁盘中的数据,所以,索引节点也会缓存到内存中,从而加速文件的访问。
  • 磁盘在执行文件系统格式化时,会被分成三个存储区域,超级块、索引节点区和数据块区。超级块,存储整个文件系统的状态。索引节点区,用来存储索引节点。数据块区,则用来存储文件数据。

虚拟文件系统

目录项、索引节点、逻辑块以及超级块,构成了 Linux 文件系统的四大基本要素。不过,为了支持各种不同的文件系统,Linux 内核在用户进程和文件系统的中间,又引入了一个抽象层,也就是虚拟文件系统 VFS(Virtual File System)。


image.png

文件系统的观测指标

容量

文件系统的磁盘空间使用情况

 df -Th /dev/vda1
Filesystem     Type  Size  Used Avail Use% Mounted on
/dev/vda1      ext4   99G   77G   19G  81% /

另外,inode 也会占用磁盘空间

df -i /dev/vda1
Filesystem      Inodes   IUsed   IFree IUse% Mounted on
/dev/vda1      6553600 1411937 5141663   22% /

缓存

实际上,内核使用 Slab 机制,管理目录项和索引节点的缓存。/proc/meminfo 只给出了 Slab 的整体大小,具体到每一种 Slab 缓存,还要查看 /proc/slabinfo 这个文件

cat /proc/slabinfo | grep -E '^#|dentry|inode'
# name            <active_objs> <num_objs> <objsize> <objperslab> <pagesperslab> : tunables <limit> <batchcount> <sharedfactor> : slabdata <active_slabs> <num_slabs> <sharedavail>
nfs_inode_cache     7781  16590   1120   29    8 : tunables    0    0    0 : slabdata    590    590      0
ovl_inode         139738 160300    720   45    8 : tunables    0    0    0 : slabdata   3564   3564      0
rpc_inode_cache      920    920    704   46    8 : tunables    0    0    0 : slabdata     20     20      0
xfs_inode         329696 511911   1088   30    8 : tunables    0    0    0 : slabdata  17070  17070      0
fuse_inode             0      0    832   39    8 : tunables    0    0    0 : slabdata      0      0      0
mqueue_inode_cache   1054   1054    960   34    8 : tunables    0    0    0 : slabdata     31     31      0
udf_inode_cache        0      0    816   40    8 : tunables    0    0    0 : slabdata      0      0      0
isofs_inode_cache    987    987    688   47    8 : tunables    0    0    0 : slabdata     21     21      0
fat_inode_cache        0      0    776   42    8 : tunables    0    0    0 : slabdata      0      0      0
jbd2_inode         22819  50816     64   64    1 : tunables    0    0    0 : slabdata    794    794      0
ext2_inode_cache       0      0    864   37    8 : tunables    0    0    0 : slabdata      0      0      0
ext4_inode_cache  135042 265177   1152   28    8 : tunables    0    0    0 : slabdata   9609   9609      0
hugetlbfs_inode_cache     48     48    664   24    4 : tunables    0    0    0 : slabdata      2      2      0
inotify_inode_mark  52071  52275     80   51    1 : tunables    0    0    0 : slabdata   1025   1025      0
sock_inode_cache   74776  75040    832   39    8 : tunables    0    0    0 : slabdata   1925   1925      0
proc_inode_cache  217797 222471    712   46    8 : tunables    0    0    0 : slabdata   4839   4839      0
shmem_inode_cache  29175  31218    752   43    8 : tunables    0    0    0 : slabdata    726    726      0
inode_cache       176590 178181    640   25    4 : tunables    0    0    0 : slabdata   7128   7128      0
dentry            4171929 13868208    224   36    2 : tunables    0    0    0 : slabdata 385231 385231      0

其中,dentry 行表示目录项缓存,inode_cache 行,表示 VFS 索引节点缓存,其余的则是各种文件系统的索引节点缓存。
实际性能分析中,我们更常使用 slabtop ,来找到占用内存最多的缓存类型。

# 按下c按照缓存大小排序,按下a按照活跃对象数排序 
$ slabtop 
 Active / Total Objects (% used)    : 14703586 / 26109197 (56.3%)
 Active / Total Slabs (% used)      : 672727 / 672727 (100.0%)
 Active / Total Caches (% used)     : 187 / 273 (68.5%)
 Active / Total Size (% used)       : 3634188.87K / 6402995.95K (56.8%)
 Minimum / Average / Maximum Object : 0.01K / 0.25K / 10.19K

  OBJS ACTIVE  USE OBJ SIZE  SLABS OBJ/SLAB CACHE SIZE NAME
13884516 4184714  30%    0.22K 385684       36   3085472K dentry
512121 330274  64%    1.06K  17077       30    546464K xfs_inode
618562 325811  52%    0.57K  22108       28    353728K radix_tree_node
265177 135042  50%    1.12K   9609   28    307488K ext4_inode_cache
282828 270095  95%    1.00K   8855   32    283360K kmalloc-1k
1898550 1883641  99%    0.13K  63285       30    253140K kernfs_node_cache
223391 218976  98%    0.70K   4859   46    155488K proc_inode_cache
180631 179228  99%    0.62K   7226   25    115616K inode_cache
160300 139738  87%    0.70K   3564   45    114048K ovl_inode
844896 577538  68%    0.10K  21664   39     86656K buffer_head
  7503   7213  96%   10.19K   2505    3     80160K task_struct
 15976  15705  98%    4.00K   1997    8     63904K kmalloc-4k
199375 192826  96%    0.31K   7975   25     63800K filp
262412 260230  99%    0.23K   7718   34     61744K vm_area_struct

Linux磁盘 I/O

I/O性能指标

  • 使用率,是指磁盘处理 IO 的时间百分比,过高的使用率(比如超过 80%),通常以为着磁盘 IO 存在着性能瓶颈。
  • 饱和度,是指磁盘处理 IO 的繁忙程度,过高的磁盘饱和度意味着磁盘存在着严重的性能瓶颈,当饱和度为 100% 时,则意味着磁盘无法接受新的 IO 请求。
  • IOPS,是指每秒的IO 请求数。
  • 吞吐量,是指每秒的 IO 请求大小。
  • 响应时间,是指 IO 请求从发出到接受响应的间隔时间。

I/O指标观测工具

iostat

iostat 是最常用的磁盘 I/O 性能观测工具,它提供了每个磁盘的使用率、IOPS、吞吐量等各种常见的性能指标,当然,这些指标实际上来自 /proc/diskstats。

-d -x表示显示所有磁盘I/O的指标
 $ iostat -d -x 1
Device            r/s     w/s     rkB/s     wkB/s   rrqm/s   wrqm/s  %rrqm  %wrqm r_await w_await aqu-sz rareq-sz wareq-sz  svctm  %util
loop0            0.00    0.00      0.03      0.00     0.00     0.00   0.00   0.00    0.06    0.00   0.00   118.64     0.00   0.47   0.00
vda              2.54   25.39     16.88    291.39     0.62    23.70  19.73  48.29    0.76    1.46   0.02     6.65    11.48   0.91   2.53
vdb              0.11    4.21      7.68    101.42     0.00     0.63   0.44  13.08    2.39    3.91   0.01    69.19    24.09   1.02   0.44

指标说明:

  • %util ,就是我们前面提到的磁盘 I/O 使用率;
  • r/s+ w/s ,就是 IOPS;\
  • rkB/s+wkB/s ,就是吞吐量;
  • r_await+w_await ,就是响应时间。

进程 IO 观测

pidstat工具

pidstat -d 1
Linux 5.4.203-1-tlinux4-0011.1 (VM-167-17-tencentos)    01/27/2024  _x86_64_    (16 CPU)

08:18:40 AM   UID       PID   kB_rd/s   kB_wr/s kB_ccwr/s iodelay  Command
08:18:41 AM     0       460      0.00     78.43      0.00       1  jbd2/vda1-8
08:18:41 AM     0     25009      0.00      3.92      0.00       0  containerd
08:18:41 AM     0     25653      0.00     70.59      0.00       0  etcd
08:18:41 AM   999   1236567      0.00    101.96      0.00       0  mysqld
  • 用户 ID(UID)和进程 ID(PID) 。
  • 每秒读取的数据大小(kB_rd/s) ,单位是 KB。
  • 每秒发出的写请求数据大小(kB_wr/s) ,单位是 KB。
  • 每秒取消的写请求数据大小(kB_ccwr/s) ,单位是 KB。
  • 块 I/O 延迟(iodelay),包括等待同步块 I/O 和换入块 I/O 结束的时间,单位是时钟周期。

iotop工具

$ iotop
Total DISK READ :       0.00 B/s | Total DISK WRITE :       7.85 K/s 
Actual DISK READ:       0.00 B/s | Actual DISK WRITE:       0.00 B/s 
  TID  PRIO  USER     DISK READ  DISK WRITE  SWAPIN     IO>    COMMAND 
15055 be/3 root        0.00 B/s    7.85 K/s  0.00 %  0.00 % systemd-journald 

相关文章

网友评论

      本文标题:Linux I/O 性能分析 - 概念篇

      本文链接:https://www.haomeiwen.com/subject/fxnpodtx.html