태그 보관물: linux-kernel

linux-kernel

xfs, 20 개의 디스크 및 Ceph가있는“대형”서버에서 페이지 조각화의 원인 0.01 2.06

리눅스 IO 시스템에 약간의 경험이있는 사람의 통찰력이 도움이 될 것입니다. 여기 내 이야기가 있습니다 :

최근 Ceph를 통해 파일을 제공하기 위해 6 개의 Dell PowerEdge rx720xd 클러스터를 구축했습니다. 이 기계에는 2 개의 누마 영역과 70 개의 홀수 기가 바이트 메모리를 가진 2 개의 소켓에 24 개의 코어가 있습니다. 디스크는 각각 하나의 디스크를 습격하는 형식으로되어 있습니다 (그렇지 않으면 직접 노출하는 방법을 볼 수 없음). 네트워킹은 mellanox infiniband IP over IB에서 제공합니다 (IP 패킷은 하드웨어가 아닌 커널 랜드에서 IB로 바)).

각 SAS 드라이브는 다음과 같이 마운트되어 있습니다.

# cat /proc/mounts | grep osd
/dev/sdm1 /var/lib/ceph/osd/ceph-90 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdj1 /var/lib/ceph/osd/ceph-87 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdu1 /var/lib/ceph/osd/ceph-99 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdd1 /var/lib/ceph/osd/ceph-82 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdk1 /var/lib/ceph/osd/ceph-88 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdl1 /var/lib/ceph/osd/ceph-89 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdh1 /var/lib/ceph/osd/ceph-86 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdo1 /var/lib/ceph/osd/ceph-97 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdc1 /var/lib/ceph/osd/ceph-81 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdb1 /var/lib/ceph/osd/ceph-80 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sds1 /var/lib/ceph/osd/ceph-98 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdn1 /var/lib/ceph/osd/ceph-91 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sde1 /var/lib/ceph/osd/ceph-83 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdq1 /var/lib/ceph/osd/ceph-93 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdg1 /var/lib/ceph/osd/ceph-85 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdt1 /var/lib/ceph/osd/ceph-95 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdf1 /var/lib/ceph/osd/ceph-84 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdr1 /var/lib/ceph/osd/ceph-94 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdi1 /var/lib/ceph/osd/ceph-96 xfs rw,noatime,attr2,inode64,noquota 0 0
/dev/sdp1 /var/lib/ceph/osd/ceph-92 xfs rw,noatime,attr2,inode64,noquota 0 0

이 머신을 통과하는 IO는 수백 MB / s로 버스트되지만, 대부분의 경우 ‘포크’가 많기 때문에 대부분 유휴 상태입니다.

# iostat -x -m
Linux 3.10.0-123.el7.x86_64 (xxx)   07/11/14    _x86_64_    (24 CPU)

avg-cpu:  %user   %nice %system %iowait  %steal   %idle
       1.82    0.00    1.05    0.11    0.00   97.02
