क्या ps लिनक्स पर केवल गैर कर्नेल प्रक्रिया प्रदर्शित कर सकता है?


41

मैं psकेवल उपयोगकर्ता प्रक्रियाओं को प्रदर्शित करने के लिए कैसे कह सकता हूं और कर्नेल थ्रेड्स नहीं?

देखें इस सवाल को देखने के लिए मैं क्या मतलब है ...

जवाबों:


37

यह (लिनक्स के तहत) करना चाहिए:

ps --ppid 2 -p 2 --deselect

kthreadd(PID 2) में PPID 0 ( लिनक्स 2.6+ पर ) है, लेकिन psPPID 0 के लिए फ़िल्टर करने की अनुमति नहीं देता है; इस प्रकार यह काम के आसपास।


अच्छा है, लेकिन यह कैसे गारंटी है कि kthreaddहमेशा पीआईडी ​​2 है?
l0b0

@ l0b0 मुझे कोई पता नहीं है :-) आप इसे दो चरणों में कर सकते हैं: पीआईडी ​​का निर्धारण करें kthreadd, फिर तदनुसार psकॉल का निर्माण करें। यह कैसे गारंटी है कि यह बात "हमेशा" को "कथ्रेड" कहा जाएगा? एक सुरक्षित समाधान अधिक जटिल होगा, psसामान्य रूप से चलेगा और आउटपुट को पार्स करेगा, शायद कुछ परीक्षण करें।
Hauke ​​Laging

2
लिनक्स 2.4 में x86 आर्च पर कम से कम, उन प्रक्रियाओं में ppid 1 था इसलिए इसे इस तरह से प्रतिष्ठित नहीं किया जा सकता था।
स्टीफन चेज़लस

1
"ps -ef" की तरह होना "ps --ppid 2 -p 2 -deselect -f" और इसे "ps aux" की तरह करना "ps --ppid 2 -p 2 -deselect u"
पीटर

1
@ मैं जाँच करता हूँ और ऐसा लगता है कि यह xध्वज है जो इस के साथ काम नहीं करता है। ps au --ppid 2 -p 2 --deselectठीक काम करता है।
संकल्प

9

कर्नेल प्रक्रियाओं को पहचानने का एक तरीका यह है कि वे किसी भी उपयोगकर्ता मेमोरी का उपयोग नहीं करते हैं, इसलिए vsz फ़ील्ड 0. है। यह भी लाश ( इस अवलोकन के लिए स्टीफन चेज़ेलस के लिए धन्यवाद) को पकड़ता है , जिसे उनकी स्थिति के आधार पर समाप्त किया जा सकता है।

ps axl | awk '$7 != 0 && $10 !~ "Z"'

बस PID को सूचीबद्ध करने के लिए:

ps -e -o pid= -o state= -o vsize= | awk '$2 != "Z" && $3 != 0 {print $1}'

मेरे समाधान की तरह, इसमें ज़ोंबी प्रक्रियाएं भी शामिल होंगी।
स्टीफन चेज़लस

1
@StephaneChazelas अच्छा बिंदु, मैंने फ़िल्टर में एक शर्त जोड़ी है।
गाइल्स का SO- बुराई पर रोक '

9

व्यवहार में मैंने निम्नलिखित मुहावरे को पर्याप्त पाया:

ps auxf | grep -v ]$

यह कोष्ठक के साथ समाप्त होने वाली रेखाओं को फ़िल्टर करता है, जिसके परिणामस्वरूप अवांछित प्रविष्टियों को छोड़ दिया जा सकता है , लेकिन इसकी संभावना बहुत कम है। बदले में यह याद रखना काफी आसान है और टाइप करने के लिए अपेक्षाकृत जल्दी है।

अवही-डेमॉन जैसी कुछ प्रक्रियाएं ब्रैकेट्स में उनकी प्रक्रिया का नाम जानकारी में जोड़ देती हैं (एवाही-डेमन के मामले में होस्टनाम) और इस आदेश द्वारा फ़िल्टर किया जाएगा।


8

उन प्रक्रियाओं की ख़ासियत यह है कि वे एक निष्पादन योग्य फ़ाइल द्वारा समर्थित नहीं हैं, इसलिए आप कर सकते हैं ( zsh में ):

ps /proc/[0-9]*/exe(^-@:h:t)

या किसी भी POSIX शेल के साथ:

ps -p "$(find -L /proc/[0-9]*/exe ! -type l | cut -d / -f3 | paste -sd , -)"

यह उन प्रक्रियाओं के लिए जाँच /proc/<pid>/exeहै, जो किसी फ़ाइल का लिंक है।

