[gparted] Don't hang reading binary data from command output (#751251)



commit 4fce7cd5eed5b298215b57dc9b1ffd1aff2fe22a
Author: Mike Fleetwood <mike fleetwood googlemail com>
Date:   Fri Jun 26 12:30:16 2015 +0100

    Don't hang reading binary data from command output (#751251)
    
    With a Kobo Touch eReader connected via USB, GParted would hang when
    scanning the device with this error written to the terminal:
    
        $ sudo src/gpartedbin
        ======================
        libparted : 2.3
        ======================
    
        (gpartedbin:10261): glibmm-CRITICAL **:
        unhandled exception (type Glib::Error) in signal handler:
        domain: g_convert_error
        code  : 1
        what  : Invalid byte sequence in conversion input
    
    The hdparm command was printing binary data as the serial number.
    Fragment of the 'hdparm -I /dev/sdf' output:
    
        # hdparm -I /dev/sdf
    
        /dev/sdf:
        SG_IO: bad/missing sense data, sb[]:  70 00 05 00 00 00 00 0a 00 00 00 00 24 00 00 00 00 00 00 00 00 
00 00 00 00 00 00 00 00 00 00 00
    
        ATAPI Optical card reader/writer, with non-removable media
                Model Number:       {BINARY_DATA}
                Serial Number:      {BINARY_DATA}
                Firmware Revision:  {BINARY_DATA}
    
    GParted reads command output using the Glib::IOChannel class.  However
    by default an IOChannel performs character set conversion on the data it
    reads, so when it came across an invalid byte sequence in the binary
    data the above exception was raised and the IOChannel::read() method
    never returned.  Hence GParted became stuck reportedly scanning the
    same device forever.  Code fragment:
    
    src/PipeCapture.cc
        49  bool PipeCapture::OnReadable( Glib::IOCondition condition )
        50  {
        ...
        58          Glib::ustring str;
    >>  59          Glib::IOStatus status = channel->read( str, 512 );
        60          if (status == Glib::IO_STATUS_NORMAL)
        61          {
        62                  for( Glib::ustring::iterator s = str.begin(); s != str.end(); s++ )
    
    Quote from the IOChannel class reference:
        https://developer.gnome.org/glibmm/stable/classGlib_1_1IOChannel.html
    
        Note that IOChannels implement an automatic implicit character set
        conversion to the data stream, and usually will not pass by default
        binary data unchanged. To set the encoding of the channel, use
        e.g. set_encoding("ISO-8859-15"). To set the channel to no encoding,
        use set_encoding() without any arguments.
    
    Fix by disabling the automatic character set conversion in the IOChannel
    used to read output from executed commands.
    
    Bug 751251 - Show serial number in device information

 src/PipeCapture.cc |    1 +
 1 files changed, 1 insertions(+), 0 deletions(-)
---
diff --git a/src/PipeCapture.cc b/src/PipeCapture.cc
index 2b5d5f8..a19dbc9 100644
--- a/src/PipeCapture.cc
+++ b/src/PipeCapture.cc
@@ -25,6 +25,7 @@ PipeCapture::PipeCapture( int fd, Glib::ustring &string ) : buff( string ),
        // tie fd to string
        // make channel
        channel = Glib::IOChannel::create_from_fd( fd );
+       channel->set_encoding("");
 }
 
 void PipeCapture::connect_signal()


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]