Skip to content

Commit 90690ba

Browse files
committed
InitSystem: add new module
Fix #974
1 parent 3811bb1 commit 90690ba

File tree

15 files changed

+321
-97
lines changed

15 files changed

+321
-97
lines changed

CMakeLists.txt

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -343,6 +343,7 @@ set(LIBFASTFETCH_SRC
343343
src/modules/gpu/gpu.c
344344
src/modules/host/host.c
345345
src/modules/icons/icons.c
346+
src/modules/initsystem/initsystem.c
346347
src/modules/gamepad/gamepad.c
347348
src/modules/kernel/kernel.c
348349
src/modules/lm/lm.c
@@ -431,6 +432,7 @@ if(LINUX)
431432
src/detection/gtk_qt/gtk.c
432433
src/detection/host/host_linux.c
433434
src/detection/icons/icons_linux.c
435+
src/detection/initsystem/initsystem_linux.c
434436
src/detection/libc/libc_linux.c
435437
src/detection/lm/lm_linux.c
436438
src/detection/loadavg/loadavg_linux.c
@@ -489,6 +491,7 @@ elseif(ANDROID)
489491
src/detection/gpu/gpu_nosupport.c
490492
src/detection/host/host_android.c
491493
src/detection/icons/icons_nosupport.c
494+
src/detection/initsystem/initsystem_linux.c
492495
src/detection/libc/libc_android.c
493496
src/detection/lm/lm_nosupport.c
494497
src/detection/loadavg/loadavg_linux.c
@@ -559,6 +562,7 @@ elseif(BSD)
559562
src/detection/host/host_bsd.c
560563
src/detection/lm/lm_linux.c
561564
src/detection/icons/icons_linux.c
565+
src/detection/initsystem/initsystem_linux.c
562566
src/detection/libc/libc_bsd.c
563567
src/detection/loadavg/loadavg_bsd.c
564568
src/detection/locale/locale_linux.c
@@ -618,6 +622,7 @@ elseif(APPLE)
618622
src/detection/gpu/gpu_apple.m
619623
src/detection/host/host_apple.c
620624
src/detection/icons/icons_nosupport.c
625+
src/detection/initsystem/initsystem_linux.c
621626
src/detection/lm/lm_nosupport.c
622627
src/detection/loadavg/loadavg_bsd.c
623628
src/detection/libc/libc_apple.c
@@ -676,6 +681,7 @@ elseif(WIN32)
676681
src/detection/gpu/gpu_windows.c
677682
src/detection/host/host_windows.c
678683
src/detection/icons/icons_windows.c
684+
src/detection/initsystem/initsystem_nosupport.c
679685
src/detection/libc/libc_windows.cpp
680686
src/detection/lm/lm_nosupport.c
681687
src/detection/loadavg/loadavg_nosupport.c

src/common/modules.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,7 @@ static FFModuleBaseInfo* H[] = {
5959

6060
static FFModuleBaseInfo* I[] = {
6161
(void*) &instance.config.modules.icons,
62+
(void*) &instance.config.modules.initSystem,
6263
NULL,
6364
};
6465

src/common/processing.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@
22

33
#include "util/FFstrbuf.h"
44

5+
#include <sys/types.h>
6+
57
const char* ffProcessAppendOutput(FFstrbuf* buffer, char* const argv[], bool useStdErr);
68

79
static inline const char* ffProcessAppendStdOut(FFstrbuf* buffer, char* const argv[])
@@ -24,5 +26,5 @@ static inline const char* ffProcessAppendStdErr(FFstrbuf* buffer, char* const ar
2426
bool ffProcessGetInfoWindows(uint32_t pid, uint32_t* ppid, FFstrbuf* pname, FFstrbuf* exe, const char** exeName, FFstrbuf* exePath, bool* gui);
2527
#else
2628
void ffProcessGetInfoLinux(pid_t pid, FFstrbuf* processName, FFstrbuf* exe, const char** exeName, FFstrbuf* exePath);
27-
const char* ffProcessGetBasicInfoLinux(pid_t pid, char* name, pid_t* ppid, int32_t* tty);
29+
const char* ffProcessGetBasicInfoLinux(pid_t pid, FFstrbuf* name, pid_t* ppid, int32_t* tty);
2830
#endif

src/common/processing_linux.c

Lines changed: 70 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
#include "common/io/io.h"
44
#include "common/time.h"
55
#include "util/stringUtils.h"
6+
#include "util/mallocHelper.h"
67

78
#include <stdlib.h>
89
#include <unistd.h>
@@ -17,6 +18,9 @@
1718
#include <sys/user.h>
1819
#include <sys/sysctl.h>
1920
#endif
21+
#ifdef __APPLE__
22+
#include <libproc.h>
23+
#endif
2024

2125
enum { FF_PIPE_BUFSIZ = 8192 };
2226

@@ -119,28 +123,31 @@ void ffProcessGetInfoLinux(pid_t pid, FFstrbuf* processName, FFstrbuf* exe, cons
119123
char filePath[64];
120124
snprintf(filePath, sizeof(filePath), "/proc/%d/cmdline", (int)pid);
121125

122-
if(ffAppendFileBuffer(filePath, exe))
126+
if(ffReadFileBuffer(filePath, exe))
123127
{
124-
ffStrbufTrimRightSpace(exe);
125128
ffStrbufRecalculateLength(exe); //Trim the arguments
129+
ffStrbufTrimRightSpace(exe);
126130
ffStrbufTrimLeft(exe, '-'); //Login shells start with a dash
127131
}
128132

129-
snprintf(filePath, sizeof(filePath), "/proc/%d/exe", (int)pid);
130-
ffStrbufEnsureFixedLengthFree(exePath, PATH_MAX);
131-
ssize_t length = readlink(filePath, exePath->chars, exePath->allocated - 1);
132-
if (length > 0) // doesn't contain trailing NUL
133+
if (exePath)
133134
{
134-
exePath->chars[length] = '\0';
135-
exePath->length = (uint32_t) length;
135+
snprintf(filePath, sizeof(filePath), "/proc/%d/exe", (int)pid);
136+
ffStrbufEnsureFixedLengthFree(exePath, PATH_MAX);
137+
ssize_t length = readlink(filePath, exePath->chars, exePath->allocated - 1);
138+
if (length > 0) // doesn't contain trailing NUL
139+
{
140+
exePath->chars[length] = '\0';
141+
exePath->length = (uint32_t) length;
142+
}
136143
}
137144

138145
#elif defined(__APPLE__)
139146

140147
size_t len = 0;
141148
int mibs[] = { CTL_KERN, KERN_PROCARGS2, pid };
142149
if (sysctl(mibs, sizeof(mibs) / sizeof(*mibs), NULL, &len, NULL, 0) == 0)
143-
{
150+
{// try get arg0
144151
#ifndef MAC_OS_X_VERSION_10_15
145152
//don't know why if don't let len longer, proArgs2 and len will change during the following sysctl() in old MacOS version.
146153
len++;
@@ -153,7 +160,8 @@ void ffProcessGetInfoLinux(pid_t pid, FFstrbuf* processName, FFstrbuf* exe, cons
153160
const char* realExePath = procArgs2 + sizeof(argc);
154161

155162
const char* arg0 = memchr(realExePath, '\0', len - (size_t) (realExePath - procArgs2));
156-
ffStrbufSetNS(exePath, (uint32_t) (arg0 - realExePath), realExePath);
163+
if (exePath)
164+
ffStrbufSetNS(exePath, (uint32_t) (arg0 - realExePath), realExePath);
157165

158166
do arg0++; while (*arg0 == '\0');
159167
assert(arg0 < procArgs2 + len);
@@ -162,6 +170,17 @@ void ffProcessGetInfoLinux(pid_t pid, FFstrbuf* processName, FFstrbuf* exe, cons
162170
ffStrbufSetS(exe, arg0);
163171
}
164172
}
173+
else
174+
{
175+
ffStrbufEnsureFixedLengthFree(exe, PATH_MAX);
176+
int length = proc_pidpath(pid, exe->chars, exe->allocated);
177+
if (length > 0)
178+
{
179+
exe->length = (uint32_t) length;
180+
if (exePath)
181+
ffStrbufSet(exePath, exe);
182+
}
183+
}
165184

166185
#elif defined(__FreeBSD__)
167186

@@ -170,7 +189,7 @@ void ffProcessGetInfoLinux(pid_t pid, FFstrbuf* processName, FFstrbuf* exe, cons
170189

171190
static_assert(ARG_MAX > PATH_MAX, "");
172191

173-
if(sysctl(
192+
if(exePath && sysctl(
174193
(int[]){CTL_KERN, KERN_PROC, KERN_PROC_PATHNAME, pid}, 4,
175194
args, &size,
176195
NULL, 0
@@ -213,34 +232,46 @@ void ffProcessGetInfoLinux(pid_t pid, FFstrbuf* processName, FFstrbuf* exe, cons
213232
*exeName = exe->chars + lastSlashIndex + 1;
214233
}
215234

216-
const char* ffProcessGetBasicInfoLinux(pid_t pid, char* name, pid_t* ppid, int32_t* tty)
235+
const char* ffProcessGetBasicInfoLinux(pid_t pid, FFstrbuf* name, pid_t* ppid, int32_t* tty)
217236
{
218237
if (pid <= 0)
219238
return "Invalid pid";
220239

221240
#ifdef __linux__
222241

223-
char statFilePath[64];
224-
snprintf(statFilePath, sizeof(statFilePath), "/proc/%d/stat", (int)pid);
225-
char buf[PROC_FILE_BUFFSIZ];
226-
ssize_t nRead = ffReadFileData(statFilePath, sizeof(buf) - 1, buf);
227-
if(nRead < 0)
228-
return "ffReadFileData(statFilePath, sizeof(buf)-1, buf) failed";
229-
buf[nRead] = '\0';
230-
231-
*ppid = 0;
232-
static_assert(sizeof(*ppid) == sizeof(int), "");
233-
234-
int tty_;
235-
if(
236-
sscanf(buf, "%*s (%255[^)]) %*c %d %*d %*d %d", name, ppid, &tty_) < 2 || //stat (comm) state ppid pgrp session tty
237-
!ffStrSet(name) ||
238-
*ppid == 0
239-
)
240-
return "sscanf(stat) failed";
241-
242-
if (tty)
243-
*tty = tty_ & 0xFF;
242+
char procFilePath[64];
243+
if (ppid)
244+
{
245+
snprintf(procFilePath, sizeof(procFilePath), "/proc/%d/stat", (int)pid);
246+
char buf[PROC_FILE_BUFFSIZ];
247+
ssize_t nRead = ffReadFileData(procFilePath, sizeof(buf) - 1, buf);
248+
if(nRead < 0)
249+
return "ffReadFileData(/proc/pid/stat, PROC_FILE_BUFFSIZ-1, buf) failed";
250+
buf[nRead] = '\0';
251+
252+
*ppid = 0;
253+
static_assert(sizeof(*ppid) == sizeof(int), "");
254+
255+
ffStrbufEnsureFixedLengthFree(name, 255);
256+
int tty_;
257+
if(
258+
sscanf(buf, "%*s (%255[^)]) %*c %d %*d %*d %d", name->chars, ppid, &tty_) < 2 || //stat (comm) state ppid pgrp session tty
259+
name->chars[0] == '\0'
260+
)
261+
return "sscanf(stat) failed";
262+
263+
ffStrbufRecalculateLength(name);
264+
if (tty)
265+
*tty = tty_ & 0xFF;
266+
}
267+
else
268+
{
269+
snprintf(procFilePath, sizeof(procFilePath), "/proc/%d/comm", (int)pid);
270+
ssize_t nRead = ffReadFileBuffer(procFilePath, name);
271+
if(nRead < 0)
272+
return "ffReadFileBuffer(/proc/pid/comm, name) failed";
273+
ffStrbufTrimRightSpace(name);
274+
}
244275

245276
#elif defined(__APPLE__)
246277

@@ -253,8 +284,9 @@ const char* ffProcessGetBasicInfoLinux(pid_t pid, char* name, pid_t* ppid, int32
253284
))
254285
return "sysctl(KERN_PROC_PID) failed";
255286

256-
*ppid = (pid_t)proc.kp_eproc.e_ppid;
257-
strcpy(name, proc.kp_proc.p_comm); //trancated to 16 chars
287+
ffStrbufSetS(name, proc.kp_proc.p_comm); //trancated to 16 chars
288+
if (ppid)
289+
*ppid = (pid_t)proc.kp_eproc.e_ppid;
258290
if (tty)
259291
{
260292
*tty = ((proc.kp_eproc.e_tdev >> 24) & 0xFF) == 0x10
@@ -273,8 +305,9 @@ const char* ffProcessGetBasicInfoLinux(pid_t pid, char* name, pid_t* ppid, int32
273305
))
274306
return "sysctl(KERN_PROC_PID) failed";
275307

276-
*ppid = (pid_t)proc.ki_ppid;
277-
strcpy(name, proc.ki_comm);
308+
ffStrbufSetS(name, proc.ki_comm);
309+
if (ppid)
310+
*ppid = (pid_t)proc.ki_ppid;
278311
if (tty)
279312
{
280313
if (proc.ki_tdev != NODEV && proc.ki_flag & P_CONTROLT)
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
#pragma once
2+
3+
#include "fastfetch.h"
4+
5+
typedef struct FFInitSystemResult
6+
{
7+
uint32_t pid;
8+
FFstrbuf name;
9+
FFstrbuf exe;
10+
} FFInitSystemResult;
11+
12+
const char* ffDetectInitSystem(FFInitSystemResult* result);
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
#include "initsystem.h"
2+
#include "common/processing.h"
3+
4+
const char* ffDetectInitSystem(FFInitSystemResult* result)
5+
{
6+
const char* error = ffProcessGetBasicInfoLinux((int) result->pid, &result->name, NULL, NULL);
7+
if (error) return error;
8+
9+
const char* exeName;
10+
11+
ffProcessGetInfoLinux((int) result->pid, &result->name, &result->exe, &exeName, NULL);
12+
13+
return NULL;
14+
}
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
#include "initsystem.h"
2+
3+
const char* ffDetectInitSystem(FF_MAYBE_UNUSED FFInitSystemResult* result)
4+
{
5+
return "Not supported on this platform";
6+
}

0 commit comments

Comments
 (0)