2012-10-13 29 views
7

मैं लिनक्स में एक निश्चित अवधि के लिए, प्रक्रिया की सीपीयू उपयोग और सभी बाल प्रक्रियाओं को जानना चाहता हूं।एक प्रक्रिया के सीपीयू उपयोग और लिनक्स में अपने सभी बाल प्रक्रियाओं की गणना कैसे करें?

अधिक विशिष्ट होना करने के लिए, यहाँ मेरी यूज-केस है:

एक प्रक्रिया है जो उपयोगकर्ता से एक अनुरोध कार्यक्रमों पर अमल करने के लिए इंतजार कर रहा है नहीं है। कार्यक्रमों को निष्पादित करने के लिए, यह प्रक्रिया बाल प्रक्रियाओं (एक समय में 5 की अधिकतम सीमा) को आमंत्रित करती है & इस बाल प्रक्रिया में से प्रत्येक इन सबमिट किए गए कार्यक्रमों में से एक को निष्पादित करती है (मान लें कि उपयोगकर्ता ने 15 प्रोग्राम एक बार सबमिट किए हैं)। इसलिए, यदि उपयोगकर्ता 15 प्रोग्राम प्रस्तुत करता है, तो प्रत्येक 5 बाल प्रक्रियाओं के 3 बैच प्रत्येक भागेंगे। जैसे ही वे कार्यक्रम के निष्पादन को समाप्त करते हैं, बाल प्रक्रियाओं को मार दिया जाता है।

मैं उन 15 कार्यक्रमों के निष्पादन के दौरान मूल प्रक्रिया और उसके सभी बाल प्रक्रिया के लिए% CPU उपयोग के बारे में जानना चाहता हूं।

क्या शीर्ष या अन्य आदेश का उपयोग करके ऐसा करने का कोई आसान तरीका है? (या किसी भी उपकरण को मुझे मूल प्रक्रिया से जोड़ना चाहिए।)

उत्तर

8

आप यह जानकारी /proc/PID/stat में पा सकते हैं जहां पीआईडी ​​आपकी मूल प्रक्रिया की प्रक्रिया आईडी है। यह मानते हुए कि माता-पिता की प्रक्रिया अपने बच्चों के लिए इंतजार कर रहा है तो कुल CPU उपयोग utime, STIME, cutime और cstime से गणना की जा सकती:

utime% लू

