dev names: Add dm_device_get_name to acquire device name for given major:minor pair
PATCH 1/2 dev names: Add dm_device_get_name to acquire device name for given major:minor pair
The code to acquire device's kernel name using sysfs is already upstream, this is just a tiny refactor that exports this functionality as libdevmapper fn. In addition, it adds a possibility to read the device-mapper name from sysfs using given major:minor pair (which is a quick operation).
The new fn "int dm_device_get_name(uint32_t major, uint32_t minor, int prefer_kernel_name, char *buf, size_t buf_size)" has a "pefer_kernel_name" switch with which it's possible to prefer kernel "dm-X"
names over device-mapper names if this is a device-mapper device (for non-dm
devices, only kernel name is possible).
Note:
Since the /sys/block/major:minor/dm/name item was added later (kernel 2.6.29 iirc), there's a fallback to return kernel "dm-X" name if we're not able to get the dm name via sysfs (with some log_debug in place).
Peter
--- libdm/libdevmapper.h | 9 ++++ libdm/libdm-common.c | 122 ++++++++++++++++++++++++++++++++++++++++--------- 2 files changed, 108 insertions(+), 23 deletions(-)
libdm/libdevmapper.h +9 -0
@@ -267,6 +267,15 @@ const char *dm_sysfs_dir(void);int dm_is_dm_major (uint32_t major);/* +* Get device name for given major and minor number. If prefer_kernel_name +* is set, kernel name is preferred over dm name for dm devices. If sysfs +* is not used (or configured incorrectly), returns 0. +*/ +int dm_device_get_name (uint32_t major,uint32_t minor, +int prefer_kernel_name, +char *buf,size_t buf_size); + +/* * Determine whether a device has any holders (devices * using this device). If sysfs is not used (or configured * incorrectly), returns 0.
libdm/libdm-common.c +99 -23
137 lines not on this page · raw message
PATCH 1/2 dev names: Add dm_device_get_name to acquire device name for given major:minor pair
Dne 7.11.2011 13:49, Peter Rajnoha napsal(a):
Quoted 46 lines
The code to acquire device's kernel name using sysfs is already upstream, this is just a tiny refactor that exports this functionality as libdevmapper fn. In addition, it adds a possibility to read the device-mapper name from sysfs using given major:minor pair (which is a quick operation).
The new fn "int
dm_device_get_name(uint32_t major, uint32_t minor, int prefer_kernel_name, char *buf, size_t buf_size)" has a "pefer_kernel_name" switch with which it's possible to prefer kernel "dm-X"
names over device-mapper names if this is a device-mapper device (for non-dm
devices, only kernel name is possible).Note:
Since the /sys/block/major:minor/dm/name item was added later (kernel 2.6.29 iirc), there's a fallback to return kernel "dm-X" name if we're not able to get the dm name via sysfs (with somelog_debugin place).Peter
--- libdm/libdevmapper.h | 9 ++++ libdm/libdm-common.c | 122 ++++++++++++++++++++++++++++++++++++++++--------- 2 files changed, 108 insertions(+), 23 deletions(-)libdm/libdevmapper.h +9
-0@@ -267,6 +267,15 @@ const char *dm_sysfs_dir(void);int dm_is_dm_major (uint32_t major);/* +* Get device name for given major and minor number. If prefer_kernel_name +* is set, kernel name is preferred over dm name for dm devices. If sysfs +* is not used (or configured incorrectly), returns 0. +*/ +int dm_device_get_name (uint32_t major,uint32_t minor, +int prefer_kernel_name, +char *buf,size_t buf_size); + +/* * Determine whether a device has any holders (devices * using this device). If sysfs is not used (or configured * incorrectly), returns 0. libdm/libdm-common.c +0
-0
libdm/libdm-common.c const char *dm_sysfs_dir(void) · line 1065
Quoted 10 lines
libdm/libdm-common.c +7
-0@@ -1056,6 +1056,103 @@ const char *dm_sysfs_dir(void)return _sysfs_dir; } +static int _sysfs_get_dm_name (uint32_t major,uint32_t minor,char *buf,size_t buf_size) +{ +char sysfs_path[PATH_MAX ]; +char temp_buf[PATH_MAX ]; +FILE *fp; + + if (dm_snprintf(sysfs_path, PATH_MAX, "%sdev/block/%" PRIu32 ":%" PRIu32
I'd prefer to use 'sizeof(sysfs_path)' in these case - even though in this case it doesn't really matter.
Quoted 5 lines
libdm/libdm-common.c +5
-0+ "/dm/name", _sysfs_dir, major, minor) < 0) { +log_error ("_sysfs_get_dm_name: dm_snprintf failed" ); +return 0 ; + } +
libdm/libdm-common.c const char *dm_sysfs_dir(void) · line 1080
Quoted 10 lines
libdm/libdm-common.c +10
-0+if (!(fp =fopen (sysfs_path,"r" ))) { +if (errno !=ENOENT ) +log_sys_error ("fopen" , sysfs_path); +else +log_sys_debug ("fopen" , sysfs_path); +return 0 ; + } + +if (!fgets (temp_buf,sizeof (temp_buf), fp)) { +log_sys_debug ("fgets" , sysfs_path);
log_sys_error()
libdm/libdm-common.c const char *dm_sysfs_dir(void) · line 1081
Quoted 1 line
libdm/libdm-common.c +1
-0+return 0 ;
Well we should have 2 kinds of errors here - but since there is fallback, it's not that important.
libdm/libdm-common.c const char *dm_sysfs_dir(void) · line 1083
Quoted 2 lines
libdm/libdm-common.c +2
-0+ } + temp_buf[strlen (temp_buf) -1 ] ='\0' ;
Maybe we should check here, the character is really '\n' before removing it. But the behavior on the border PATH_MAX size might be tricky.
libdm/libdm-common.c const char *dm_sysfs_dir(void) · line 1093
Quoted 10 lines
libdm/libdm-common.c +10
-0+ +if (fclose (fp)) +log_sys_error ("fclose" , sysfs_path); + +if (buf_size <strlen (temp_buf) +1 ) { +log_error ("_sysfs_get_dm_name: output buffer too small" ); +return 0 ; + } + +strcpy (buf, temp_buf);
+newline
Quoted 44 lines
libdm/libdm-common.c +44
-0+return 1 ; +} + +static int _sysfs_get_kernel_name (uint32_t major,uint32_t minor,char *buf,size_t buf_size) +{ +char sysfs_path[PATH_MAX ]; +char temp_buf[PATH_MAX ]; +ssize_t size; +char *name; + +if (dm_snprintf (sysfs_path,PATH_MAX ,"%sdev/block/%" PRIu32":%" PRIu32, + _sysfs_dir, major, minor) <0 ) { +log_error ("_sysfs_get_kerne_name: dm_snprintf failed" ); +return 0 ; + } + +if ((size =readlink (sysfs_path, temp_buf,PATH_MAX )) <0 ) { +if (errno !=ENOENT ) +log_sys_error ("readlink" , sysfs_path); +else +log_sys_debug ("readlink" , sysfs_path); +return 0 ; + } + temp_buf[size] ='\0' ; + +if (!(name =strrchr (temp_buf,'/' ))) { +log_error ("Could not locate device kernel name in sysfs path %s" , temp_buf); +return 0 ; + } + name +=1 ; + +if (buf_size <strlen (name) +1 ) { +log_error ("_sysfs_get_kernel_name: output buffer too small" ); +return 0 ; + } + +strcpy (buf, name); +return 1 ; +} + +int dm_device_get_name (uint32_t major,uint32_t minor,int prefer_kernel_name, +char *buf,size_t buf_size) +{ +if (!*_sysfs_dir)
libdm/libdm-common.c const char *dm_sysfs_dir(void) · line 1147
Quoted 10 lines
libdm/libdm-common.c +10
-0+return 0 ; + +/* +* device-mapper devices and prefer_kernel_name = 0 +* get dm name by reading /sys/dev/block/major:minor/dm/name, +* fallback to _sysfs_get_kernel_name if not successful +*/ +if (dm_is_dm_major (major) && !prefer_kernel_name && +_sysfs_get_dm_name (major, minor, buf, buf_size)) +return 1 ;
+ stack; for fail case
Quoted 52 lines
libdm/libdm-common.c +10
-24+ +/* +* non-device-mapper devices or prefer_kernel_name = 1 +* get kernel name using readlink /sys/dev/block/major:minor -> .../dm-X +*/ +return _sysfs_get_kernel_name (major, minor, buf, buf_size); +} +int dm_device_has_holders (uint32_t major,uint32_t minor) {char sysfs_path[PATH_MAX ];@@ -1126,32 +1223,11 @@ static int _mounted_fs_on_device(const char *kernel_dev_name)int dm_device_has_mounted_fs (uint32_t major,uint32_t minor) { -char sysfs_path[PATH_MAX ]; -char temp_path[PATH_MAX ]; -char *kernel_dev_name; -ssize_t size; - -if (!*_sysfs_dir) -return 0 ; +char kernel_dev_name[PATH_MAX ];/* Get kernel device name first */ -if (dm_snprintf (sysfs_path,PATH_MAX ,"%sdev/block/%" PRIu32":%" PRIu32, - _sysfs_dir, major, minor) <0 ) { -log_error ("sysfs_path dm_snprintf failed" ); -return 0 ; - } - -if ((size =readlink (sysfs_path, temp_path,PATH_MAX )) <0 ) { -log_sys_error ("readlink" , sysfs_path); +if (!dm_device_get_name (major, minor,1 , kernel_dev_name,PATH_MAX ))return 0 ; - } - temp_path[size] ='\0' ; - -if (!(kernel_dev_name =strrchr (temp_path,'/' ))) { -log_error ("Could not locate device kernel name in sysfs path %s" , temp_path); -return 0 ; - } - kernel_dev_name +=1 ;/* Check /sys/fs/<fs_name>/<kernel_dev_name> presence */ return _mounted_fs_on_device (kernel_dev_name); --lvm-devel mailing list
lvm-devel at redhat.com
https://www.redhat.com/mailman/listinfo/lvm-devel