diff options
author | Burt P <pburt0@gmail.com> | 2018-09-08 15:23:38 -0500 |
---|---|---|
committer | Leandro A. F. Pereira <leandro@hardinfo.org> | 2018-09-26 20:51:53 -0700 |
commit | 62964b789d933e68e4024e165b20288471a0029c (patch) | |
tree | 8a0f017d06e2eda097cbe51c5eb63f359517ab28 /hardinfo/gpu_util.c | |
parent | 49a4c95c6dd6bfa5815c4ebccb1758b0e3268a94 (diff) |
dt gpu: find gpu in the device tree
Will now look for any .../gpu and .../gpu@<address> instead of
looking only at /soc/gpu.
Signed-off-by: Burt P <pburt0@gmail.com>
Diffstat (limited to 'hardinfo/gpu_util.c')
-rw-r--r-- | hardinfo/gpu_util.c | 78 |
1 files changed, 76 insertions, 2 deletions
diff --git a/hardinfo/gpu_util.c b/hardinfo/gpu_util.c index fb37c0cb..2c89be72 100644 --- a/hardinfo/gpu_util.c +++ b/hardinfo/gpu_util.c @@ -179,6 +179,60 @@ static void make_nice_name(gpud *s) { } +/* Look for this kind of thing: + * * /soc/gpu + * * /gpu@ff300000 + * + * Usually a gpu dt node will have ./name = "gpu" + */ +static gchar *dt_find_gpu(dtr *dt, char *np) { + gchar *dir_path, *dt_path, *ret; + gchar *ftmp, *ntmp; + const gchar *fn; + GDir *dir; + dtr_obj *obj; + + /* consider self */ + obj = dtr_obj_read(dt, np); + dt_path = dtr_obj_path(obj); + ntmp = strstr(dt_path, "/gpu"); + if (ntmp) { + /* was found in node name */ + if ( strchr(ntmp+1, '/') == NULL) { + ftmp = ntmp + 4; + /* should either be NULL or @ */ + if (*ftmp == '\0' || *ftmp == '@') + return g_strdup(dt_path); + } + } + + /* search children ... */ + dir_path = g_strdup_printf("%s/%s", dtr_base_path(dt), np); + dir = g_dir_open(dir_path, 0 , NULL); + if (dir) { + while((fn = g_dir_read_name(dir)) != NULL) { + ftmp = g_strdup_printf("%s/%s", dir_path, fn); + if ( g_file_test(ftmp, G_FILE_TEST_IS_DIR) ) { + if (strcmp(np, "/") == 0) + ntmp = g_strdup_printf("/%s", fn); + else + ntmp = g_strdup_printf("%s/%s", np, fn); + ret = dt_find_gpu(dt, ntmp); + g_free(ntmp); + if (ret != NULL) { + g_free(ftmp); + g_dir_close(dir); + return ret; + } + } + g_free(ftmp); + } + g_dir_close(dir); + } + + return NULL; +} + gpud *dt_soc_gpu() { static const char std_soc_gpu_drm_path[] = "/sys/devices/platform/soc/soc:gpu/drm"; @@ -197,16 +251,31 @@ gpud *dt_soc_gpu() { { "brcm,bcm2837-vc4", "Broadcom", "VideoCore IV" }, { "brcm,bcm2836-vc4", "Broadcom", "VideoCore IV" }, { "brcm,bcm2835-vc4", "Broadcom", "VideoCore IV" }, + { "arm,mali-450", "ARM", "Mali 450" }, + { "arm,mali", "ARM", "Mali family" }, { NULL, NULL } }; + char *dt_gpu_path = NULL, *compat_path = NULL; char *compat = NULL; char *vendor = NULL, *device = NULL; int i; gpud *gpu = NULL; - compat = dtr_get_string("/soc/gpu/compatible", 1); - if (compat == NULL) return NULL; + dtr *dt = dtr_new(NULL); + if (!dtr_was_found(dt)) + goto dt_gpu_end; + + dt_gpu_path = dt_find_gpu(dt, "/"); + + if (dt_gpu_path == NULL) + goto dt_gpu_end; + + compat_path = g_strdup_printf("%s/compatible", dt_gpu_path); + compat = dtr_get_string(compat_path, 1); + + if (compat == NULL) + goto dt_gpu_end; gpu = gpud_new(); @@ -233,6 +302,11 @@ gpud *dt_soc_gpu() { if (device) gpu->device_str = strdup(device); make_nice_name(gpu); + +dt_gpu_end: + free(dt_gpu_path); + free(compat_path); + dtr_free(dt); return gpu; } |