समय की राशि कि यह प्रक्रिया उपयोगकर्ता मोड में निर्धारित की गई है, घड़ी की टिक में मापा गया है (sysconf (_SC_CLK_TCK) द्वारा विभाजित करें। इसमें अतिथि समय, अतिथि_टाइम (वर्चुअल सीपीयू चलाने में व्यतीत समय, नीचे देखें), ताकि एपी ऐसी सुविधाएं जो अतिथि समय क्षेत्र से अवगत नहीं हैं उनकी गणना से उस समय को खो देते हैं।

STIME% लू

समय की राशि है कि इस प्रक्रिया कर्नेल मोड में तय किया गया है, घड़ी में मापा sysconf (_SC_CLK_TCK) द्वारा (डिवाइड टिक्स।

cutime% ld

की राशि इस प्रक्रिया की प्रतीक्षा की गई है- बच्चों के लिए उपयोगकर्ता मोड में निर्धारित किया गया है, घड़ी की टिक में मापा गया है ( sysconf (_SC_CLK_TCK) द्वारा विभाजित करें। (समय भी देखें (2)।) इसमें अतिथि समय, cguest_time (एक समय चलने में व्यतीत समय वर्चुअल सीपीयू , निचे देखो)।

cstime% ld

समय की राशि है कि इस प्रक्रिया के इंतजार कर रहे थे-के लिए बच्चों कर्नेल मोड, घड़ी में मापा में अनुसूचित टिक्स (डिवाइड किया गया है sysconf (_SC_CLK_TCK) द्वारा।

देखें proc(5) manpage विवरण के लिए

+0

माता-पिता के लिए बाल प्रक्रियाओं का इंतजार करने का क्या अर्थ है? यदि पृष्ठभूमि प्रक्रियाओं को पृष्ठभूमि में चलाने के लिए फोर्क किया जाता है तो क्या यह तकनीक विफल हो जाएगी? –

1

सटीक आदेश नहीं हो सकता है। लेकिन आप विभिन्न प्रक्रियाओं के सीपीयू उपयोग को प्राप्त करने और इसे जोड़ने के लिए नीचे कुछ ऐसा कर सकते हैं।

#ps -C sendmail,firefox -o pcpu= | awk '{s+=$1} END {print s}'

/proc/[pid]/स्टेट स्थिति प्रक्रिया के बारे में जानकारी। इसका प्रयोग पीएस द्वारा किया जाता है और मानव पठनीय रूप में बनाया जाता है।

एक और तरीका cgroups का उपयोग करना और cpuacct का उपयोग करना है।

http://www.kernel.org/doc/Documentation/cgroups/cpuacct.txt

https://access.redhat.com/knowledge/docs/en-US/Red_Hat_Enterprise_Linux/6/html/Resource_Management_Guide/sec-cpuacct.html

2

और निश्चित रूप से आप उपयोग कर कट्टर-तरह से यह कर सकते हैं अच्छे पुराने सी

find_cpu.c

#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 
#include <unistd.h> 

#define MAX_CHILDREN 100 

/** 
* System command execution output 
* @param <char> command - system command to execute 
* @returb <char> execution output 
*/ 
char *system_output (const char *command) 
{ 
    FILE *pipe; 
    static char out[1000]; 
    pipe = popen (command, "r"); 
    fgets (out, sizeof(out), pipe); 
    pclose (pipe); 
    return out; 
} 

/** 
* Finding all process's children 
* @param <Int> - process ID 
* @param <Int> - array of childs 
*/ 
void find_children (int pid, int children[]) 
{ 
    char empty_command[] = "/bin/ps h -o pid --ppid "; 
    char pid_string[5]; 

    snprintf(pid_string, 5, "%d", pid); 

    char *command = (char*) malloc(strlen(empty_command) + strlen(pid_string) + 1); 
    sprintf(command, "%s%s", empty_command, pid_string); 

    FILE *fp = popen(command, "r"); 

    int child_pid, i = 1; 
    while (fscanf(fp, "%i", &child_pid) != EOF) 
    { 
    children[i] = child_pid; 
    i++; 
    } 
} 

/** 
* Parsign `ps` command output 
* @param <char> out - ps command output 
* @return <int> cpu utilization 
*/ 
float parse_cpu_utilization (const char *out) 
{ 
    float cpu; 
    sscanf (out, "%f", &cpu); 
    return cpu; 
} 


int main(void) 
{ 
    unsigned pid = 1; 

    // getting array with process children 
    int process_children[MAX_CHILDREN] = { 0 }; 
    process_children[0] = pid; // parent PID as first element 
    find_children(pid, process_children); 

    // calculating summary processor utilization 
    unsigned i; 
    float common_cpu_usage = 0.0; 
    for (i = 0; i < sizeof(process_children)/sizeof(int); ++i) 
    { 
    if (process_children[i] > 0) 
    { 
     char *command = (char*)malloc(1000); 
     sprintf (command, "/bin/ps -p %i -o 'pcpu' --no-headers", process_children[i]); 
     common_cpu_usage += parse_cpu_utilization(system_output(command)); 
    } 
    } 
    printf("%f\n", common_cpu_usage); 
    return 0; 
} 

संकलित:

gcc -Wall -pedantic --std=gnu99 find_cpu.c 

आनंद लें!

0

सभी प्रक्रियाओं के लिए कुल CPU की गणना करने के लिए यहां एक-लाइनर है। आप शीर्ष आउटपुट में कॉलम फ़िल्टर पास करके इसे समायोजित कर सकते हैं:

top -b -d 5 -n 2 | awk '$1 == "PID" {block_num++; next} block_num == 2 {sum += $9;} END {print sum}'