लेकिन इसका मतलब है कि आपको सिम्बल की स्थिति की जांच करने में सक्षम होने के लिए /proc/<pid>/exeसुपरयुसर होने की आवश्यकता है।

संपादित करें : जैसा कि यह होता है कि ज़ोंबी प्रक्रियाएं (कम से कम) एक ही स्थिति को संतुष्ट करती हैं, इसलिए यदि आप उन्हें बाहर नहीं रखना चाहते हैं, तो आपको उसे वापस जोड़ना होगा। पसंद:

ps -p "$(
  { find -L /proc/[0-9]*/exe ! -type l | cut -d / -f3
    ps -Ao pid=,state= | sed -n 's/ Z//p'
  } | paste -sd , -)"

ध्यान दें कि ps -fवर्ग कोष्ठक में उन प्रक्रिया नामों को दिखाता है क्योंकि वे कर्नेल प्रक्रिया नहीं हैं, लेकिन क्योंकि उनके पास एक खाली है argv[](इसलिए ps प्रक्रिया के बजाय प्रक्रिया नाम दिखाता है argv[0])। आपके पास एक खाली जगह के साथ एक उपयोगकर्ता स्थान प्रक्रिया argv[]हो सकती है और आपके पास एक प्रक्रिया का नाम हो सकता है जो argv[0]कि फॉर्म के साथ है [some-string]इसलिए psउन वर्ग कोष्ठक के आधार पर आउटपुट को फ़िल्टर करना एक मूर्ख विकल्प नहीं है।


यह गैर मानक शेल सिंटैक्स है, मुझे लगता है।
टॉटर

1
@ टोटर, जैसा कि मैंने कहा, पहला zshवाक्य वाक्य रचना है। दूसरा मानक POSIX है sh(और psऔर findऔर cutऔर paste) वाक्य रचना। बेशक /procPOSIX द्वारा निर्दिष्ट नहीं है।
स्टीफन चेज़लस

इस उत्तर को स्वीकार करना क्योंकि यह सार्वभौमिक है (संपादन के लिए धन्यवाद)। हालाँकि, जब तक आप 2.4 कर्नेल के साथ सौदा नहीं करते तब तक Hauke ​​Laging का उत्तर भी बहुत अच्छा और सीधा है।
टॉटर

@ टॉटर, ड्यूक के जवाब में सुपरसुसर निजीकरण की आवश्यकता नहीं होने का भी फायदा है। मेरा जवाब 2.4 और 2.6 / 3 कर्नेल के साथ काम करता है, लेकिन मुझे लगता है कि यह गारंटी नहीं है कि यह 4.x में वैसे भी काम करेगा।
स्टीफन चेज़लस

हम्म, तुम सही हो, मैं रूट विशेषाधिकारों के बारे में नहीं सोचा था। यह गलतियाँ हो सकती हैं क्योंकि आपको अभी भी एक उत्तर मिलता है जब आप जड़ नहीं हैं, लेकिन यह अलग है (इसलिए जब आप उन्हें गिनते हैं, तो आपको सावधान रहना चाहिए, कहते हैं wc -l)। खैर, मैं Hauke ​​Laging का जवाब तब स्वीकार करूंगा , और आपको उत्थान दूंगा। ;)
टोटर

1

आप केवल psआउटपुट को पार्स कर सकते हैं और प्रक्रिया के नाम खोज सकते हैं जो कोष्ठक में नहीं हैं:

ps aux | awk '$NF!~/^\[.+\]$/'

आपके द्वारा रुचि रखने वाले उपयोगकर्ताओं की सूची प्राप्त करने के लिए थोड़ा कम अविश्वसनीय तरीका: awk -F: '$7 ~ home { print $1 }' /etc/passwd- लेकिन फिर भी आपको ऐसी प्रक्रियाएँ मिलेंगी जिनमें ऐसे किसी भी उपयोगकर्ता नाम का उल्लेख है , और आप अस्थायी फ़ाइल को छोड़ देंगे। मैं अपना पद छोड़ दूंगा, लेकिन केवल इसलिए कि आपका तीसरा समाधान उचित है।
कीथ थॉम्पसन

बाह, आप सभी तरह से सही हैं, @KeTTompson, दूसरों को हटा दिया, वे इसके लायक नहीं हैं। क्या आप मुझे (अब) अप्रचलित टिप्पणियों को साफ करने में मदद कर सकते हैं?
terdon