Device:         rrqm/s   wrqm/s     r/s     w/s    rMB/s    wMB/s avgrq-sz avgqu-sz   await r_await w_await  svctm  %util
sda               0.00     0.11    0.25    0.23     0.00     0.00    27.00     0.00    2.07    3.84    0.12   0.61   0.03
sdb               0.02     0.57    3.49    2.28     0.08     0.14    77.18     0.01    2.27    2.99    1.18   1.75   1.01
sdd               0.03     0.65    3.93    3.39     0.10     0.16    70.39     0.01    1.97    2.99    0.79   1.57   1.15
sdc               0.03     0.60    3.76    2.86     0.09     0.13    65.57     0.01    2.10    3.02    0.88   1.68   1.11
sdf               0.03     0.63    4.19    2.96     0.10     0.15    73.51     0.02    2.16    3.03    0.94   1.73   1.24
sdg               0.03     0.62    3.93    3.01     0.09     0.15    70.44     0.01    2.06    3.01    0.81   1.66   1.15
sde               0.03     0.56    4.35    2.61     0.10     0.14    69.53     0.02    2.26    3.00    1.02   1.82   1.26
sdj               0.02     0.73    3.67    4.74     0.10     0.37   116.06     0.02    1.84    3.01    0.93   1.31   1.10
sdh               0.03     0.62    4.31    3.04     0.10     0.15    67.83     0.02    2.15    3.04    0.89   1.75   1.29
sdi               0.02     0.59    3.82    2.47     0.09     0.13    74.35     0.01    2.20    2.96    1.03   1.76   1.10
sdl               0.03     0.59    4.75    2.46     0.11     0.14    70.19     0.02    2.33    3.02    1.00   1.93   1.39
sdk               0.02     0.57    3.66    2.41     0.09     0.13    73.57     0.01    2.20    3.00    0.97   1.76   1.07
sdm               0.03     0.66    4.03    3.17     0.09     0.14    66.13     0.01    2.02    3.00    0.78   1.64   1.18
sdn               0.03     0.62    4.70    3.00     0.11     0.16    71.63     0.02    2.25    3.01    1.05   1.79   1.38
sdo               0.02     0.62    3.75    2.48     0.10     0.13    76.01     0.01    2.16    2.94    0.99   1.70   1.06
sdp               0.03     0.62    5.03    2.50     0.11     0.15    68.65     0.02    2.39    3.08    0.99   1.99   1.50
sdq               0.03     0.53    4.46    2.08     0.09     0.12    67.74     0.02    2.42    3.04    1.09   2.01   1.32
sdr               0.03     0.57    4.21    2.31     0.09     0.14    72.05     0.02    2.35    3.00    1.16   1.89   1.23
sdt               0.03     0.66    4.78    5.13     0.10     0.20    61.78     0.02    1.90    3.10    0.79   1.49   1.47
sdu               0.03     0.55    3.93    2.42     0.09     0.13    70.77     0.01    2.17    2.97    0.85   1.79   1.14
sds               0.03     0.60    4.11    2.70     0.10     0.15    74.77     0.02    2.25    3.01    1.10   1.76   1.20
sdw               1.53     0.00    0.23   38.90     0.00     1.66    87.01     0.01    0.22    0.11    0.22   0.05   0.20
sdv               0.88     0.00    0.16   28.75     0.00     1.19    84.55     0.01    0.24    0.10    0.24   0.05   0.14
dm-0              0.00     0.00    0.00    0.00     0.00     0.00     8.00     0.00    1.84    1.84    0.00   1.15   0.00
dm-1              0.00     0.00    0.23    0.29     0.00     0.00    23.78     0.00    1.87    4.06    0.12   0.55   0.03
dm-2              0.00     0.00    0.01    0.00     0.00     0.00     8.00     0.00    0.47    0.47    0.00   0.45   0.00

문제 :

약 48 시간 후에 연속 페이지가 너무 세분화되어 마그네 우트 4 (16 페이지, 65536 바이트) 할당이 실패하기 시작하고 SLAB가 커질 때 kalloc 실패로 인해 패킷 삭제가 시작됩니다.

이것은 비교적 “건강한”서버의 모습입니다 :

# cat /sys/kernel/debug/extfrag/unusable_index
Node 0, zone      DMA 0.000 0.000 0.000 0.001 0.003 0.007 0.015 0.031 0.031 0.096 0.225
Node 0, zone    DMA32 0.000 0.009 0.015 0.296 0.733 0.996 0.997 0.998 0.998 1.000 1.000
Node 0, zone   Normal 0.000 0.000 0.019 0.212 0.454 0.667 0.804 0.903 0.986 1.000 1.000
Node 1, zone   Normal 0.000 0.027 0.040 0.044 0.071 0.270 0.506 0.772 1.000 1.000 1.000

조각화가 상당히 악화되면 시스템이 커널 공간에서 회전하기 시작하는 것처럼 보이고 모든 것이 무너집니다. 이 장애가 발생하는 동안 한 가지 이상은 xfsaild가 많은 CPU를 사용하는 것처럼 보이고 중단 할 수없는 절전 상태에 빠진다는 것입니다. 그러나 전체 시스템 장애가 발생했을 때 이상하게 결론을 내리고 싶지 않습니다.

지금까지 해결 방법.

조각화에서도 이러한 할당이 실패하지 않도록하기 위해 다음과 같이 설정했습니다.

vm.min_free_kbytes = 16777216

