[gparted] Prevent assert failure from OperationDelete::get_partition_new() (#767233)



commit 3daf73a01b6c2853c0f12d8c7b0e17cfee952971
Author: Mike Fleetwood <mike fleetwood googlemail com>
Date:   Sat Jun 4 13:03:16 2016 +0100

    Prevent assert failure from OperationDelete::get_partition_new() (#767233)
    
    Composing these operations caused GParted to abort on an assert failure:
    (1) Delete an existing partition,
    (2) Create a new partition,
    (3) Delete new partition.
    
    This is the equivalent issue as fixed in the previous commit, except with
    the delete operation rather than the check operation:
        Prevent assert failure from OperationCheck::get_partition_new() (#767233)
    
        # ./gpartedbin
        ======================
        libparted : 2.4
        ======================
        **
        ERROR:OperationDelete.cc:41:virtual GParted::Partition& 
GParted::OperationDelete::get_partition_new(): assertion failed: (false)
        Aborted (core dumped)
    
        # gdb ./gpartedbin core.19232 --batch --quiet --ex backtrace -ex quit
        [New Thread 19232]
        [New Thread 19234]
        [Thread debugging using libthread_db enabled]
        Core was generated by `./gpartedbin'.
        Program terminated with signal 6, Aborted.
        #0  0x000000361f2325e5 in raise (sig=6) at ../nptl/sysdeps/unix/sysv/linux/raise.c:64
        64        return INLINE_SYSCALL (tgkill, 3, pid, selftid, sig);
        #0  0x000000361f2325e5 in raise (sig=6) at ../nptl/sysdeps/unix/sysv/linux/raise.c:64
        #1  0x000000361f233dc5 in abort () at abort.c:92
        #2  0x0000003620a67324 in g_assertion_message (domain=<value optimized out>, file=<value optimized 
out>, line=<value optimized out>, func=0x50fcc0 "virtual GParted::Partition& 
GParted::OperationDelete::get_partition_new()", message=0x1b55f60 "assertion failed: (false)") at 
gtestutils.c:1358
        #3  0x0000003620a678f0 in g_assertion_message_expr (domain=0x0, file=0x50fa68 "OperationDelete.cc", 
line=41, func=0x50fcc0 "virtual GParted::Partition& GParted::OperationDelete::get_partition_new()", 
expr=<value optimized out>) at gtestutils.c:1369
        #4  0x000000000049aa0d in GParted::OperationDelete::get_partition_new (this=0x1b321b0) at 
OperationDelete.cc:41
        #5  0x00000000004c6700 in GParted::Win_GParted::activate_delete (this=0x7ffc91403670) at 
Win_GParted.cc:2068
        ...
    
    As before the crash is happened in Win_GParted::activate_delete() as it
    was going through the list of operations removing those which applied to
    the never created partition.  It came across the delete operation of an
    existing partition and called get_partition_new().  As partition_new was
    not set or used by the delete operation this asserted false and crashed
    GParted.
    
    Unlike the check operation case, the delete operation doesn't have a
    partition afterwards.  (As GParted represents unallocated space with
    partition objects then the delete operation could be populated with a
    new partition by constructing the correctly merged unallocated space
    partition object, but that is what OperationDelete::apply_to_visual()
    does and having a place holder doesn't seem like the right thing to do).
    Instead exclude delete operations, on existing partitions, when looking
    for operations applying to this not yet created partition as they are
    mutually exclusive.
    
    Bug 767233 - GParted core dump on assert failure in
                 OperationDelete::get_partition_new()

 src/Win_GParted.cc |    8 +++++---
 1 files changed, 5 insertions(+), 3 deletions(-)
---
diff --git a/src/Win_GParted.cc b/src/Win_GParted.cc
index 27bd45b..57b1df5 100644
--- a/src/Win_GParted.cc
+++ b/src/Win_GParted.cc
@@ -2065,14 +2065,16 @@ void Win_GParted::activate_delete()
        {
                //remove all operations done on this new partition (this includes creation)     
                for ( int t = 0 ; t < static_cast<int>( operations .size() ) ; t++ ) 
-                       if ( operations[t]->get_partition_new().get_path() == 
selected_partition_ptr->get_path() )
+                       if ( operations[t]->type                           != OPERATION_DELETE                
   &&
+                            operations[t]->get_partition_new().get_path() == 
selected_partition_ptr->get_path()    )
                                remove_operation( t-- ) ;
                                
                //determine lowest possible new_count
                new_count = 0 ; 
                for ( unsigned int t = 0 ; t < operations .size() ; t++ )
-                       if ( operations[t]->get_partition_new().status           == STAT_NEW  &&
-                            operations[t]->get_partition_new().partition_number >  new_count    )
+                       if ( operations[t]->type                                 != OPERATION_DELETE &&
+                            operations[t]->get_partition_new().status           == STAT_NEW         &&
+                            operations[t]->get_partition_new().partition_number >  new_count           )
                                new_count = operations[t]->get_partition_new().partition_number;
                        
                new_count += 1 ;


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