2
ध्यान दें कि आउटपुट $NFमें कमांड लाइन का अंतिम शब्द है ps aux। गैर-कर्नेल प्रक्रियाएं हो सकती हैं [...]। जैसा कि मैंने अपने उत्तर में कहा है कि [xxx]नोटेशन इसलिए नहीं है क्योंकि वे कर्नेल प्रक्रियाएं हैं, बल्कि इसलिए कि उनके पास कोई कमांड लाइन (कोई तर्क नहीं) है जो गैर-कर्नेल प्रक्रियाओं की भी अनुमति है।
स्टीफन चेज़लस

1

बिजीबॉक्स में यह कोशिश करने वाले किसी व्यक्ति के लिए जहां psभारी सरलीकृत होता है और आउटपुट अलग होता है, गिल्स के शानदार उत्तर का यह संस्करण अच्छी तरह से काम करता है:

ps -o pid,user,comm,vsz,stat | awk '$4 != 0 && $5 !~ "Z"'

गिल्स के उत्तर के अनुसार, यहां की कार्यप्रणाली ऐसी प्रक्रियाओं को खोजने के लिए है जो किसी भी उपयोगकर्ता की मेमोरी (`vsz col == 0) का उपयोग नहीं करते हैं, और ज़ोंबी प्रक्रियाओं को फ़िल्टर करते हैं (स्थिति कॉल 'Z' नहीं है)।

आउटपुट कॉलम को आसानी से समायोजित किया जा सकता है, जब तक कि 1-आधारित awk फ़ील्ड नंबर तदनुसार समायोजित नहीं किए जाते हैं। उन विकल्पों को देखें जो आपके पीएस ने फर्जी मूल्य में उपलब्ध हैं और यह आपको बताएगा। उदाहरण के लिए:

$ ps -o foo
ps: bad -o argument 'foo', supported arguments: user,group,comm,args,pid,ppid,pgid,tty,vsz,stat,rss

0

यदि आपको केवल काउंट्स की आवश्यकता है ... मुझे कर्नेल बनाम उपयोगकर्ता प्रक्रियाओं को फ़िल्टर करने की समान आवश्यकता थी, लेकिन मुझे केवल प्रत्येक के संबंधित काउंट्स की आवश्यकता थी। यह मेरा समाधान था:

ps -eo vsize | awk '{p[$1==0]++} END {printf "%-16s %6d\n%-16s %6d\n%-16s %6d\n", "Kernel processes", p[1], "User processes", p[0], "Total processes", p[0]+p[1]}'

नमूना उत्पादन :

Kernel processes    353
User processes       52
Total processes     405

स्पष्टीकरण : मैं हैक का उपयोग कर रहा हूं कि वीएसजेड = 0 प्रक्रियाओं को कर्नेल प्रक्रिया माना जा सकता है। इसलिए awk, मैं वीएसजेड (से ps -eo vsize) पर एक तुलना का मूल्यांकन करता हूं , चाहे वह शून्य के बराबर हो। तुलना का परिणाम या तो एक बूलियन 0 होगा या 1. मैं एक सरणी बनाता हूं p[], और जैसा कि मैं प्रक्रियाओं की सूची को चलाता हूं, अगर यह एक कर्नेल प्रक्रिया है, तो मैं वेतन वृद्धि करता हूं p[1]++। अन्यथा, उपयोगकर्ता प्रक्रिया के रूप में, मैं वेतन वृद्धि करता हूं p[0]++। सभी वेतन वृद्धि के बाद, मैं END { }ब्लॉक में p [0] और p [1] के लिए मान (यानी मायने रखता है) लेबल और प्रिंट करता हूं ।


0

आप मेरे दोस्त की तलाश कर रहे हैं ps, लेकिन वह नहीं है pstree

सबसे पहले, पहले कर्नेल प्रक्रिया को पहचानें। इसका पीआईडी ​​सिस्टमड के बिना सिस्टम पर आमतौर पर 1 और सिस्टमड के साथ 2 है।

फिर इस कमांड का उपयोग करें:

$ pstree -p <1 or 2> | grep -o '([0-9]\+)' | grep -o '[0-9]\+'

चयनित उत्तर (✅ के साथ एक) अन्य कमांड का उपयोग कर रहा है:

$ ps --ppid 2 -p 2 --deselect

इस psआदेश के साथ समस्या यह है कि इसमें केवल प्रत्यक्ष बच्चे शामिल हैं, लेकिन सभी वंशज नहीं हैं। pstreeआदेश सभी सन्तान भी शामिल है। आप | wcसत्यापित करने के लिए इन दो आदेशों के आउटपुट की तुलना और गणना कर सकते हैं (एक आसान तरीका उपयोग कर रहे हैं )।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.