SLAB 캐시에서 수백만 개의 blkdev_requests를 본 후 다음을 통해 더티 페이지를 줄이려고했습니다.

vm.dirty_ratio = 1
vm.dirty_background_ratio = 1
vm.min_slab_ratio = 1
vm.zone_reclaim_mode = 3

한 번에 너무 많은 변수를 변경했을 수도 있지만 inode와 덴트 리가 조각화를 일으키는 경우를 대비하여 최소로 유지하기로 결정했습니다.

vm.vfs_cache_pressure = 10000

그리고 이것은 도움이 된 것 같습니다. 그래도 조각화는 여전히 높으며 inode 및 dentry 문제가 줄어들어 이상한 것으로 나타났습니다.

내 질문:

캐시를 삭제하면 사라지는 blkdev_requests가 너무 많은 이유는 무엇입니까?

여기 내가 의미하는 바가있다 :

# slabtop -o -s c | head -20
 Active / Total Objects (% used)    : 19362505 / 19431176 (99.6%)
 Active / Total Slabs (% used)      : 452161 / 452161 (100.0%)
 Active / Total Caches (% used)     : 72 / 100 (72.0%)
 Active / Total Size (% used)       : 5897855.81K / 5925572.61K (99.5%)
 Minimum / Average / Maximum Object : 0.01K / 0.30K / 15.69K

  OBJS ACTIVE  USE OBJ SIZE  SLABS OBJ/SLAB CACHE SIZE NAME
2565024 2565017  99%    1.00K  80157       32   2565024K xfs_inode
3295194 3295194 100%    0.38K  78457       42   1255312K blkdev_requests
3428838 3399527  99%    0.19K  81639       42    653112K dentry
5681088 5680492  99%    0.06K  88767       64    355068K kmalloc-64
2901366 2897861  99%    0.10K  74394       39    297576K buffer_head
 34148  34111  99%    8.00K   8537        4    273184K kmalloc-8192
334768 334711  99%    0.57K  11956       28    191296K radix_tree_node
614959 614959 100%    0.15K  11603       53     92824K xfs_ili
 21263  19538  91%    2.84K   1933       11     61856K task_struct
 18720  18636  99%    2.00K   1170       16     37440K kmalloc-2048
 32032  25326  79%    1.00K   1001       32     32032K kmalloc-1024
 10234   9202  89%    1.88K    602       17     19264K TCP
 22152  19765  89%    0.81K    568       39     18176K task_xstate

# echo 2 > /proc/sys/vm/drop_caches                                                                                                                                                   :(
# slabtop -o -s c | head -20
 Active / Total Objects (% used)    : 965742 / 2593182 (37.2%)
 Active / Total Slabs (% used)      : 69451 / 69451 (100.0%)
 Active / Total Caches (% used)     : 72 / 100 (72.0%)
 Active / Total Size (% used)       : 551271.96K / 855029.41K (64.5%)
 Minimum / Average / Maximum Object : 0.01K / 0.33K / 15.69K

  OBJS ACTIVE  USE OBJ SIZE  SLABS OBJ/SLAB CACHE SIZE NAME
 34140  34115  99%    8.00K   8535        4    273120K kmalloc-8192
143444  20166  14%    0.57K   5123       28     81968K radix_tree_node
768729 224574  29%    0.10K  19711       39     78844K buffer_head
 73280   8287  11%    1.00K   2290       32     73280K xfs_inode
 21263  19529  91%    2.84K   1933       11     61856K task_struct
686848  97798  14%    0.06K  10732       64     42928K kmalloc-64
223902  41010  18%    0.19K   5331       42     42648K dentry
 32032  23282  72%    1.00K   1001       32     32032K kmalloc-1024
 10234   9211  90%    1.88K    602       17     19264K TCP
 22152  19924  89%    0.81K    568       39     18176K task_xstate
 69216  59714  86%    0.25K   2163       32     17304K kmalloc-256
 98421  23541  23%    0.15K   1857       53     14856K xfs_ili
  5600   2915  52%    2.00K    350       16     11200K kmalloc-2048

이것은 blkdev_request 축적이 나에게 말한다 하지 더티 페이지와 관련된 사실, 활성 객체가 정말 활성화되지 또한 것을? 실제로 사용되지 않는 경우 어떻게 이러한 개체를 해제 할 수 있습니까? 무슨 일이야?

