Linux API列出正在运行的进程?

Tho*_*omi 49 c c++ linux api process

我需要一个C/C++ API,它允许我列出Linux系统上正在运行的进程,并列出每个进程打开的文件.

希望最终直接读取的/ proc /文件系统.

谁能想到办法做到这一点?

Aid*_*ell 41

http://procps.sourceforge.net/

http://procps.cvs.sourceforge.net/viewvc/procps/procps/proc/readproc.c?view=markup

是ps和其他处理工具的来源.他们确实使用proc(表明它可能是传统和最好的方式).它们的来源非常易读.文件

/procps-3.2.8/proc/readproc.c
Run Code Online (Sandbox Code Playgroud)

可能有用.ephemient发布的一个有用的建议是链接到libproc提供的API ,它应该在你的repo中可用(或者我已经安装过),但是你需要标题的"-dev"变体和what-not.

祝好运

  • procps还可以构建一个`libproc.a`,其中(例如)http://packages.debian.org/libproc-dev中的Debian包 (2认同)
  • 提供这个源文件的链接是非常有用的,我知道我可以使用谷歌,但是如果我们都应该使用谷歌来找到所有答案,那么这个网站就不需要存在 (2认同)
  • http://procps.cvs.sourceforge.net/viewvc/procps/procps/proc/readproc.c?view=markup (2认同)

小智 24

如果你不想读'/ proc.然后你可以考虑编写一个内核模块,它将实现你自己的系统调用.并且应该编写系统调用,以便它可以获取当前进程的列表,例如:

/* ProcessList.c 
    Robert Love Chapter 3
    */
    #include < linux/kernel.h >
    #include < linux/sched.h >
    #include < linux/module.h >

    int init_module(void)
    {
    struct task_struct *task;
    for_each_process(task)
    {
    printk("%s [%d]\n",task->comm , task->pid);
    }

    return 0;
    }

    void cleanup_module(void)
    {
    printk(KERN_INFO "Cleaning Up.\n");
    }
Run Code Online (Sandbox Code Playgroud)

