diff --git a/src/rex-edid.c b/src/rex-edid.c index e00a826..87ae015 100644 --- a/src/rex-edid.c +++ b/src/rex-edid.c @@ -22,6 +22,7 @@ #include #include #include +#include #define REX_EDID_VERSION_MAJ 0u #define REX_EDID_VERSION_MIN 2u @@ -189,102 +190,103 @@ int rex_edid_xrandr(void){ return 0; } -/*get device name from DEVPATH environment variable and prepend '/sys' to it*/ -char* get_device_path(int* len){ - char* devpath; - int length; - char* tmp; - - /*udev stores the device location in sysfs in DEVPATH environment variable*/ - devpath = getenv("DEVPATH"); - if(!devpath) - return NULL; - length = strlen(devpath) + 5; - tmp = malloc(length); - if(!tmp) - return NULL; - tmp[length-1] = 0; - - snprintf(tmp, length, "/sys%s", devpath); - if(len) - *len = length-1; - return tmp; -} - -/*extract device name from the device path (the last part of the pathname)*/ -char* get_device_name(char* devpath, int strlength){ - int i; - for(i = strlength-1;i >= 0;--i){ - if(devpath[i] == '/'){ - if(i == strlength) - return NULL; - return &(devpath[i])+1; - } +char** add_interface(char* str, size_t slen, char** list, size_t cap, size_t len){ + if(len >= cap){ + list = realloc(list, cap*2 * sizeof(char*)); } - return NULL; + list[len] = malloc(slen+1); + strncpy(list[len], str, slen); + list[len][slen] = 0; + return list; +} +void free_int_list(char** list, size_t len){ + for(size_t i = 0;i < len;++i) + free(list[i]); + free(list); } int rex_edid_sysfs(void){ - int devpath_len; /*length of device path name*/ int devname_len; /*length of device name*/ - char* devpath; /*name of device path*/ char* devname; /*name of the device*/ + char** dev_int_names = malloc(sizeof(char*)); /*name of device interfaces*/ + size_t num_names = 0; + size_t names_size = 1; DIR* dp; /*pointer to open device directory in sysfs*/ struct dirent* dir; /*accessor to sysfs directory*/ /*set up device names*/ - devpath = get_device_path(&devpath_len); - if(!devpath){ - fprintf(stderr, "DEVPATH is empty!\n"); - return -3; - } - devname = get_device_name(devpath, devpath_len); - devname_len = strlen(devname); - - /*open directory*/ - dp = opendir(devpath); + dp = opendir("/sys/class/drm"); if(!dp){ - fprintf(stderr, "Unable to open DEVPATH!\n"); + fprintf(stderr, "Unable to open device path!\n"); return -2; } - - /*check all contents of device directory*/ while((dir = readdir(dp))){ - if(!strncmp(dir->d_name, devname, devname_len)){ - int edid_len; /*length of full path to edid file*/ - char* edid_file; /*buffer for edid path name*/ - unsigned char c; /*place to store char from file*/ - - /*set up edid file path*/ - edid_len = strlen(dir->d_name)+1 + devpath_len + 6; - edid_file = malloc(edid_len); - snprintf(edid_file, edid_len, "%s/%s/edid", devpath, dir->d_name); - printf("%s:", dir->d_name + devname_len+1); - - /*read in edid data from file*/ - FILE* fd = fopen(edid_file, "r"); - if(!fd){ - fprintf(stderr, "Unable to open edid file\n"); - free(edid_file); - printf("\n"); - continue; + if(!strncmp(dir->d_name, "card", 4)){ + size_t l = strlen(dir->d_name); + int add = 1; + for(size_t i = 4;i < l;++i){ + if(dir->d_name[i] == '-'){ + add = 0; + } } - - c = fgetc(fd); - while(!feof(fd)){ - printf("%02x", c); - c = fgetc(fd); + if(add){ + dev_int_names = add_interface(dir->d_name, l, dev_int_names, names_size, num_names); + ++num_names; } - - /*cleanup*/ - fclose(fd); - free(edid_file); - printf("\n"); } } - closedir(dp); - free(devpath); + + chdir("/sys/class/drm"); + + for(size_t i = 0;i < num_names;++i){ + devname = dev_int_names[i]; + devname_len = strlen(devname); + + /*open directory*/ + dp = opendir(devname); + if(!dp){ + fprintf(stderr, "Unable to open %s!\n", devname); + continue; + } + + /*check all contents of device directory*/ + while((dir = readdir(dp))){ + if(!strncmp(dir->d_name, devname, devname_len)){ + int edid_len; /*length of full path to edid file*/ + char* edid_file; /*buffer for edid path name*/ + unsigned char c; /*place to store char from file*/ + + /*set up edid file path*/ + edid_len = strlen(dir->d_name)+6; + edid_file = malloc(edid_len); + snprintf(edid_file, edid_len, "%s/edid", dir->d_name); + printf("%s:", dir->d_name + devname_len+1); + + /*read in edid data from file*/ + FILE* fd = fopen(edid_file, "r"); + if(!fd){ + fprintf(stderr, "Unable to open edid file\n"); + free(edid_file); + continue; + } + + c = fgetc(fd); + while(!feof(fd)){ + printf("%02x", c); + c = fgetc(fd); + } + + /*cleanup*/ + fclose(fd); + free(edid_file); + printf("\n"); + } + } + + closedir(dp); + } + free_int_list(dev_int_names, num_names); return 0; }