일부 배경의 경우 drop_caches가 수행하는 작업은 다음과 같습니다.

http://lxr.free-electrons.com/source/fs/drop_caches.c

최신 정보:

그것들이 blkdev_requests가 아닐 수도 있지만 그 ‘제목’아래에 xfs_buf 항목이 표시 될 수 있습니까? 이것이 어떻게 작동하는지 잘 모르겠습니다.

/sys/kernel/slab # ls -l blkdev_requests(
lrwxrwxrwx 1 root root 0 Nov  7 23:18 blkdev_requests -> :t-0000384/

/sys/kernel/slab # ls -l | grep 384
lrwxrwxrwx 1 root root 0 Nov  7 23:18 blkdev_requests -> :t-0000384/
lrwxrwxrwx 1 root root 0 Nov  7 23:19 ip6_dst_cache -> :t-0000384/
drwxr-xr-x 2 root root 0 Nov  7 23:18 :t-0000384/
lrwxrwxrwx 1 root root 0 Nov  7 23:19 xfs_buf -> :t-0000384/

나는 왜 이들이 ‘drop_slabs’에 의해 지워 졌는지, 또는이 조각화의 원인을 해결하는 방법을 모른다.

보너스 질문 :이 조각화의 근원에 도달하는 더 좋은 방법은 무엇입니까?

이 글을 읽어 보시면 관심을 가져 주셔서 감사합니다!

추가 요청 정보 :

메모리 및 xfs 정보 :
https://gist.github.com/christian-marie/f417cc3134544544a8d1

페이지 할당 실패 :
https://gist.github.com/christian-marie/7bc845d2da7847534104

후속 조치 : 성능 정보 및 압축 관련 사항

http://ponies.io/raw/compaction.png

압축 코드는 조금 비효율적 인 것 같습니다. 실패한 압축을 복제하기 위해 코드를 함께 모았습니다. https://gist.github.com/christian-marie/cde7e80c5edb889da541

이것은 문제를 재현하는 것 같습니다.

또한 이벤트 추적을 통해 계속해서 많은 실패한 회수가 있음을 알 수 있습니다.


<...>-322 [023] .... 19509.445609: mm_vmscan_direct_reclaim_end: nr_reclaimed=1

Vmstat 출력도 관련이 있습니다. 시스템이이 고부하 상태에있는 동안 압축은 지붕을 통과합니다 (대부분 실패).


pgmigrate_success 38760827
pgmigrate_fail 350700119
compact_migrate_scanned 301784730
compact_free_scanned 204838172846
compact_isolated 18711615
compact_stall 270115
compact_fail 244488
compact_success 25212

실제로 재생 / 압축에 문제가 있습니다.

현재 저는 ipoib 설정에 SG 지원을 추가하여 높은 할당량을 줄이는 것을 찾고 있습니다. 실제 문제는 vmscan과 관련된 것으로 보입니다.

이것은 흥미롭고이 질문을 참조합니다 : http://marc.info/?l=linux-mm&m=141607142529562&w=2



답변

의견이 많기 때문에 관찰 한 내용에 답을하겠다고 생각했습니다.

https://gist.github.com/christian-marie/7bc845d2da7847534104 에서 출력을 기반으로합니다.

우리는 다음을 결정할 수 있습니다.

  1. 시도 된 메모리 할당에 대한 GFP_MASK는 다음을 수행 할 수 있습니다.
    • (I 비상 풀에 액세스 할 수 생각 이 수단은 영역에 대한 높은 워터 마크 아래의 데이터에 액세스)
    • 비상 준비금을 사용 하지 마십시오 (최소 워터 마크 아래의 memroy에 대한 액세스를 허용하지 않는다고 생각 합니다)
    • 일반 영역 중 하나에서 할당하십시오.
    • 공간을 확보하기 위해 교환 할 수 있습니다.
    • 공간을 확보하기 위해 캐시를 삭제할 수 있습니다.

영역 조각화는 다음 위치에 있습니다.

