Merge branch 'xnvctrl' into develop

pull/109/head
FlightlessMango 4 years ago
commit c9558eec50

@ -7,18 +7,22 @@ FILE *amdGpuFile = nullptr, *amdTempFile = nullptr, *amdGpuVramTotalFile = nullp
pthread_t cpuThread, gpuThread, cpuInfoThread;
void *getNvidiaGpuInfo(void *){
if (!nvmlSuccess)
checkNvidia();
if (nvmlSuccess){
getNvidiaInfo();
getNVMLInfo();
gpu_info.load = nvidiaUtilization.gpu;
gpu_info.temp = nvidiaTemp;
gpu_info.memoryUsed = nvidiaMemory.used / (1024.f * 1024.f * 1024.f);
gpu_info.CoreClock = nvidiaCoreClock;
gpu_info.MemClock = nvidiaMemClock * 2;
gpu_info.MemClock = nvidiaMemClock;
} else if (nvctrlSuccess) {
getNvctrlInfo();
gpu_info.load = nvctrl_info.load;
gpu_info.temp = nvctrl_info.temp;
gpu_info.memoryUsed = nvctrl_info.memoryUsed / (1024.f);
gpu_info.CoreClock = nvctrl_info.CoreClock;
gpu_info.MemClock = nvctrl_info.MemClock;
}
pthread_detach(gpuThread);
return NULL;
}

@ -3,6 +3,7 @@
#include <stdlib.h>
#include <stdio.h>
#include "nvidia_info.h"
#include "nvctrl.h"
using namespace std;
extern FILE *amdGpuFile, *amdTempFile, *amdGpuVramTotalFile, *amdGpuVramUsedFile, *amdGpuCoreClockFile, *amdGpuMemoryClockFile;

@ -0,0 +1,95 @@
// This is generated file. Do not modify directly.
// Path to the code generator: /home/crz/git/MangoHud/generate_library_loader.py .
#include "loader_nvctrl.h"
// Put these sanity checks here so that they fire at most once
// (to avoid cluttering the build output).
#if !defined(LIBRARY_LOADER_NVCTRL_H_DLOPEN) && !defined(LIBRARY_LOADER_NVCTRL_H_DT_NEEDED)
#error neither LIBRARY_LOADER_NVCTRL_H_DLOPEN nor LIBRARY_LOADER_NVCTRL_H_DT_NEEDED defined
#endif
#if defined(LIBRARY_LOADER_NVCTRL_H_DLOPEN) && defined(LIBRARY_LOADER_NVCTRL_H_DT_NEEDED)
#error both LIBRARY_LOADER_NVCTRL_H_DLOPEN and LIBRARY_LOADER_NVCTRL_H_DT_NEEDED defined
#endif
libnvctrl_loader::libnvctrl_loader() : loaded_(false) {
}
libnvctrl_loader::~libnvctrl_loader() {
CleanUp(loaded_);
}
bool libnvctrl_loader::Load(const std::string& library_name) {
if (loaded_) {
return false;
}
#if defined(LIBRARY_LOADER_NVCTRL_H_DLOPEN)
library_ = dlopen(library_name.c_str(), RTLD_LAZY);
if (!library_)
return false;
XNVCTRLIsNvScreen =
reinterpret_cast<decltype(this->XNVCTRLIsNvScreen)>(
dlsym(library_, "XNVCTRLIsNvScreen"));
if (!XNVCTRLIsNvScreen) {
CleanUp(true);
return false;
}
XNVCTRLQueryVersion =
reinterpret_cast<decltype(this->XNVCTRLQueryVersion)>(
dlsym(library_, "XNVCTRLQueryVersion"));
if (!XNVCTRLQueryVersion) {
CleanUp(true);
return false;
}
XNVCTRLQueryAttribute =
reinterpret_cast<decltype(this->XNVCTRLQueryAttribute)>(
dlsym(library_, "XNVCTRLQueryAttribute"));
if (!XNVCTRLQueryAttribute) {
CleanUp(true);
return false;
}
XNVCTRLQueryTargetStringAttribute =
reinterpret_cast<decltype(this->XNVCTRLQueryTargetStringAttribute)>(
dlsym(library_, "XNVCTRLQueryTargetStringAttribute"));
if (!XNVCTRLQueryTargetStringAttribute) {
CleanUp(true);
return false;
}
XNVCTRLQueryTargetAttribute64 =
reinterpret_cast<decltype(this->XNVCTRLQueryTargetAttribute64)>(
dlsym(library_, "XNVCTRLQueryTargetAttribute64"));
if (!XNVCTRLQueryTargetAttribute64) {
CleanUp(true);
return false;
}
#endif
#if defined(LIBRARY_LOADER_NVCTRL_H_DT_NEEDED)
XNVCTRLQueryVersion = &::XNVCTRLQueryVersion;
XNVCTRLQueryAttribute = &::XNVCTRLQueryAttribute;
#endif
loaded_ = true;
return true;
}
void libnvctrl_loader::CleanUp(bool unload) {
#if defined(LIBRARY_LOADER_NVCTRL_H_DLOPEN)
if (unload) {
dlclose(library_);
library_ = NULL;
}
#endif
loaded_ = false;
XNVCTRLQueryVersion = NULL;
XNVCTRLQueryAttribute = NULL;
}

