View Javadoc
1   /*
2    * Copyright 2016-2024 The OSHI Project Contributors
3    * SPDX-License-Identifier: MIT
4    */
5   package oshi.software.os;
6   
7   import java.util.List;
8   import java.util.Map;
9   
10  import oshi.annotation.concurrent.ThreadSafe;
11  import oshi.driver.windows.wmi.Win32ProcessCached;
12  import oshi.util.FileUtil;
13  import oshi.util.GlobalConfig;
14  
15  /**
16   * Represents a Process on the operating system, which may contain multiple threads.
17   */
18  @ThreadSafe
19  public interface OSProcess {
20  
21      /**
22       * Gets the name of the process, often the executable program.
23       *
24       * @return the name of the process.
25       */
26      String getName();
27  
28      /**
29       * Gets the full filesystem path of the executing process.
30       *
31       * @return the full path of the executing process.
32       */
33      String getPath();
34  
35      /**
36       * Gets the process command line used to start the process, including arguments if available to be determined. This
37       * method generally returns the same information as {@link #getArguments()} in a more user-readable format, and is
38       * more robust to non-elevated access.
39       * <p>
40       * The format of this string is platform-dependent, may be truncated, and may require the end user to parse the
41       * result. Users should generally prefer {@link #getArguments()} which already parses the results, and use this
42       * method as a backup.
43       * <p>
44       * On AIX and Solaris, the string may be truncated to 80 characters if there was insufficient permission to read the
45       * process memory.
46       * <p>
47       * On Windows, attempts to retrieve the value from process memory, which requires that the process be owned by the
48       * same user as the executing process, or elevated permissions, and additionally requires the target process to have
49       * the same bitness (e.g., this will fail on a 32-bit process if queried by 64-bit and vice versa). If reading
50       * process memory fails, by default, performs a single WMI query for this process, with some latency. If this method
51       * will be frequently called for multiple processes, see the configuration file to enable a batch query mode
52       * leveraging {@link Win32ProcessCached#getCommandLine} to improve performance, or setting that parameter via
53       * {@link GlobalConfig#set(String, Object)} before instantiating any {@link OSProcess} object.
54       *
55       * @return the process command line.
56       */
57      String getCommandLine();
58  
59      /**
60       * Makes a best effort attempt to get a list of the the command-line arguments of the process. Returns the same
61       * information as {@link #getCommandLine()} but parsed to a list. May require elevated permissions or same-user
62       * ownership.
63       *
64       * @return A list of Strings representing the arguments. May return an empty list if there was a failure (for
65       *         example, because the process is already dead or permission was denied).
66       */
67      List<String> getArguments();
68  
69      /**
70       * Makes a best effort attempt to obtain the environment variables of the process. May require elevated permissions
71       * or same-user ownership.
72       *
73       * @return A map representing the environment variables and their values. May return an empty map if there was a
74       *         failure (for example, because the process is already dead or permission was denied).
75       */
76      Map<String, String> getEnvironmentVariables();
77  
78      /**
79       * Makes a best effort attempt to obtain the current working directory for the process.
80       *
81       * @return the process current working directory.
82       */
83      String getCurrentWorkingDirectory();
84  
85      /**
86       * Gets the user name of the process owner.
87       *
88       * @return the user name. On Windows systems, also returns the domain prepended to the username.
89       */
90      String getUser();
91  
92      /**
93       * Gets the user id of the process owner.
94       *
95       * @return the userID. On Windows systems, returns the Security ID (SID)
96       */
97      String getUserID();
98  
99      /**
100      * Gets the group under which the process is executing.
101      * <p>
102      * On Windows systems, populating this value for processes other than the current user requires administrative
103      * privileges (and still may fail for some system processes) and can incur significant latency. When successful,
104      * returns a the default primary group with access to this process, corresponding to the SID in
105      * {@link #getGroupID()}.
106      *
107      * @return the group.
108      */
109     String getGroup();
110 
111     /**
112      * Gets the group id under which the process is executing.
113      * <p>
114      * On Windows systems, populating this value for processes other than the current user requires administrative
115      * privileges (and still may fail for some system processes) and can incur significant latency. When successful,
116      * returns the default primary group SID with access to this process, corresponding to the name in
117      * {@link #getGroup()}.
118      *
119      * @return the groupID.
120      */
121     String getGroupID();
122 
123     /**
124      * Gets the process state.
125      *
126      * @return the execution state of the process.
127      */
128     State getState();
129 
130     /**
131      * Gets the process ID.
132      * <p>
133      * While this is a 32-bit value, it is unsigned on Windows and in extremely rare circumstances may return a negative
134      * value.
135      *
136      * @return the processID.
137      */
138     int getProcessID();
139 
140     /**
141      * Gets the process ID of this process's parent.
142      *
143      * @return the parentProcessID, if any; 0 otherwise.
144      */
145     int getParentProcessID();
146 
147     /**
148      * Gets the number of threads being executed by this process. More information is available using
149      * {@link #getThreadDetails()}.
150      *
151      * @return the number of threads in this process.
152      */
153     int getThreadCount();
154 
155     /**
156      * Gets the priority of this process.
157      * <p>
158      * For Linux and Unix, priority is a value in the range -20 to 19 (20 on some systems). The default priority is 0;
159      * lower priorities cause more favorable scheduling.
160      * <p>
161      * For Windows, priority values can range from 0 (lowest priority) to 31 (highest priority).
162      * <p>
163      * macOS has 128 priority levels, ranging from 0 (lowest priority) to 127 (highest priority). They are divided into
164      * several major bands: 0 through 51 are the normal levels; the default priority is 31. 52 through 79 are the
165      * highest priority regular threads; 80 through 95 are for kernel mode threads; and 96 through 127 correspond to
166      * real-time threads, which are treated differently than other threads by the scheduler.
167      *
168      * @return the priority of this process.
169      */
170     int getPriority();
171 
172     /**
173      * Gets the Virtual Memory Size (VSZ). Includes all memory that the process can access, including memory that is
174      * swapped out and memory that is from shared libraries.
175      *
176      * @return the Virtual Memory Size
177      */
178     long getVirtualSize();
179 
180     /**
181      * Gets the Resident Set Size (RSS). Used to show how much memory is allocated to that process and is in RAM. It
182      * does not include memory that is swapped out. It does include memory from shared libraries as long as the pages
183      * from those libraries are actually in memory. It does include all stack and heap memory.
184      * <p>
185      * On Windows, returns the Private Working Set size, which should match the "Memory" column in the Windows Task
186      * Manager.
187      * <p>
188      * On Linux, returns the RSS value from {@code /proc/[pid]/stat}, which may be inaccurate because of a
189      * kernel-internal scalability optimization. If accurate values are required, read {@code /proc/[pid]/smaps} using
190      * {@link FileUtil#getKeyValueMapFromFile(String, String)}.
191      *
192      * @return the Resident Set Size
193      */
194     long getResidentSetSize();
195 
196     /**
197      * Gets kernel/system (privileged) time used by the process.
198      *
199      * @return the number of milliseconds the process has executed in kernel/system mode.
200      */
201     long getKernelTime();
202 
203     /**
204      * Gets user time used by the process.
205      *
206      * @return the number of milliseconds the process has executed in user mode.
207      */
208     long getUserTime();
209 
210     /**
211      * Gets up time / elapsed time since the process started.
212      *
213      * @return the number of milliseconds since the process started.
214      */
215     long getUpTime();
216 
217     /**
218      * Gets the process start time.
219      *
220      * @return the start time of the process in number of milliseconds since January 1, 1970 UTC.
221      */
222     long getStartTime();
223 
224     /**
225      * Gets the bytes read by the process. This includes all I/O activity generated by the process to include file,
226      * network, and device I/Os.
227      * <p>
228      * On Solaris, includes both bytes read and written.
229      *
230      * @return the number of bytes the process has read.
231      */
232     long getBytesRead();
233 
234     /**
235      * Gets the bytes written by the process. This includes all I/O activity generated by the process to include file,
236      * network, and device I/Os.
237      * <p>
238      * On Solaris, all IO bytes are included read bytes so this value is 0.
239      *
240      * @return the number of bytes the process has written to disk.
241      */
242     long getBytesWritten();
243 
244     /**
245      * Gets the number of open file handles (or network connections) that belongs to the process.
246      * <p>
247      * On FreeBSD and Solaris, this value is only populated if information for a single process id is requested.
248      *
249      * @return open files or -1 if unknown or not supported
250      */
251     long getOpenFiles();
252 
253     /**
254      * Gets the soft limit for open file handles (or network connections) of the given process.
255      * <p>
256      * Retrieving the soft limit for processes other than the calling process is only supported on Linux, FreeBsd and
257      * Solaris.
258      *
259      * @return the soft open file limit for the process if available. Returns -1 if the calling process is not the same
260      *         as this OSProcess instance and the underlying operating system does not support retrieving the soft limit
261      *         for other processes.
262      */
263     long getSoftOpenFileLimit();
264 
265     /**
266      * Gets the hard limit for open file handles (or network connections) that belong to the given process.
267      * <p>
268      * Retrieving the hard limit for processes other than the calling process is only supported on Linux, FreeBsd and
269      * Solaris.
270      *
271      * @return the hard open file limit for the process if available. Returns -1 if the calling process is not the same
272      *         as this OSProcess instance and the underlying operating system does not support retrieving the hard limit
273      *         for other processes.
274      */
275     long getHardOpenFileLimit();
276 
277     /**
278      * Gets cumulative CPU usage of this process.
279      * <p>
280      * This calculation sums CPU ticks across all processors and may exceed 100% for multi-threaded processes. This is
281      * consistent with the cumulative CPU presented by the "top" command on Linux/Unix machines.
282      *
283      * @return The proportion of up time that the process was executing in kernel or user mode.
284      */
285     double getProcessCpuLoadCumulative();
286 
287     /**
288      * Gets CPU usage of this process since a previous snapshot of the same process, provided as a parameter.
289      * <p>
290      * This calculation sums CPU ticks across all processors and may exceed 100% for multi-threaded processes. This is
291      * consistent with process usage calulations on Linux/Unix machines, but should be divided by the number of logical
292      * processors to match the value displayed by the Windows Task Manager.
293      * <p>
294      * The accuracy of this calculation is dependent on both the number of threads on which the process is executing,
295      * and the precision of the Operating System's tick counters. A polling interval of at least a few seconds is
296      * recommended.
297      *
298      * @param proc An {@link OSProcess} object containing statistics for this same process collected at a prior point in
299      *             time. May be null.
300      * @return If the prior snapshot is for the same process at a prior point in time, the proportion of elapsed up time
301      *         between the current process snapshot and the previous one that the process was executing in kernel or
302      *         user mode. Returns cumulative load otherwise.
303      */
304     double getProcessCpuLoadBetweenTicks(OSProcess proc);
305 
306     /**
307      * Attempts to get the bitness (32 or 64) of the process.
308      *
309      * @return The bitness, if able to be determined, 0 otherwise.
310      */
311     int getBitness();
312 
313     /**
314      * Gets the process affinity mask for this process.
315      * <p>
316      * On Windows systems with more than 64 processors, if the threads of the calling process are in a single processor
317      * group, returns the process affinity mask for that group (which may be zero if the specified process is running in
318      * a different group). If the calling process contains threads in multiple groups, returns zero.
319      * <p>
320      * Because macOS does not export interfaces that identify processors or control thread placement, explicit thread to
321      * processor binding is not supported and this method will return a bitmask of all logical processors.
322      * <p>
323      * If the Operating System fails to retrieve an affinity mask (e.g., the process has terminated), returns zero.
324      *
325      * @return a bit vector in which each bit represents the processors that a process is allowed to run on.
326      */
327     long getAffinityMask();
328 
329     /**
330      * Attempts to update process attributes. Returns false if the update fails, which will occur if the process no
331      * longer exists.
332      *
333      * @return {@code true} if the update was successful, false if the update failed. In addition, on a failed update
334      *         the process state will be changed to {@link State#INVALID}.
335      */
336     boolean updateAttributes();
337 
338     /**
339      * Retrieves the threads of the process and their details.
340      * <p>
341      * The amount of returned information is operating-system dependent and may incur some latency.
342      *
343      * @return a list of threads
344      */
345     List<OSThread> getThreadDetails();
346 
347     /**
348      * Gets the number of minor (soft) faults the process has made which have not required loading a memory page from
349      * disk. Sometimes called reclaims.
350      * <p>
351      * On Windows, this includes the total of major and minor faults.
352      * <p>
353      * Not available on AIX.
354      *
355      * @return minor page faults (reclaims).
356      */
357     default long getMinorFaults() {
358         return 0L;
359     }
360 
361     /**
362      * Gets the number of major (hard) faults the process has made which have required loading a memory page from disk.
363      * <p>
364      * Windows does not distinguish major and minor faults at the process level, so this value returns 0 and major
365      * faults are included in {@link #getMinorFaults()}.
366      * <p>
367      * Not available on AIX.
368      *
369      * @return major page faults.
370      */
371     default long getMajorFaults() {
372         return 0L;
373     }
374 
375     /**
376      * A snapshot of the context switches the process has done. Since the context switches could be voluntary and
377      * non-voluntary, this gives the sum of both.
378      * <p>
379      * Not available on Windows. An approximation may be made by summing associated values from
380      * {@link OSThread#getContextSwitches()}.
381      * <p>
382      * Not available on AIX.
383      *
384      * @return sum of both voluntary and involuntary context switches if available, 0 otherwise.
385      */
386     default long getContextSwitches() {
387         return 0L;
388     }
389 
390     /**
391      * Process and Thread Execution States
392      */
393     enum State {
394         /**
395          * Intermediate state in process creation
396          */
397         NEW,
398         /**
399          * Actively executing process
400          */
401         RUNNING,
402         /**
403          * Interruptible sleep state
404          */
405         SLEEPING,
406         /**
407          * Blocked, uninterruptible sleep state
408          */
409         WAITING,
410         /**
411          * Intermediate state in process termination
412          */
413         ZOMBIE,
414         /**
415          * Stopped by the user, such as for debugging
416          */
417         STOPPED,
418         /**
419          * Other or unknown states not defined
420          */
421         OTHER,
422         /**
423          * The state resulting if the process fails to update statistics, probably due to termination.
424          */
425         INVALID,
426         /**
427          * Special case of waiting if the process has been intentionally suspended (Windows only)
428          */
429         SUSPENDED
430     }
431 }