Users: add support for Windows

This commit is contained in:
李通洲 2022-10-06 17:47:49 +08:00
parent a0a46ab73f
commit c0daeb16df
6 changed files with 125 additions and 45 deletions

View File

@ -269,19 +269,21 @@ if(BSD OR APPLE)
)
endif()
if(LINUX OR ANDROID OR WIN_MSYS)
if(LINUX OR ANDROID)
list(APPEND LIBFASTFETCH_SRC
src/detection/cpu/cpu_linux.c
src/detection/memory/memory_linux.c
)
endif()
if(LINUX OR ANDROID OR BSD OR WIN_MSYS)
if(LINUX OR ANDROID OR BSD)
list(APPEND LIBFASTFETCH_SRC
src/detection/cpuUsage/cpuUsage_linux.c
src/detection/disk/disk_linux.c
src/detection/poweradapter/poweradapter_linux.c
src/detection/temps/temps_linux.c
src/detection/users/users_linux.c
src/detection/opengl/opengl_linux.c
)
endif()
@ -302,7 +304,6 @@ if(LINUX OR BSD)
src/detection/media/media_linux.c
src/detection/wmtheme/wmtheme_linux.c
src/detection/font/font_linux.c
src/detection/opengl/opengl_linux.c
)
endif()
@ -311,16 +312,27 @@ if(WIN_MSYS)
src/detection/host/host_windows.cpp
src/detection/bios/bios_windows.cpp
src/detection/board/board_windows.cpp
src/detection/os/os_linux.c
src/detection/gpu/gpu_windows.cpp
src/detection/battery/battery_windows.cpp
src/detection/displayserver/displayserver_windows.c
src/detection/terminalfont/terminalfont_linux.c
src/detection/media/media_linux.c
src/detection/wmtheme/wmtheme_windows.c
src/detection/font/font_linux.c
src/detection/opengl/opengl_windows.c
src/detection/users/users_windows.cpp
src/util/windows/wmi.cpp
# Shared
src/detection/terminalfont/terminalfont_linux.c
src/detection/poweradapter/poweradapter_linux.c
# TODO
src/detection/os/os_linux.c
src/detection/media/media_linux.c
src/detection/font/font_linux.c
src/detection/cpu/cpu_linux.c
src/detection/memory/memory_linux.c
src/detection/cpuUsage/cpuUsage_linux.c
src/detection/disk/disk_linux.c
src/detection/temps/temps_linux.c
)
endif()
@ -345,6 +357,7 @@ if(APPLE)
src/detection/wmtheme/wmtheme_apple.m
src/detection/temps/temps_apple.c
src/detection/font/font_apple.m
src/detection/users/users_linux.c
src/detection/opengl/opengl_apple.c
)
endif()
@ -369,7 +382,6 @@ if(ANDROID)
src/detection/media/media_android.c
src/detection/wmtheme/wmtheme_android.c
src/detection/font/font_android.c
src/detection/opengl/opengl_linux.c
)
endif()

View File

@ -0,0 +1,10 @@
#pragma once
#ifndef FF_INCLUDED_detection_users_users
#define FF_INCLUDED_detection_users_users
#include "fastfetch.h"
void ffDetectUsers(FFlist* users /* List of FFstrbuf */, FFstrbuf* error);
#endif

View File

@ -0,0 +1,36 @@
#include "fastfetch.h"
#include "users.h"
#if FF_HAVE_UTMPX_H
#include <utmpx.h>
#else
//for Android compatibility
#include <utmp.h>
#define utmpx utmp
#define setutxent setutent
#define getutxent getutent
#endif
void ffDetectUsers(FFlist* users, FFstrbuf* error)
{
struct utmpx* n = NULL;
setutxent();
next:
while((n = getutxent()))
{
if(n->ut_type != USER_PROCESS)
continue;
for(uint32_t i = 0; i < users->length; ++i)
{
if(ffStrbufCompS((FFstrbuf*)ffListGet(users, i), n->ut_user) == 0)
goto next;
}
ffStrbufInitS((FFstrbuf*)ffListAdd(users), n->ut_user);
}
if(users->length == 0)
ffStrbufAppendS(error, "Unable to detect users");
}

View File