@ -0,0 +1,44 @@
// This is generated file. Do not modify directly.
// Path to the code generator: /home/crz/git/MangoHud/generate_library_loader.py .
#ifndef LIBRARY_LOADER_NVCTRL_H
#define LIBRARY_LOADER_NVCTRL_H
#define Bool bool
#include <X11/Xlib.h>
#include "NVCtrl/NVCtrlLib.h"
#define LIBRARY_LOADER_NVCTRL_H_DLOPEN
#include <string>
#include <dlfcn.h>
class libnvctrl_loader {
public:
libnvctrl_loader();
libnvctrl_loader(const std::string& library_name) { Load(library_name); }
~libnvctrl_loader();
bool Load(const std::string& library_name);
bool IsLoaded() { return loaded_; }
decltype(&::XNVCTRLIsNvScreen) XNVCTRLIsNvScreen;
decltype(&::XNVCTRLQueryVersion) XNVCTRLQueryVersion;
decltype(&::XNVCTRLQueryAttribute) XNVCTRLQueryAttribute;
decltype(&::XNVCTRLQueryTargetStringAttribute) XNVCTRLQueryTargetStringAttribute;
decltype(&::XNVCTRLQueryTargetAttribute64) XNVCTRLQueryTargetAttribute64;
private:
void CleanUp(bool unload);
#if defined(LIBRARY_LOADER_NVCTRL_H_DLOPEN)
void* library_;
#endif
bool loaded_;
// Disallow copy constructor and assignment operator.
libnvctrl_loader(const libnvctrl_loader&);
void operator=(const libnvctrl_loader&);
};
#endif // LIBRARY_LOADER_NVCTRL_H

@ -44,6 +44,7 @@ vklayer_files = files(
'font_unispace.c',
'cpu.cpp',
'loaders/loader_nvml.cpp',
'loaders/loader_nvctrl.cpp',
'nvml.cpp',
'file_utils.cpp',
'memory.cpp',
@ -52,6 +53,7 @@ vklayer_files = files(
'gpu.cpp',
'notify.cpp',
'elfhacks.cpp',
'nvctrl.cpp',
)
opengl_files = files(

@ -0,0 +1,108 @@
#include <stdio.h>
#include <cstring>
#include <sstream>
#include <unordered_map>
#include "nvctrl.h"
#include "loaders/loader_nvctrl.h"
#include "string_utils.h"
typedef std::unordered_map<std::string, std::string> string_map;
Display *display = XOpenDisplay(NULL);
libnvctrl_loader nvctrl("libXNVCtrl.so");
struct nvctrlInfo nvctrl_info;
bool nvctrlSuccess = false;
bool checkXNVCtrl()
{
if (nvctrl.IsLoaded()) {
nvctrlSuccess = nvctrl.XNVCTRLIsNvScreen(display, 0);
return nvctrlSuccess;
}
return false;
}
void parse_token(std::string token, string_map& options) {
std::string param, value;
size_t equal = token.find("=");
if (equal == std::string::npos)
return;
value = token.substr(equal+1);
param = token.substr(0, equal);
trim(param);
trim(value);
//std::cerr << __func__ << ": " << param << "=" << value << std::endl;
if (!param.empty())
options[param] = value;
}
char* get_attr_target_string(int attr, int target_type, int target_id) {
char* c = nullptr;
if (!nvctrl.XNVCTRLQueryTargetStringAttribute(display, target_type, target_id, 0, attr, &c)) {
fprintf(stderr, "Failed to query attribute '%d'.\n", attr);
}
return c;
}
void getNvctrlInfo(){
string_map params;
std::string token;
int enums[] = {
NV_CTRL_STRING_GPU_UTILIZATION,
NV_CTRL_STRING_GPU_CURRENT_CLOCK_FREQS,
0 // keep null
};
for (size_t i=0; enums[i]; i++) {
char* str = get_attr_target_string(enums[i], NV_CTRL_TARGET_TYPE_GPU, 0);
if (!str)
continue;
std::stringstream ss (str);
while (std::getline(ss, token, ',')) {
parse_token(token, params);
}
free(str);
}
if (!try_stoi(nvctrl_info.load, params["graphics"]))
nvctrl_info.load = 0;
if (!try_stoi(nvctrl_info.CoreClock, params["nvclock"]))
nvctrl_info.CoreClock = 0;
if (!try_stoi(nvctrl_info.MemClock, params["memclock"]))
nvctrl_info.MemClock = 0;
int64_t temp = 0;
nvctrl.XNVCTRLQueryTargetAttribute64(display,
NV_CTRL_TARGET_TYPE_GPU,
0,
0,
NV_CTRL_GPU_CORE_TEMPERATURE,
&temp);
nvctrl_info.temp = temp;
int64_t memtotal = 0;
nvctrl.XNVCTRLQueryTargetAttribute64(display,
NV_CTRL_TARGET_TYPE_GPU,
0,
0,
NV_CTRL_TOTAL_DEDICATED_GPU_MEMORY,
&memtotal);
nvctrl_info.memoryTotal = memtotal;
int64_t memused = 0;
nvctrl.XNVCTRLQueryTargetAttribute64(display,
NV_CTRL_TARGET_TYPE_GPU,
0,
0,
NV_CTRL_USED_DEDICATED_GPU_MEMORY,
&memused);
nvctrl_info.memoryUsed = memused;
}

@ -0,0 +1,14 @@
struct nvctrlInfo{
int load;
int temp;
float memoryUsed;
float memoryTotal;
int MemClock;
int CoreClock;
};
extern struct nvctrlInfo nvctrl_info;
extern bool nvctrlSuccess;
bool checkXNVCtrl(void);
void getNvctrlInfo(void);
char *get_attr_target_string(int attr, int target_type, int target_id);

@ -9,5 +9,5 @@ extern struct nvmlUtilization_st nvidiaUtilization;
extern struct nvmlMemory_st nvidiaMemory;
extern bool nvmlSuccess;
bool checkNvidia(void);
void getNvidiaInfo(void);
bool checkNVML(void);
void getNVMLInfo(void);

@ -10,7 +10,7 @@ unsigned int nvidiaTemp, nvidiaCoreClock, nvidiaMemClock;
struct nvmlUtilization_st nvidiaUtilization;
struct nvmlMemory_st nvidiaMemory {};
bool checkNvidia(){
bool checkNVML(){
if (nvml.IsLoaded()){
result = nvml.nvmlInit();
if (NVML_SUCCESS != result) {
@ -25,11 +25,14 @@ bool checkNvidia(){
return false;
}
void getNvidiaInfo(){
void getNVMLInfo(){
nvmlReturn_t response;
nvml.nvmlDeviceGetHandleByIndex(0, &nvidiaDevice);
nvml.nvmlDeviceGetUtilizationRates(nvidiaDevice, &nvidiaUtilization);
response = nvml.nvmlDeviceGetUtilizationRates(nvidiaDevice, &nvidiaUtilization);
nvml.nvmlDeviceGetTemperature(nvidiaDevice, NVML_TEMPERATURE_GPU, &nvidiaTemp);
nvml.nvmlDeviceGetMemoryInfo(nvidiaDevice, &nvidiaMemory);
nvml.nvmlDeviceGetClockInfo(nvidiaDevice, NVML_CLOCK_GRAPHICS, &nvidiaCoreClock);
nvml.nvmlDeviceGetClockInfo(nvidiaDevice, NVML_CLOCK_MEM, &nvidiaMemClock);
if (response == NVML_ERROR_NOT_SUPPORTED)
nvmlSuccess = false;
}

@ -782,7 +782,14 @@ void init_gpu_stats(uint32_t& vendorID, overlay_params& params)
// NVIDIA or Intel but maybe has Optimus
if (vendorID == 0x8086
|| vendorID == 0x10de) {
if ((params.enabled[OVERLAY_PARAM_ENABLED_gpu_stats] = checkNvidia())) {
if (checkNVML())
getNVMLInfo();
if (!nvmlSuccess)
checkXNVCtrl();
if ((params.enabled[OVERLAY_PARAM_ENABLED_gpu_stats] = (nvmlSuccess || nvctrlSuccess))) {
vendorID = 0x10de;
}
}

@ -84,7 +84,9 @@ static bool try_stoi(int& val, const std::string& str, std::size_t* pos = 0, int
val = std::stoi(str, pos, base);
return true;
} catch (std::invalid_argument& e) {
#ifndef NDEBUG
std::cerr << __func__ << ": invalid argument: '" << str << "'" << std::endl;
#endif
}
return false;
}
@ -95,7 +97,9 @@ static bool try_stoull(unsigned long long& val, const std::string& str, std::siz
val = std::stoull(str, pos, base);
return true;
} catch (std::invalid_argument& e) {
#ifndef NDEBUG
std::cerr << __func__ << ": invalid argument: '" << str << "'" << std::endl;
#endif
}
return false;
}

Loading…
Cancel
Save