Home | History | Annotate | Download | only in process
      1 // Copyright (c) 2013 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 // This file contains methods to iterate over processes on the system.
      6 
      7 #ifndef BASE_PROCESS_PROCESS_ITERATOR_H_
      8 #define BASE_PROCESS_PROCESS_ITERATOR_H_
      9 
     10 #include <stddef.h>
     11 
     12 #include <list>
     13 #include <string>
     14 #include <vector>
     15 
     16 #include "base/base_export.h"
     17 #include "base/files/file_path.h"
     18 #include "base/macros.h"
     19 #include "base/process/process.h"
     20 #include "build/build_config.h"
     21 
     22 #if defined(OS_WIN)
     23 #include <windows.h>
     24 #include <tlhelp32.h>
     25 #elif defined(OS_MACOSX) || defined(OS_OPENBSD)
     26 #include <sys/sysctl.h>
     27 #elif defined(OS_FREEBSD)
     28 #include <sys/user.h>
     29 #elif defined(OS_POSIX)
     30 #include <dirent.h>
     31 #endif
     32 
     33 namespace base {
     34 
     35 #if defined(OS_WIN)
     36 struct ProcessEntry : public PROCESSENTRY32 {
     37   ProcessId pid() const { return th32ProcessID; }
     38   ProcessId parent_pid() const { return th32ParentProcessID; }
     39   const wchar_t* exe_file() const { return szExeFile; }
     40 };
     41 #elif defined(OS_POSIX)
     42 struct BASE_EXPORT ProcessEntry {
     43   ProcessEntry();
     44   ProcessEntry(const ProcessEntry& other);
     45   ~ProcessEntry();
     46 
     47   ProcessId pid() const { return pid_; }
     48   ProcessId parent_pid() const { return ppid_; }
     49   ProcessId gid() const { return gid_; }
     50   const char* exe_file() const { return exe_file_.c_str(); }
     51   const std::vector<std::string>& cmd_line_args() const {
     52     return cmd_line_args_;
     53   }
     54 
     55   ProcessId pid_;
     56   ProcessId ppid_;
     57   ProcessId gid_;
     58   std::string exe_file_;
     59   std::vector<std::string> cmd_line_args_;
     60 };
     61 #endif  // defined(OS_POSIX)
     62 
     63 // Used to filter processes by process ID.
     64 class ProcessFilter {
     65  public:
     66   // Returns true to indicate set-inclusion and false otherwise.  This method
     67   // should not have side-effects and should be idempotent.
     68   virtual bool Includes(const ProcessEntry& entry) const = 0;
     69 
     70  protected:
     71   virtual ~ProcessFilter() {}
     72 };
     73 
     74 // This class provides a way to iterate through a list of processes on the
     75 // current machine with a specified filter.
     76 // To use, create an instance and then call NextProcessEntry() until it returns
     77 // false.
     78 class BASE_EXPORT ProcessIterator {
     79  public:
     80   typedef std::list<ProcessEntry> ProcessEntries;
     81 
     82   explicit ProcessIterator(const ProcessFilter* filter);
     83   virtual ~ProcessIterator();
     84 
     85   // If there's another process that matches the given executable name,
     86   // returns a const pointer to the corresponding PROCESSENTRY32.
     87   // If there are no more matching processes, returns NULL.
     88   // The returned pointer will remain valid until NextProcessEntry()
     89   // is called again or this NamedProcessIterator goes out of scope.
     90   const ProcessEntry* NextProcessEntry();
     91 
     92   // Takes a snapshot of all the ProcessEntry found.
     93   ProcessEntries Snapshot();
     94 
     95  protected:
     96   virtual bool IncludeEntry();
     97   const ProcessEntry& entry() { return entry_; }
     98 
     99  private:
    100   // Determines whether there's another process (regardless of executable)
    101   // left in the list of all processes.  Returns true and sets entry_ to
    102   // that process's info if there is one, false otherwise.
    103   bool CheckForNextProcess();
    104 
    105   // Initializes a PROCESSENTRY32 data structure so that it's ready for
    106   // use with Process32First/Process32Next.
    107   void InitProcessEntry(ProcessEntry* entry);
    108 
    109 #if defined(OS_WIN)
    110   HANDLE snapshot_;
    111   bool started_iteration_;
    112 #elif defined(OS_MACOSX) || defined(OS_BSD)
    113   std::vector<kinfo_proc> kinfo_procs_;
    114   size_t index_of_kinfo_proc_;
    115 #elif defined(OS_POSIX)
    116   DIR* procfs_dir_;
    117 #endif
    118   ProcessEntry entry_;
    119   const ProcessFilter* filter_;
    120 
    121   DISALLOW_COPY_AND_ASSIGN(ProcessIterator);
    122 };
    123 
    124 // This class provides a way to iterate through the list of processes
    125 // on the current machine that were started from the given executable
    126 // name.  To use, create an instance and then call NextProcessEntry()
    127 // until it returns false.
    128 class BASE_EXPORT NamedProcessIterator : public ProcessIterator {
    129  public:
    130   NamedProcessIterator(const FilePath::StringType& executable_name,
    131                        const ProcessFilter* filter);
    132   ~NamedProcessIterator() override;
    133 
    134  protected:
    135   bool IncludeEntry() override;
    136 
    137  private:
    138   FilePath::StringType executable_name_;
    139 
    140   DISALLOW_COPY_AND_ASSIGN(NamedProcessIterator);
    141 };
    142 
    143 // Returns the number of processes on the machine that are running from the
    144 // given executable name.  If filter is non-null, then only processes selected
    145 // by the filter will be counted.
    146 BASE_EXPORT int GetProcessCount(const FilePath::StringType& executable_name,
    147                                 const ProcessFilter* filter);
    148 
    149 }  // namespace base
    150 
    151 #endif  // BASE_PROCESS_PROCESS_ITERATOR_H_
    152