上面的代码来自我的文章http://linuxgazette.net/133/saha.html.一旦你有自己的系统调用,你可以从你的用户空间程序调用它.

  • 来吧伙计们,这很有趣!让我们活一点:-) (13认同)
  • 使程序依赖于自定义内核模块比读取/ proc /更脏.没有一个很好的理由我不会这样做...... (9认同)
  • 编写新的系统调用通常是个坏主意.更糟糕的是,你没有它可以获得正在运行的进程列表.编写新的系统调用应该有_really_充分的理由.[Linux内核开发手册](http://www.linuxjournal.com/content/book-excerpt-linux-kernel-development-3rd-edition)简要介绍了它. (2认同)

sho*_*nex 8

如果你不这样做,那么我猜你将使用的API将最终读取/ proc文件系统.以下是程序执行此操作的一些示例:

但不幸的是,这并不构成API.

  • 究竟.读取/ proc文件系统*是用于将进程信息导出到用户空间的Linux内核官方机制.要求不使用它的解决方案基本上只是表明对系统如何工作的无知.它不会导致更好的软件. (7认同)

Ste*_*ger 8

你去(C/C++):

你可以在这里找到它:http: //ubuntuforums.org/showthread.php?t = 657097

#ifndef __cplusplus
    #define _GNU_SOURCE
#endif

#include <unistd.h>
#include <dirent.h>
#include <sys/types.h> // for opendir(), readdir(), closedir()
#include <sys/stat.h> // for stat()

#ifdef __cplusplus
    #include <iostream>
    #include <cstdlib>
    #include <cstring>
    #include <cstdarg>
#else
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    #include <stdarg.h>
#endif


#define PROC_DIRECTORY "/proc/"
#define CASE_SENSITIVE    1
#define CASE_INSENSITIVE  0
#define EXACT_MATCH       1
#define INEXACT_MATCH     0


int IsNumeric(const char* ccharptr_CharacterList)
{
    for ( ; *ccharptr_CharacterList; ccharptr_CharacterList++)
        if (*ccharptr_CharacterList < '0' || *ccharptr_CharacterList > '9')
            return 0; // false
    return 1; // true
}


int strcmp_Wrapper(const char *s1, const char *s2, int intCaseSensitive)
{
    if (intCaseSensitive)
        return !strcmp(s1, s2);
    else
        return !strcasecmp(s1, s2);
}

int strstr_Wrapper(const char* haystack, const char* needle, int intCaseSensitive)
{
    if (intCaseSensitive)
        return (int) strstr(haystack, needle);
    else
        return (int) strcasestr(haystack, needle);
}


#ifdef __cplusplus
pid_t GetPIDbyName(const char* cchrptr_ProcessName, int intCaseSensitiveness, int intExactMatch)
#else
pid_t GetPIDbyName_implements(const char* cchrptr_ProcessName, int intCaseSensitiveness, int intExactMatch)
#endif
{
    char chrarry_CommandLinePath[100]  ;
    char chrarry_NameOfProcess[300]  ;
    char* chrptr_StringToCompare = NULL ;
    pid_t pid_ProcessIdentifier = (pid_t) -1 ;
    struct dirent* de_DirEntity = NULL ;
    DIR* dir_proc = NULL ;

    int (*CompareFunction) (const char*, const char*, int) ;

    if (intExactMatch)
        CompareFunction = &strcmp_Wrapper;
    else
        CompareFunction = &strstr_Wrapper;


    dir_proc = opendir(PROC_DIRECTORY) ;
    if (dir_proc == NULL)
    {
        perror("Couldn't open the " PROC_DIRECTORY " directory") ;
        return (pid_t) -2 ;
    }

    // Loop while not NULL
    while ( (de_DirEntity = readdir(dir_proc)) )
    {
        if (de_DirEntity->d_type == DT_DIR)
        {
            if (IsNumeric(de_DirEntity->d_name))
            {
                strcpy(chrarry_CommandLinePath, PROC_DIRECTORY) ;
                strcat(chrarry_CommandLinePath, de_DirEntity->d_name) ;
                strcat(chrarry_CommandLinePath, "/cmdline") ;
                FILE* fd_CmdLineFile = fopen (chrarry_CommandLinePath, "rt") ;  // open the file for reading text
                if (fd_CmdLineFile)
                {
                    fscanf(fd_CmdLineFile, "%s", chrarry_NameOfProcess) ; // read from /proc/<NR>/cmdline
                    fclose(fd_CmdLineFile);  // close the file prior to exiting the routine

                    if (strrchr(chrarry_NameOfProcess, '/'))
                        chrptr_StringToCompare = strrchr(chrarry_NameOfProcess, '/') +1 ;
                    else
                        chrptr_StringToCompare = chrarry_NameOfProcess ;

                    //printf("Process name: %s\n", chrarry_NameOfProcess);
                    //printf("Pure Process name: %s\n", chrptr_StringToCompare );

                    if ( CompareFunction(chrptr_StringToCompare, cchrptr_ProcessName, intCaseSensitiveness) )
                    {
                        pid_ProcessIdentifier = (pid_t) atoi(de_DirEntity->d_name) ;
                        closedir(dir_proc) ;
                        return pid_ProcessIdentifier ;
                    }
                }
            }
        }
    }
    closedir(dir_proc) ;
    return pid_ProcessIdentifier ;
}

#ifdef __cplusplus
    pid_t GetPIDbyName(const char* cchrptr_ProcessName)
    {
        return GetPIDbyName(cchrptr_ProcessName, CASE_INSENSITIVE, EXACT_MATCH) ;
    }
#else
    // C cannot overload functions - fixed
    pid_t GetPIDbyName_Wrapper(const char* cchrptr_ProcessName, ... )
    {
        int intTempArgument ;
        int intInputArguments[2] ;
        // intInputArguments[0] = 0 ;
        // intInputArguments[1] = 0 ;
        memset(intInputArguments, 0, sizeof(intInputArguments) ) ;
        int intInputIndex ;
        va_list argptr;

        va_start( argptr, cchrptr_ProcessName );
            for (intInputIndex = 0;  (intTempArgument = va_arg( argptr, int )) != 15; ++intInputIndex)
            {
                intInputArguments[intInputIndex] = intTempArgument ;
            }
        va_end( argptr );
        return GetPIDbyName_implements(cchrptr_ProcessName, intInputArguments[0], intInputArguments[1]);
    }

    #define GetPIDbyName(ProcessName,...) GetPIDbyName_Wrapper(ProcessName, ##__VA_ARGS__, (int) 15)

#endif

int main()
{
    pid_t pid = GetPIDbyName("bash") ; // If -1 = not found, if -2 = proc fs access error
    printf("PID %d\n", pid);
    return EXIT_SUCCESS ;
}
Run Code Online (Sandbox Code Playgroud)


dan*_*iel 5

PS和其他所有工具(内核模块除外)读取/proc./proc是由内核动态创建的特殊文件系统,以便用户模式进程可以读取原本只能用于内核的数据.

因此,推荐的方法是阅读/proc.

您可以快速直观地查看/proc文件系统,了解其结构.对于每个进程,都有一个/proc/pidpid是进程ID号.在此文件夹中,有几个文件包含有关当前进程的不同数据.如果你跑

strace ps -aux
Run Code Online (Sandbox Code Playgroud)

您将看到程序如何ps从中读取此数据/proc.