[3443189.780792] Node 0 Normal: 3300*4kB (UEM) 8396*8kB (UEM) 4218*16kB (UEM) 76*32kB (UEM) 12*64kB (M) 0*128kB 0*256kB 0*512kB 0*1024kB 0*2048kB 0*4096kB = 151056kB
[3443189.780801] Node 1 Normal: 26667*4kB (UEM) 6084*8kB (UEM) 2040*16kB (UEM) 96*32kB (UEM) 22*64kB (UEM) 4*128kB (U) 0*256kB 0*512kB 0*1024kB 0*2048kB 0*4096kB = 192972kB

당시 메모리 사용률은 다음과 같습니다.

[3443189.780759] Node 0 Normal free:149520kB min:40952kB low:51188kB high:61428kB active_anon:9694208kB inactive_anon:1054236kB active_file:7065912kB inactive_file:7172412kB unevictable:0kB isolated(anon):5452kB isolated(file):3616kB present:30408704kB managed:29881160kB mlocked:0kB dirty:0kB writeback:0kB mapped:25440kB shmem:743788kB slab_reclaimable:1362240kB slab_unreclaimable:783096kB kernel_stack:29488kB pagetables:43748kB unstable:0kB bounce:0kB free_cma:0kB writeback_tmp:0kB pages_scanned:0 all_unreclaimable? no
[3443189.780766] Node 1 Normal free:191444kB min:45264kB low:56580kB high:67896kB active_anon:11371988kB inactive_anon:1172444kB active_file:8084140kB inactive_file:8556980kB unevictable:0kB isolated(anon):4388kB isolated(file):4676kB present:33554432kB managed:33026648kB mlocked:0kB dirty:0kB writeback:0kB mapped:45400kB shmem:2263296kB slab_reclaimable:1606604kB slab_unreclaimable:438220kB kernel_stack:55936kB pagetables:44944kB unstable:0kB bounce:0kB free_cma:0kB writeback_tmp:0kB pages_scanned:0 all_unreclaimable? no

페이지 할당 실패 출력에서 ​​각 영역의 조각화가 잘못되었습니다. 무료 주문 0 페이지가 많으며 주문 페이지가 훨씬 적거나 없습니다. ‘좋은’결과는 각 주문에 따라 무료 페이지가 풍부하며, 주문이 많을수록 점차 크기가 작아집니다. 상위 페이지 5 이상이 0이면 상위 할당에 대한 단편화 및 기아 상태를 나타냅니다.

나는 현재이 기간 동안 조각화가 슬래브 캐시와 관련이 있음을 암시하는 확실한 증거를 보지 못했습니다. 결과 메모리 통계에서 다음을 볼 수 있습니다.

Node 0 = active_anon:9694208kB inactive_anon:1054236kB
Node 1 = active anon:11371988kB inactive_anon:1172444kB

사용자 공간에서 할당 된 거대한 페이지가 없으므로 사용자 공간은 항상 차수 0 메모리를 청구합니다. 따라서 두 영역 모두에 22GiB 이상의 조각 모음 가능한 메모리가 있습니다.

내가 설명 할 수없는 행동

높은 순서의 할당이 실패하면, 높은 순서의 메모리 할당 영역이 발생하고 성공하기 위해 항상 메모리 압축이 시도 된다는 것을 이해합니다 . 왜 이런 일이 발생하지 않습니까? 만약 그렇다면, 22GiB의 메모리가 재주문 될 때 조각 모음 할 메모리를 찾을 수없는 이유는 무엇입니까?

내가 설명 할 수있는 행동

이것은 제대로 이해하기 위해 더 많은 연구가 필요하지만, 사용 가능한 여유 메모리가 많기 때문에 일부 페이지 캐시를 자동으로 스왑 / 드롭하는 할당 기능이 여기에 적용되지 않을 가능성이 높으므로 재생이 발생하지 않습니다. 높은 주문에서는 충분하지 않습니다.

사용 가능한 메모리의 프로그래머를 많이하는 동안 4 개 요청이 각 영역에 남아있는 몇 순서는 인 ‘분’워터 마크 아래 ‘무료 메모리’에 문제의 결과 “실제 사용 가능한 메모리에서 각 주문 및 공제에 대한 모든 사용 가능한 메모리를 총” 실제 할당 실패로 이어지는 것.


답변