Update parsing of btrfs filesystem show for multi-device membership (#733601)
This patch changes the reading of the btrfs multi-device membership to resolve issue 1/2 by ignoring the exit status from the 'btrfs filesystem show' command and relying on parsing the required information to determine success or failure. Bug #733601 - Btrfs: Warnings and missing label with btrfs-progs 3.12 and 3.14
This commit is contained in:
parent
422829ebff
commit
a4f761e290
46
src/btrfs.cc
46
src/btrfs.cc
|
@ -463,36 +463,35 @@ const BTRFS_Device & btrfs::get_cache_entry( const Glib::ustring & path )
|
||||||
if ( bd_iter != btrfs_device_cache .end() )
|
if ( bd_iter != btrfs_device_cache .end() )
|
||||||
return bd_iter ->second ;
|
return bd_iter ->second ;
|
||||||
|
|
||||||
int exit_status ;
|
|
||||||
Glib::ustring output, error ;
|
Glib::ustring output, error ;
|
||||||
std::vector<int> devid_list ;
|
std::vector<int> devid_list ;
|
||||||
std::vector<Glib::ustring> path_list ;
|
std::vector<Glib::ustring> path_list ;
|
||||||
if ( btrfs_found )
|
if ( btrfs_found )
|
||||||
exit_status = Utils::execute_command( "btrfs filesystem show " + path, output, error, true ) ;
|
Utils::execute_command( "btrfs filesystem show " + path, output, error, true ) ;
|
||||||
else
|
else
|
||||||
exit_status = Utils::execute_command( "btrfs-show " + path, output, error, true ) ;
|
Utils::execute_command( "btrfs-show " + path, output, error, true ) ;
|
||||||
if ( ! exit_status )
|
//In many cases the exit status doesn't reflect valid output or an error condition
|
||||||
|
// so rely on parsing the output to determine success.
|
||||||
|
|
||||||
|
//Extract devid and path for each device from output like this:
|
||||||
|
// Label: none uuid: 36eb51a2-2927-4c92-820f-b2f0b5cdae50
|
||||||
|
// Total devices 2 FS bytes used 156.00KB
|
||||||
|
// devid 2 size 2.00GB used 512.00MB path /dev/sdb2
|
||||||
|
// devid 1 size 2.00GB used 240.75MB path /dev/sdb1
|
||||||
|
Glib::ustring::size_type offset = 0 ;
|
||||||
|
Glib::ustring::size_type index ;
|
||||||
|
while ( ( index = output .find( "devid ", offset ) ) != Glib::ustring::npos )
|
||||||
{
|
{
|
||||||
//Extract devid and path for each device from output like this:
|
int devid = -1 ;
|
||||||
// Label: none uuid: 36eb51a2-2927-4c92-820f-b2f0b5cdae50
|
sscanf( output .substr( index ) .c_str(), "devid %d", &devid ) ;
|
||||||
// Total devices 2 FS bytes used 156.00KB
|
Glib::ustring devid_path = Utils::regexp_label( output .substr( index ),
|
||||||
// devid 2 size 2.00GB used 512.00MB path /dev/sdb2
|
"devid .* path (/dev/[[:graph:]]+)" ) ;
|
||||||
// devid 1 size 2.00GB used 240.75MB path /dev/sdb1
|
if ( devid > -1 && ! devid_path .empty() )
|
||||||
Glib::ustring::size_type offset = 0 ;
|
|
||||||
Glib::ustring::size_type index ;
|
|
||||||
while ( ( index = output .find( "devid ", offset ) ) != Glib::ustring::npos )
|
|
||||||
{
|
{
|
||||||
int devid = -1 ;
|
devid_list .push_back( devid ) ;
|
||||||
sscanf( output .substr( index ) .c_str(), "devid %d", &devid ) ;
|
path_list .push_back( devid_path ) ;
|
||||||
Glib::ustring devid_path = Utils::regexp_label( output .substr( index ),
|
|
||||||
"devid .* path (/dev/[[:graph:]]+)" ) ;
|
|
||||||
if ( devid > -1 && ! devid_path .empty() )
|
|
||||||
{
|
|
||||||
devid_list .push_back( devid ) ;
|
|
||||||
path_list .push_back( devid_path ) ;
|
|
||||||
}
|
|
||||||
offset = index + 5 ; //Next find starts immediately after current "devid"
|
|
||||||
}
|
}
|
||||||
|
offset = index + 5 ; //Next find starts immediately after current "devid"
|
||||||
}
|
}
|
||||||
//Add cache entries for all found devices
|
//Add cache entries for all found devices
|
||||||
for ( unsigned int i = 0 ; i < devid_list .size() ; i ++ )
|
for ( unsigned int i = 0 ; i < devid_list .size() ; i ++ )
|
||||||
|
@ -507,8 +506,7 @@ const BTRFS_Device & btrfs::get_cache_entry( const Glib::ustring & path )
|
||||||
if ( bd_iter != btrfs_device_cache .end() )
|
if ( bd_iter != btrfs_device_cache .end() )
|
||||||
return bd_iter ->second ;
|
return bd_iter ->second ;
|
||||||
|
|
||||||
//If "btrfs filesystem show" / "btrfs-show" commands not found, returned non-zero
|
//If for any reason we fail to parse the information return an "unknown" record
|
||||||
// exit status or failed to parse information return an "unknown" record
|
|
||||||
static BTRFS_Device btrfs_dev = { -1, } ;
|
static BTRFS_Device btrfs_dev = { -1, } ;
|
||||||
return btrfs_dev ;
|
return btrfs_dev ;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue