X-Git-Url: https://git.wpitchoune.net/gitweb/?p=psensor.git;a=blobdiff_plain;f=src%2Flib%2Fnvidia.c;h=685f97da9311b1e50a082400e9bf1be22a1c2592;hp=b9a766a1d9f93fdd1b1964f643c7f74f89b600d5;hb=c1e20f2631a1249720e9c75d753eacfcb0f6c7b9;hpb=269ab66f9042f48748b18180d176978e509a11cf diff --git a/src/lib/nvidia.c b/src/lib/nvidia.c index b9a766a..685f97d 100644 --- a/src/lib/nvidia.c +++ b/src/lib/nvidia.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 2010-2014 jeanfi@gmail.com + * Copyright (C) 2010-2016 jeanfi@gmail.com * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as @@ -31,9 +31,22 @@ #include #include +#include #include -Display *display; +static Display *display; + +static const char *PROVIDER_NAME = "nvctrl"; + +static void set_nvidia_id(struct psensor *s, int id) +{ + *(int *)s->provider_data = id; +} + +static int get_nvidia_id(struct psensor *s) +{ + return *(int *)s->provider_data; +} static char *get_product_name(int id, int type) { @@ -50,15 +63,17 @@ static char *get_product_name(int id, int type) NV_CTRL_STRING_PRODUCT_NAME, &name); if (res == True) { - if (strcmp(name, "Unknown")) { + if (strcmp(name, "Unknown")) return name; - } else { - log_err(_("Unknown NVIDIA product name for GPU %d"), - id); - free(name); - } + + log_err(_("%s: Unknown NVIDIA product name for GPU %d"), + PROVIDER_NAME, + id); + free(name); } else { - log_err(_("Failed to retrieve NVIDIA product name for GPU %d"), + log_err(_("%s: " + "Failed to retrieve NVIDIA product name for GPU %d"), + PROVIDER_NAME, id); } @@ -74,8 +89,8 @@ static double get_att(int target, int id, int att) if (res == True) return temp; - else - return UNKNOWN_DBL_VALUE; + + return UNKNOWN_DBL_VALUE; } static double get_usage_att(char *atts, const char *att) @@ -132,20 +147,30 @@ static const char *get_nvidia_type_str(int type) { if (type & SENSOR_TYPE_GRAPHICS) return "graphics"; - else if (type & SENSOR_TYPE_VIDEO) + + if (type & SENSOR_TYPE_VIDEO) return "video"; - else if (type & SENSOR_TYPE_MEMORY) + + if (type & SENSOR_TYPE_MEMORY) return "memory"; - else if (type & SENSOR_TYPE_PCIE) + + if (type & SENSOR_TYPE_PCIE) return "PCIe"; - else if (type & SENSOR_TYPE_AMBIENT) + + if (type & SENSOR_TYPE_AMBIENT) return "ambient"; - else if (type & SENSOR_TYPE_TEMP) + + if (type & SENSOR_TYPE_TEMP) return "temp"; - else if (type & SENSOR_TYPE_FAN) - return "fan"; - else - return "unknown"; + + if (type & SENSOR_TYPE_FAN) { + if (type & SENSOR_TYPE_RPM) + return "fan rpm"; + + return "fan level"; + } + + return "unknown"; } static double get_usage(int id, int type) @@ -189,10 +214,15 @@ static double get_value(int id, int type) return get_att(NV_CTRL_TARGET_TYPE_GPU, id, att); } else if (type & SENSOR_TYPE_FAN) { - return get_att(NV_CTRL_TARGET_TYPE_COOLER, - id, - NV_CTRL_THERMAL_COOLER_SPEED); - } else { /* SENSOR_TYPE_USAGE */ + if (type & SENSOR_TYPE_RPM) + return get_att(NV_CTRL_TARGET_TYPE_COOLER, + id, + NV_CTRL_THERMAL_COOLER_SPEED); + else /* SENSOR_TYPE_PERCENT */ + return get_att(NV_CTRL_TARGET_TYPE_COOLER, + id, + NV_CTRL_THERMAL_COOLER_LEVEL); + } else { /* SENSOR_TYPE_PERCENT */ return get_usage(id, type); } } @@ -200,14 +230,18 @@ static double get_value(int id, int type) static void update(struct psensor *sensor) { double v; + int id; + + id = get_nvidia_id(sensor); - v = get_value(sensor->nvidia_id, sensor->type); + v = get_value(id, sensor->type); if (v == UNKNOWN_DBL_VALUE) - log_err(_("Failed to retrieve measure of type %x " + log_err(_("%s: Failed to retrieve measure of type %x " "for NVIDIA GPU %d"), + PROVIDER_NAME, sensor->type, - sensor->nvidia_id); + id); psensor_set_current_value(sensor, v); } @@ -222,7 +256,8 @@ static char *i2str(int i) size_t n; /* second +1 to avoid issue about the conversion of a double - * to a lower int */ + * to a lower int + */ n = 1 + (ceil(log10(INT_MAX)) + 1) + 1; str = malloc(n); @@ -238,6 +273,7 @@ static struct psensor *create_nvidia_sensor(int id, int subtype, int value_len) int type; size_t n; struct psensor *s; + double v; type = SENSOR_TYPE_NVCTRL | subtype; @@ -249,157 +285,118 @@ static struct psensor *create_nvidia_sensor(int id, int subtype, int value_len) stype = get_nvidia_type_str(type); n = strlen(pname) + 1 + strlen(strnid) + 1 + strlen(stype) + 1; - name = malloc(n); sprintf(name, "%s %s %s", pname, strnid, stype); - sid = malloc(strlen("nvidia") + 1 + strlen(name) + 1); - sprintf(sid, "nvidia %s", name); + sid = malloc(strlen(PROVIDER_NAME) + 1 + strlen(name) + 1); + sprintf(sid, "%s %s", PROVIDER_NAME, name); s = psensor_create(sid, name, pname, type, value_len); - s->nvidia_id = id; + s->provider_data = malloc(sizeof(int)); + set_nvidia_id(s, id); + + if ((type & SENSOR_TYPE_GPU) && (type & SENSOR_TYPE_TEMP)) { + v = get_att(NV_CTRL_TARGET_TYPE_GPU, + id, + NV_CTRL_GPU_CORE_THRESHOLD); + s->max = v; + } free(strnid); return s; } -static int init() +static int init(void) { int evt, err; display = XOpenDisplay(NULL); if (!display) { - log_err(_("Cannot open connection to X11 server.")); + log_err(_("%s: Cannot open connection to X11 server."), + PROVIDER_NAME); return 0; } if (XNVCTRLQueryExtension(display, &evt, &err)) return 1; - log_err(_("Failed to retrieve NVIDIA information.")); + log_err(_("%s: Failed to retrieve NVIDIA information."), + PROVIDER_NAME); return 0; } void nvidia_psensor_list_update(struct psensor **sensors) { - struct psensor **ss, *s; + struct psensor *s; - ss = sensors; - while (*ss) { - s = *ss; + while (*sensors) { + s = *sensors; - if (s->type & SENSOR_TYPE_NVCTRL) + if (!(s->type & SENSOR_TYPE_REMOTE) + && s->type & SENSOR_TYPE_NVCTRL) update(s); - ss++; + sensors++; } } static void add(struct psensor ***sensors, int id, int type, int values_len) { - struct psensor **tmp, *s; + struct psensor *s; s = create_nvidia_sensor(id, type, values_len); - if (s) { - tmp = psensor_list_add(*sensors, s); - free(*sensors); - *sensors = tmp; - } + if (s) + psensor_list_append(sensors, s); } -struct psensor ** -nvidia_psensor_list_add(struct psensor **ss, int values_len) +void nvidia_psensor_list_append(struct psensor ***ss, int values_len) { - int i, n, utype, rpm; + int i, n, utype; Bool ret; - char *str; if (!init()) - return ss; + return; ret = XNVCTRLQueryTargetCount(display, NV_CTRL_TARGET_TYPE_GPU, &n); if (ret == True) { for (i = 0; i < n; i++) { - add(&ss, + add(ss, i, SENSOR_TYPE_GPU | SENSOR_TYPE_TEMP, values_len); - utype = SENSOR_TYPE_GPU | SENSOR_TYPE_USAGE; - add(&ss, i, utype | SENSOR_TYPE_AMBIENT, values_len); - add(&ss, i, utype | SENSOR_TYPE_GRAPHICS, values_len); - add(&ss, i, utype | SENSOR_TYPE_VIDEO, values_len); - add(&ss, i, utype | SENSOR_TYPE_MEMORY, values_len); - add(&ss, i, utype | SENSOR_TYPE_PCIE, values_len); + utype = SENSOR_TYPE_GPU | SENSOR_TYPE_PERCENT; + add(ss, i, utype | SENSOR_TYPE_AMBIENT, values_len); + add(ss, i, utype | SENSOR_TYPE_GRAPHICS, values_len); + add(ss, i, utype | SENSOR_TYPE_VIDEO, values_len); + add(ss, i, utype | SENSOR_TYPE_MEMORY, values_len); + add(ss, i, utype | SENSOR_TYPE_PCIE, values_len); } } ret = XNVCTRLQueryTargetCount(display, NV_CTRL_TARGET_TYPE_COOLER, &n); if (ret == True) { - log_debug("NVIDIA: number of fans: %d", n); + log_fct("%s: Number of fans: %d", PROVIDER_NAME, n); for (i = 0; i < n; i++) { - ret = XNVCTRLQueryTargetAttribute - (display, - NV_CTRL_TARGET_TYPE_COOLER, - i, - 0, - NV_CTRL_THERMAL_COOLER_SPEED, &rpm); - if (ret == True) - log_debug("NVIDIA: fan speed %d %d", i, rpm); - else - log_err(_("NVIDIA: " - "failed to retrieve fan speed %d"), - i); - - ret = XNVCTRLQueryTargetAttribute - (display, - NV_CTRL_TARGET_TYPE_COOLER, - i, - 0, - NV_CTRL_THERMAL_COOLER_LEVEL, &rpm); - if (ret == True) - log_debug("NVIDIA: fan level %d %d", i, rpm); - else - log_err(_("NVIDIA: " - "failed to retrieve fan level %d"), - i); - - - add(&ss, i, SENSOR_TYPE_FAN, values_len); - } - } else { - log_err(_("NVIDIA: failed to retrieve number of fans.")); - } + utype = SENSOR_TYPE_FAN | SENSOR_TYPE_RPM; + if (check_sensor(i, utype)) + add(ss, i, utype, values_len); - ret = XNVCTRLQueryTargetCount(display, NV_CTRL_TARGET_TYPE_VCSC, &n); - if (ret == True) { - log_debug("NVIDIA: number of VCSC: %d", n); - for (i = 0; i < n; i++) { - ret = XNVCTRLQueryTargetStringAttribute - (display, - NV_CTRL_TARGET_TYPE_VCSC, - i, - 0, - NV_CTRL_STRING_VCSC_FAN_STATUS, &str); - if (ret == True) - log_debug("NVIDIA: vcsc fan %d %s", i, str); - else - log_err(_("NVIDIA: " - "failed to retrieve vcsc fan info %d"), - i); - - add(&ss, i, SENSOR_TYPE_FAN, values_len); + utype = SENSOR_TYPE_FAN | SENSOR_TYPE_PERCENT; + if (check_sensor(i, utype)) + add(ss, i, utype, values_len); } + } else { + log_err(_("%s: Failed to retrieve number of fans."), + PROVIDER_NAME); } - - return ss; } -void nvidia_cleanup() +void nvidia_cleanup(void) { if (display) { XCloseDisplay(display);