สมมติว่าฉันมีผู้ใช้ 20 คนเข้าสู่ระบบในกล่อง linux ของฉัน ฉันจะรู้ได้อย่างไรว่าแต่ละหน่วยความจำใช้งานเท่าใด
สมมติว่าฉันมีผู้ใช้ 20 คนเข้าสู่ระบบในกล่อง linux ของฉัน ฉันจะรู้ได้อย่างไรว่าแต่ละหน่วยความจำใช้งานเท่าใด
คำตอบ:
คุณสามารถลองใช้smem (ดูELC2009: การแสดงภาพการใช้หน่วยความจำด้วย smemสำหรับข้อมูลเพิ่มเติม) โดยเฉพาะอย่างยิ่งsudo smem -u
ควรให้ข้อมูลที่คุณต้องการ
--no-install-recommends
ได้
ไม่สนใจปัญหาหน่วยความจำที่ใช้ร่วมกันนี่คือสคริปต์ด่วนที่ให้ RSS และ VMEM แก่คุณสำหรับผู้ใช้ที่เข้าสู่ระบบทั้งหมดเรียงตาม vmem และจัดเรียงเป็นคอลัมน์น่ารัก:
(echo "user rss(KiB) vmem(KiB)";
for user in $(users | tr ' ' '\n' | sort -u); do
echo $user $(ps -U $user --no-headers -o rss,vsz \
| awk '{rss+=$1; vmem+=$2} END{print rss" "vmem}')
done | sort -k3
) | column -t
เพื่อให้ได้ผลรวมของ RSS ฉันคิดว่างานต่อไปนี้ นี้จะได้รับผลรวมของ RSS สำหรับผู้ใช้ kbrandt และรูต
ps -U kbrandt,root --no-headers -o rss | (tr '\n' +; echo 0) | bc
นั่นเป็นคำถามที่ยุ่งยาก คุณสามารถสรุปยอดรวมจำนวนการแลกเปลี่ยน RSS + ทั้งหมดในเอาต์พุต "ps" ได้อย่างง่ายดาย แต่หน่วยความจำที่ใช้ร่วมกันเป็นอย่างไร ผู้ใช้ที่ต่างกันสามารถแชร์หน้ารหัสเดียวกันได้อย่างง่ายดายหากพวกเขาใช้กระบวนการเดียวกัน คุณคิดว่าใครเป็นใคร? แล้วบัฟเฟอร์และแคชล่ะ ขึ้นอยู่กับความแม่นยำของผลลัพธ์ที่คุณต้องการ ยิ่งคุณต้องการความแม่นยำมากเท่าใดก็จะยิ่งยากขึ้นเท่านั้น
ฉันไม่แน่ใจว่าจะรายงานการใช้งานหน่วยความจำโดยผู้ใช้อย่างไร แต่ถ้าคุณกังวลเกี่ยวกับการควบคุมการใช้งานของพวกเขาคุณควรค้นหา ulimit มันจะช่วยให้คุณตั้งค่าขีด จำกัด ฮาร์ดและซอฟต์สำหรับผู้ใช้ / กลุ่มพื้นฐานสำหรับหน่วยความจำและทรัพยากรอื่น ๆ ในระบบของคุณ
คุณอาจลองทำสิ่งต่อไปนี้:
ps auxU maxwell | awk '{memory + = $ 4}; END {หน่วยความจำพิมพ์} '
ps aux | grep mysql | awk '{memory +=$4}; END {print memory }'
ซึ่ง mysql สามารถถูกแทนที่ด้วยชื่อของผู้ใช้หรือกระบวนการ
มองหาสิ่งเดียวกันฉันก็รู้เรื่องนี้
ps aux | awk '{arr[$1]+=$4}; END {for (i in arr) {print i,arr[i]}}' | sort -k2
เพื่อพิมพ์กระบวนการที่สั่งโดย mem จัดกลุ่มตามผู้ใช้ (คอลัมน์ 1, $ 1) คุณสามารถจัดกลุ่มตามสิ่งอื่น ๆ และรวมสิ่งอื่น ๆ เปลี่ยน $ 1 และ $ 4
ฉันมีความสุขที่จะหาทางแก้ปัญหาเพียงแค่ต้องการแบ่งปัน
ps --no-headers -eo user,rss | awk '{arr[$1]+=$2}; END {for (i in arr) {print i,arr[i]}}' | sort -nk2
ฉันทำไม่กี่ปรับเปลี่ยนและกำลังใช้นี้: คำสั่ง sort ต้องการ-n
แฟล็กเพื่อแยกหน่วยความจำเป็นตัวเลข ด้วยวิธีนี้คุณสามารถแทนที่คำว่า "ผู้ใช้" ด้วย "คำสั่ง" เพื่อจัดกลุ่มตามชื่อแอปพลิเคชันแทน
สคริปต์ทุบตีนี้น่าเกลียดเหมือนนรก แต่ขอบคุณสำหรับการออกกำลังกายทุบตีของฉันคือ (เป็น) ได้รับสนิม!
#!/bin/sh
OLDIFS=$IFS
IFS=$'\n'
tempsum=0
totalmem=0
for m in `ps -eo user,rss --sort user | sed -e 's/ */ /g' | awk -F'[ ]' {'print $0'}`; do
nu=`echo $m|cut -d" " -f1`
nm=`echo $m|cut -d" " -f2`
# echo "$nu $nm $nu"
if [ "$nu" != "$ou" ] && [ $(echo "$nm"|grep -E "^[0-9]+$") ]
then
if [ "$tempsum" -ne 0 ]; then echo "Printing total mem for $ou: $tempsum"; fi
ou=$nu
tempsum=$nm
let "totalmem += $nm"
else
let "tempsum += $nm"
let "totalmem += $nm"
fi
done
echo "Total Memory in Use: $totalmem/$(free | grep Mem: | awk '{print $2}')"
IFS=$OLDIFS
ผลลัพธ์:
[20:34][root@server2:~]$ ./memorybyuser.sh
Printing total mem for admin: 1387288
Printing total mem for apache: 227792
Printing total mem for avahi: 1788
Printing total mem for dbus: 980
Printing total mem for 68: 3892
Printing total mem for root: 55880
Printing total mem for rpc: 292
Printing total mem for rpcuser: 740
Printing total mem for smmsp: 720
Printing total mem for xfs: 680
Total Memory in Use: 1682360/4152144
โปรดแสดงความคิดเห็น / ถูกต้องและฉันจะอัปเดตคำตอบ นอกจากนี้ฉันจะใช้หน่วยความจำเอาท์พุท rss จาก PS เนื่องจากคนอื่น ๆ ได้กล่าวถึงว่ามีข้อดี / ข้อเสียในการใช้ค่านี้
smem ไม่มีอยู่ในระบบของฉันและสคริปต์ของเดฟไม่ทำงานด้วยเหตุผลบางอย่างดังนั้นฉันจึงเขียน Perl oneliner Perl ที่น่าเกลียดนี้เพื่อประมวลผลเอาต์พุต ps:
ps -eo user,rss | perl -e 'foreach (<>) { m/(\w+)\s+(\d+)/; $mem{$1} += $2; }; foreach $u (keys %mem) { if ($mem{$u}) { print "$u - $mem{$u}\n" }}' | sort
โปรดทราบว่าผู้ใช้บางคนมีการระบุโดยใช้ UID ของพวกเขามากกว่าชื่อผู้ใช้ของพวกเขา คุณสามารถจัดการกับสิ่งนี้ได้โดยการแยกชื่อผู้ใช้จาก / etc / passwd โดยใช้ uglier:
ps -eo user,rss | perl -e 'open(F, "/etc/passwd"); foreach $l (<F>) { if ($l=~/(.*?):.*?:(\d+)/) { $users{$2}=$1; }}; foreach (<>) { m/(\w+)\s+(\d+)/; $mem{$1} += $2; }; foreach $u (keys (%mem)) { $UN = $u; if ($UN=~/^\d+$/) { $UN = $users{$UN};}; if ($mem{$u}) { print "$UN - $mem{$u}\n" }}' | sort
การใช้ Bash Script
#!/bin/bash
total_mem=0
printf "%-10s%-10s\n" User MemUsage'(%)'
while read u m
do
[[ $old_user != $u ]] && { printf "%-10s%-0.1f\n" $old_user $total_mem;
total_mem=0; }
total_mem="$(echo $m + $total_mem | bc)"
old_user=$u
done < <(ps --no-headers -eo user,%mem| sort -k1)
#EOF
เอาท์พุท
User MemUsage(%)
apache 4.8
dbus 0.0
mysql 3.8
nagios 3.1
pmap `pgrep -u 503` | grep total | awk '{print $2}' | awk '{s+=$1}END{print s}'
503 - UID
คุณสามารถรับ UID จาก/etc/passwd
การทำเช่นนี้สำหรับผู้ใช้ทั้งหมด
ที่สถานะของเคอร์เนล Linux นี้ฉันสามารถคิดถึงวิธีที่เหมาะสมเพียงวิธีเดียวในการทำงานนี้ให้สำเร็จ - โดยใช้กลุ่มหน่วยความจำ คุณจะต้องให้ผู้ใช้เข้าสู่ระบบใน cgroup ของตัวเองและสิ่งนี้อาจต้องมีการพัฒนาโมดูล pam ของตัวเองหรือ (แทนที่จะ) แก้ไขโมดูลที่มีอยู่สำหรับที่
เอกสารที่มีประโยชน์ที่ควรอ่านเกี่ยวกับเรื่องนี้คือ: คู่มือการจัดการทรัพยากรโดยRedHat®