mirror of
https://github.com/fastfetch-cli/fastfetch.git
synced 2026-09-13 02:42:09 +02:00
GPU temp detection
This commit is contained in:
@@ -12,7 +12,6 @@ Here i just add things that are easy to forget.
|
||||
- `libffprint`: contains the printing functions, logos, format etc
|
||||
- `fastfetch` and `flashfetch`: Executables, that initialize the config of libffprint. Fist one at runtime, second one at compile time
|
||||
- [ ] Better OS output for all possible combinations of /etc/os-release variables.
|
||||
- [ ] Expose temperatures to GPU format string
|
||||
- [ ] Find wayland compositor by looking at \${XDG_RUNTIME_DIR}/${WAYLAND_DISPLAY:-wayland-0}
|
||||
- [ ] Make LocalIP module more configurable
|
||||
- [ ] Automatic migrate old config files to newer versions
|
||||
|
||||
@@ -50,7 +50,7 @@ Title, Separator, OS, Host, Kernel, Uptime, Processes, Packages, Shell, Resoluti
|
||||
|
||||
##### Logos
|
||||
```
|
||||
Android, Arch, Arco, Artix, Bedrock, CachyOS, CentOS, Debian, Devuan, Deepin, Endeavour, Fedora, Garuda, Gentoo, KDE Neon, Kubuntu, Linux, Manjaro, Mint, NixOS, OpenSUSE, OpenSUSE Tumbleweed, OpenSUSE LEAP, Pop!_OS, RebornOS, RedstarOS, Rocky, Ubuntu, Void, Zorin
|
||||
Alpine, Android, Arch, Arco, Artix, Bedrock, CachyOS, CentOS, Debian, Devuan, Deepin, Endeavour, Fedora, Garuda, Gentoo, KDE Neon, Kubuntu, Linux, Manjaro, Mint, NixOS, OpenSUSE, OpenSUSE Tumbleweed, OpenSUSE LEAP, Pop!_OS, RebornOS, RedstarOS, Rocky, Ubuntu, Void, Zorin
|
||||
```
|
||||
* Most of the logos have a small variant. Access it by appending _small to the logo name.
|
||||
* Some logos have an old variant. Access it by appending _old to the logo name.
|
||||
|
||||
+1
-1
@@ -19,7 +19,7 @@
|
||||
--terminal-font-format "Raw: {}; Name: {}; Size: {}; Styles: {}; Pretty: {}"
|
||||
--cpu-format "Name: {}; Pretty: {}; Vendor: {}; Logical online: {}; Logical configured: {}; Physical: {}; Cores: {}; temperature: {}; bios: {}; scaling max: {}; scaling min: {}; info max: {}; info min: {}; cpuinfo: {}; frequency: {}"
|
||||
--cpu-usage-format "Percentage: {}"
|
||||
--gpu-format "Vendor: {}; Vendor pretty: {}; Name: {}; Name pretty: {}; Driver: {}"
|
||||
--gpu-format "Vendor: {}; Vendor pretty: {}; Name: {}; Name pretty: {}; Driver: {}; Temperature: {}"
|
||||
--memory-format "Used: {}; Total: {}; Percentage: {}"
|
||||
--disk-format "Used: {}; Total: {}; Files: {}; Percentage: {}"
|
||||
--battery-format "Manufactor: {}; Model: {}; Technology: {}; Capacaty: {}; Status: {}"
|
||||
|
||||
+21
-10
@@ -3,6 +3,7 @@
|
||||
#include <pthread.h>
|
||||
#include <dirent.h>
|
||||
#include <string.h>
|
||||
#include <math.h>
|
||||
|
||||
static bool isTempFile(const char* name)
|
||||
{
|
||||
@@ -20,22 +21,34 @@ static bool parseHwmonDir(FFstrbuf* dir, FFTempValue* value)
|
||||
return false;
|
||||
|
||||
uint32_t dirLength = dir->length;
|
||||
value->value = 0.0 / 0.0; //use NaN as error value
|
||||
|
||||
FFstrbuf valueString;
|
||||
ffStrbufInit(&valueString);
|
||||
|
||||
struct dirent* dirent;
|
||||
while((dirent = readdir(dirp)) != NULL)
|
||||
{
|
||||
if(isTempFile(dirent->d_name))
|
||||
{
|
||||
ffStrbufAppendS(dir, dirent->d_name);
|
||||
ffGetFileContent(dir->chars, &value->value);
|
||||
ffStrbufSubstrBefore(dir, dirLength);
|
||||
break;
|
||||
}
|
||||
if(!isTempFile(dirent->d_name))
|
||||
continue;
|
||||
|
||||
ffStrbufAppendS(dir, dirent->d_name);
|
||||
ffGetFileContent(dir->chars, &valueString);
|
||||
ffStrbufSubstrBefore(dir, dirLength);
|
||||
|
||||
//ffStrbufToDouble() returns NaN if the string couldn't be parsed
|
||||
value->value = ffStrbufToDouble(&valueString);
|
||||
if(value->value != value->value)
|
||||
continue;
|
||||
|
||||
value->value /= 1000.0; //millidegrees to degrees
|
||||
break;
|
||||
}
|
||||
|
||||
closedir(dirp);
|
||||
ffStrbufDestroy(&valueString);
|
||||
|
||||
if(value->value.length == 0)
|
||||
if(value->value != value->value)
|
||||
return false;
|
||||
|
||||
ffStrbufAppendS(dir, "name");
|
||||
@@ -92,12 +105,10 @@ const FFTempsResult* ffDetectTemps(const FFinstance* instance)
|
||||
FFTempValue* temp = ffListAdd(&result.values);
|
||||
ffStrbufInit(&temp->name);
|
||||
ffStrbufInit(&temp->deviceClass);
|
||||
ffStrbufInit(&temp->value);
|
||||
if(!parseHwmonDir(&baseDir, temp))
|
||||
{
|
||||
ffStrbufDestroy(&temp->name);
|
||||
ffStrbufDestroy(&temp->deviceClass);
|
||||
ffStrbufDestroy(&temp->value);
|
||||
--result.values.length;
|
||||
}
|
||||
|
||||
|
||||
@@ -174,6 +174,7 @@ static void detectVulkan(const FFinstance* instance, FFVulkanResult* result)
|
||||
ffStrbufInit(&gpu->vendor);
|
||||
ffStrbufInit(&gpu->name);
|
||||
ffStrbufInit(&gpu->driver);
|
||||
gpu->temperature = 0.0 / 0.0; //NaN, no way to detect temperature using vulkan
|
||||
ffStrbufAppendS(&gpu->name, physicalDeviceProperties.properties.deviceName);
|
||||
}
|
||||
|
||||
|
||||
+3
-2
@@ -262,12 +262,13 @@ static inline void printCommandHelp(const char* command)
|
||||
}
|
||||
else if(strcasecmp(command, "gpu-format") == 0)
|
||||
{
|
||||
constructAndPrintCommandHelpFormat("gpu", "{2} {4}", 5,
|
||||
constructAndPrintCommandHelpFormat("gpu", "{2} {4}", 6,
|
||||
"GPU vendor",
|
||||
"GPU vendor pretty",
|
||||
"GPU name",
|
||||
"GPU name pretty",
|
||||
"GPU driver"
|
||||
"GPU driver",
|
||||
"GPU temperature"
|
||||
);
|
||||
}
|
||||
else if(strcasecmp(command, "memory-format") == 0)
|
||||
|
||||
+2
-1
@@ -242,6 +242,7 @@ typedef struct FFGPUResult
|
||||
FFstrbuf vendor;
|
||||
FFstrbuf name;
|
||||
FFstrbuf driver;
|
||||
double temperature;
|
||||
} FFGPUResult;
|
||||
|
||||
typedef struct FFVulkanResult
|
||||
@@ -273,8 +274,8 @@ typedef struct FFDisplayServerResult
|
||||
typedef struct FFTempValue
|
||||
{
|
||||
FFstrbuf name;
|
||||
FFstrbuf value;
|
||||
FFstrbuf deviceClass;
|
||||
double value;
|
||||
} FFTempValue;
|
||||
|
||||
typedef struct FFTempsResult
|
||||
|
||||
+4
-14
@@ -36,18 +36,10 @@ static double detectCPUTemp(const FFinstance* instance)
|
||||
FFTempValue* value = ffListGet(&temps->values, i);
|
||||
|
||||
if(
|
||||
ffStrbufFirstIndexS(&value->name, "cpu") == value->name.length &&
|
||||
ffStrbufCompS(&value->name, "k10temp") != 0 &&
|
||||
ffStrbufCompS(&value->name, "coretemp") != 0
|
||||
) continue;
|
||||
|
||||
double temp = ffStrbufToDouble(&value->value);
|
||||
|
||||
//NaN
|
||||
if(temp != temp)
|
||||
continue;
|
||||
|
||||
return temp / 1000.0; // millidegrees to degrees
|
||||
ffStrbufFirstIndexS(&value->name, "cpu") < value->name.length ||
|
||||
ffStrbufCompS(&value->name, "k10temp") == 0 ||
|
||||
ffStrbufCompS(&value->name, "coretemp") == 0
|
||||
) return value->value;
|
||||
}
|
||||
|
||||
return 0.0 / 0.0; //NaN
|
||||
@@ -170,8 +162,6 @@ void ffPrintCPU(FFinstance* instance)
|
||||
double cpuTemp;
|
||||
if(instance->config.cpu.outputFormat.length > 0)
|
||||
cpuTemp = detectCPUTemp(instance);
|
||||
else
|
||||
cpuTemp = 0.0 / 0.0; //NaN
|
||||
|
||||
FFstrbuf cpu;
|
||||
ffStrbufInitA(&cpu, 128);
|
||||
|
||||
+31
-4
@@ -3,7 +3,7 @@
|
||||
#include <string.h>
|
||||
|
||||
#define FF_GPU_MODULE_NAME "GPU"
|
||||
#define FF_GPU_NUM_FORMAT_ARGS 5
|
||||
#define FF_GPU_NUM_FORMAT_ARGS 6
|
||||
|
||||
static void printGPUResult(FFinstance* instance, uint8_t index, FFcache* cache, FFGPUResult* result)
|
||||
{
|
||||
@@ -39,6 +39,7 @@ static void printGPUResult(FFinstance* instance, uint8_t index, FFcache* cache,
|
||||
{FF_FORMAT_ARG_TYPE_STRBUF, &result->name},
|
||||
{FF_FORMAT_ARG_TYPE_STRBUF, &namePretty},
|
||||
{FF_FORMAT_ARG_TYPE_STRBUF, &result->driver},
|
||||
{FF_FORMAT_ARG_TYPE_DOUBLE, &result->temperature}
|
||||
});
|
||||
|
||||
ffStrbufDestroy(&result->vendor);
|
||||
@@ -89,6 +90,26 @@ static void pciGetDriver(struct pci_dev* dev, FFstrbuf* driver, char*(*ffpci_get
|
||||
ffStrbufDestroy(&path);
|
||||
}
|
||||
|
||||
static double pciGetTemperatur(const FFinstance* instance, uint16_t deviceClass)
|
||||
{
|
||||
const FFTempsResult* tempsResult = ffDetectTemps(instance);
|
||||
|
||||
for(uint32_t i = 0; i < tempsResult->values.length; i++)
|
||||
{
|
||||
FFTempValue* tempValue = ffListGet(&tempsResult->values, i);
|
||||
|
||||
uint32_t tempClass;
|
||||
if(sscanf(tempValue->deviceClass.chars, "%x", &tempClass) != 1)
|
||||
continue;
|
||||
|
||||
//The kernel exposes the device class multiplied by 256 for some reason
|
||||
if(tempClass == deviceClass * 256)
|
||||
return tempValue->value;
|
||||
}
|
||||
|
||||
return 0.0 / 0.0; //NaN
|
||||
}
|
||||
|
||||
static bool pciPrintGPUs(FFinstance* instance)
|
||||
{
|
||||
FF_LIBRARY_LOAD(pci, instance->config.libPCI, false, "libpci.so", 4)
|
||||
@@ -121,16 +142,22 @@ static bool pciPrintGPUs(FFinstance* instance)
|
||||
FFGPUResult* result = ffListAdd(&results);
|
||||
|
||||
ffStrbufInitA(&result->vendor, 256);
|
||||
ffpci_lookup_name(pacc, result->vendor.chars, (int) result->vendor.allocated -1, PCI_LOOKUP_VENDOR, dev->vendor_id, dev->device_id);
|
||||
ffpci_lookup_name(pacc, result->vendor.chars, (int) ffStrbufGetFree(&result->vendor), PCI_LOOKUP_VENDOR, dev->vendor_id, dev->device_id);
|
||||
ffStrbufRecalculateLength(&result->vendor);
|
||||
|
||||
ffStrbufInitA(&result->name, 256);
|
||||
ffpci_lookup_name(pacc, result->name.chars, (int) result->name.allocated - 1, PCI_LOOKUP_DEVICE, dev->vendor_id, dev->device_id);
|
||||
ffpci_lookup_name(pacc, result->name.chars, (int) ffStrbufGetFree(&result->name), PCI_LOOKUP_DEVICE, dev->vendor_id, dev->device_id);
|
||||
ffStrbufRecalculateLength(&result->name);
|
||||
|
||||
ffStrbufInit(&result->driver);
|
||||
if(instance->config.gpu.outputFormat.length > 0) //We only need it for the format string, so don't detect it if it isn't needed
|
||||
result->temperature = 0;
|
||||
|
||||
//We only need it for the format string, so don't detect it if it isn't needed
|
||||
if(instance->config.gpu.outputFormat.length > 0)
|
||||
{
|
||||
pciGetDriver(dev, &result->driver, ffpci_get_param);
|
||||
result->temperature = pciGetTemperatur(instance, dev->device_class);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user