一種基於記憶體的檔案系統tmpfs
大家可能有遇到類似的場景,想要對機器進行壓測模擬 OOM 的場景,但是無奈機器的規格實在太高,若用程式碼去實現,大家可以想象一下如何實現?那麼有沒有好有的辦法,不用寫程式碼,用幾個簡單的命令直接就可以向機器申請記憶體呢?或者更極端點,直接把機器的記憶體給榨乾了。。 |
若你經常使用linux,你會發現 df -Th 後,一定會有 tmpfs 型別的檔案系統掛載在 /dev/shm 下面,雖然你大概率不會關注到它。
$df-Th FilesystemTypeSizeUsedAvailUse%Mountedon devtmpfsdevtmpfs910M0910M0%/dev tmpfstmpfs919M0919M0%/dev/shm tmpfstmpfs919M896K918M1%/run tmpfstmpfs919M0919M0%/sys/fs/cgroup /dev/vda1ext440G11G27G28%/ tmpfstmpfs184M0184M0%/run/user/0
而這個 tmpfs 就是明哥今天要介紹的主角。
tmpfs,顧名思義,是臨時檔案系統,是一種基於記憶體的檔案系統。
它和虛擬磁碟 ramdisk比較類似像,但不完全相同,和ramdisk一樣,tmpfs可以使用RAM,但它也可以使用swap分割槽來儲存,而且傳統的ramdisk是個塊裝置,要用mkfs來格式化它,才能真正地使用它;而tmpfs是一個檔案系統,並不是塊裝置,只是安裝它,就可以使用了。tmpfs是最好的基於RAM的檔案系統。
這意味著,你往掛載了 tmpfs 的目錄下寫入的檔案,都會直接寫入記憶體中。
假如你想佔用機器 10G 的記憶體,那我只要先建立一個臨時目錄 /tmp/memory ,並指定 tmpfs 的檔案系統型別及大小 10240M 掛載到該目錄下。
$mount-ttmpfs-osize=10240Mtmpfs/tmp/memory
接著咱使用 dd命令,往該目錄下寫入多少內容,就會佔用多少記憶體,由於我們的目的是佔用記憶體,因此 if 直接使用 /dev/zero
$ddif=/dev/zeroof=/tmp/memory/block
當 dd 寫入完成後,你再使用 free 去檢視可用記憶體,會發現剩餘的記憶體可分配的記憶體少了 10G。
如果你想用完機器的所有記憶體,完全可以在 mount 的時候,指定 size 為機器的記憶體大小,但你要清楚你在做什麼,否則執行完 dd ,你的機器可能就掛了。
利用上面這個方法,其實還可以做更多的事情,比如你在機器你有兩個 NUMA Node ,但你只想佔用 NUMA Node 0 的記憶體,那就可以指定 NUMA Node 0 的記憶體,怎麼辦呢?
首先利用 lscpu 找到 NUMA Node 0 上的所有 cpu 核
$node0_cpus=$(lscpu|grep"NUMAnode0"|awk'{print$NF}')
然後使用 taskset 工具加 -c 引數來指定對應的 cpu 核來執行建立 tmpfs 目錄和 dd 的過程
$cat>/root/mem_alloc.sh<<EOF #!/bin/bash tmpdir=`mktemp` mount-ttmpfs-osize=1024Mtmpfs${tmpdir} ddif=/dev/zeroof=${tmpdir}/block EOF $taskset-c"${node0_cpus}"sh/root/mem_alloc.sh
執行完成後,如果你所佔用的記憶體,沒有超過 NUMA Node 0 的本地記憶體,那麼你使用 numactl 就會發現上面命令都只佔用了 NUMA Node0 的記憶體。