@ -0,0 +1,42 @@
extern "C" {
#include "users.h"
}
#include "util/windows/wmi.hpp"
void ffDetectUsers(FFlist* users, FFstrbuf* error)
{
IEnumWbemClassObject* pEnumerator = ffQueryWmi(L"SELECT Antecedent FROM Win32_LoggedOnUser", error);
if(!pEnumerator)
return;
IWbemClassObject *pclsObj = NULL;
ULONG uReturn = 0;
next:
while(SUCCEEDED(pEnumerator->Next(WBEM_INFINITE, 1, &pclsObj, &uReturn)) && uReturn != 0)
{
FFstrbuf antecedent;
ffStrbufInit(&antecedent);
ffGetWmiObjValue(pclsObj, L"Antecedent", &antecedent); // \\.\root\cimv2:Win32_Account.Domain="DOMAIN",Name="NAME"
ffStrbufTrimRight(&antecedent, '"'); // \\.\root\cimv2:Win32_Account.Domain="DOMAIN",Name="NAME
ffStrbufSubstrAfterFirstC(&antecedent, '"'); // DOMAIN",Name="NAME
uint32_t index = ffStrbufFirstIndexC(&antecedent, '"');
ffStrbufRemoveSubstr(&antecedent, index, ffStrbufLastIndexC(&antecedent, '"')); // DOMAIN"NAME
antecedent.chars[index] = '\\';
for(uint32_t i = 0; i < users->length; ++i)
{
if(ffStrbufComp((FFstrbuf*)ffListGet(users, i), &antecedent) == 0)
goto next;
}
*(FFstrbuf*)ffListAdd(users) = antecedent;
}
if(users->length == 0)
ffStrbufAppendS(error, "Unable to detect users");
pclsObj->Release();
pEnumerator->Release();
}

View File

@ -1,48 +1,25 @@
#include "fastfetch.h"
#include "common/printing.h"
#if FF_HAVE_UTMPX_H
#include <utmpx.h>
#else
//for Android compatibility
#include <utmp.h>
#define utmpx utmp
#define setutxent setutent
#define getutxent getutent
#endif
#include "detection/users/users.h"
#define FF_USERS_MODULE_NAME "Users"
#define FF_USERS_NUM_FORMAT_ARGS 1
void ffPrintUsers(FFinstance* instance)
{
struct utmpx* n = NULL;
setutxent();
FFlist users;
ffListInit(&users, sizeof(n->ut_user) + 1);
ffListInit(&users, sizeof(FFstrbuf));
next:
while((n = getutxent()))
{
if(n->ut_type == USER_PROCESS)
{
for(uint32_t i = 0; i < users.length; ++i)
{
if(strcmp((const char*)ffListGet(&users, i), n->ut_user) == 0)
goto next;
}
char* dest = ffListAdd(&users);
strncpy(dest, n->ut_user, sizeof(n->ut_user));
dest[sizeof(n->ut_user)] = '\0';
}
}
if(users.length == 0)
FFstrbuf error;
ffStrbufInit(&error);
ffDetectUsers(&users, &error);
if(error.length > 0)
{
ffPrintError(instance, FF_USERS_MODULE_NAME, 0, &instance->config.users, "%*s", error.length, error.chars);
ffListDestroy(&users);
ffPrintError(instance, FF_USERS_MODULE_NAME, 0, &instance->config.users, "Unable to detect users");
ffStrbufDestroy(&error);
return;
}
@ -52,8 +29,11 @@ next:
{
if(i > 0)
ffStrbufAppendS(&result, ", ");
ffStrbufAppendS(&result, (const char*)ffListGet(&users, i));
FFstrbuf* user = (FFstrbuf*)ffListGet(&users, i);
ffStrbufAppend(&result, user);
ffStrbufDestroy(user);
}
ffListDestroy(&users);
if(instance->config.users.outputFormat.length == 0)

View File

@ -145,6 +145,7 @@ void ffBstrToStrbuf(BSTR bstr, FFstrbuf* strbuf) {
ffStrbufEnsureFree(strbuf, (uint32_t)size_needed);
WideCharToMultiByte(CP_UTF8, 0, bstr, len, strbuf->chars, size_needed, nullptr, nullptr);
strbuf->length = (uint32_t)size_needed;
strbuf->chars[size_needed] = '\0';
}
bool ffGetWmiObjValue(IWbemClassObject* obj, const wchar_t* key, FFstrbuf* strbuf)
@ -176,7 +177,6 @@ bool ffGetWmiObjValue(IWbemClassObject* obj, const wchar_t* key, FFstrbuf* strbu
case CIM_REAL32: ffStrbufAppendF(strbuf, "%f", vtProp.fltVal); break;
case CIM_REAL64: ffStrbufAppendF(strbuf, "%f", vtProp.dblVal); break;
case CIM_BOOLEAN: ffStrbufAppendF(strbuf, "%s", vtProp.boolVal ? "True" : "False"); break;
case CIM_STRING: ffBstrToStrbuf(vtProp.bstrVal, strbuf); break;
case CIM_DATETIME: {
ISWbemDateTime *pDateTime;
BSTR dateStr;
@ -190,8 +190,8 @@ bool ffGetWmiObjValue(IWbemClassObject* obj, const wchar_t* key, FFstrbuf* strbu
ffBstrToStrbuf(dateStr, strbuf);
break;
};
default: result = false; break;
case CIM_STRING:
default: ffBstrToStrbuf(vtProp.bstrVal, strbuf); break;
}
}
VariantClear(&vtProp);