[gdb] podmiana funckji w trakcie debugowania

0

Cześć,
kojarzy ktoś czy można jakoś podmienić funkcje w gdb?

cos w stylu

(gdb) print exit
$5 = {<text variable, no debug info>} 0xf6b777a0 <exit>
(gdb) whatis exit
type = <text variable, no debug info>
(gdb) print sleep
$6 = {<text variable, no debug info>} 0xf76daa4b <sleep>
(gdb) set *0xf6b777a0=0xf76daa4b

EDIT:
przykładowy kod

void foo() {
   std::cout << "hello" << std::endl;
   sleep(1);
   exit(1);
   std::cout << "hello" << std::endl;
   return;
}

chciałbym jakoś pozbyć się tego exit by funkcja wypisała hello\nworld i pomyślałem,
że jak przypisze adresowi funcji exit inną funckcję (np. sleep) to pozbędę się exit'a.
ale set *0xf6b777a0=0xf76daa4b nie zadziałał ;/

1

Takie nadpisanie to mógłbyś zrobic jakbyś skompilował to bez RELRO, bo teraz pewnie masz GOT które jest read-only i nie da się tego adresu nadpisać. Zresztą i to miałoby sens tylko dla funkcji z jakiejś biblioteki dynamicznej, tak że adres jest resolvwowany później. Dla wielu funkcji adres będzie przecież inline w kodzie, a .text też sobie nie możesz nadpisać żeby zmienić kod.

Napisz może jednak co chcesz osiągnąć, bo to co robisz jest bardzo dziwne.

0

@Shalom: dzięki za jump'a! Sprawdziłem kilka scenariuszy i faktycznie udało mi się przeskoczyć wywoałnie zwykłej funkcji b +1; jump +1,
ale jeśli ta funckja to exit to tak jakby kod który jest po exit jest wycinany i nie ma go w binarce, nie można do niego skoczyć ;/
Kojarzysz czy można to jakoś obejść?
Kompiluje komendą g++ -O0 -g main.cpp

#include <iostream>
#include <unistd.h>
 
void boo(int a) {
    std::cout << "boo" << std::endl;
 
}
 
void foo() {
    std::cout << "hello" << std::endl;
    sleep(1);
    exit(1); // with boo(); I can jump over it, but with exit() I cannot
    std::cout << "world" << std::endl; // this line is not available when previous line calls exit function
    return ;
}
 
int main(int argc, char *argv[]) {
    foo();
    std::cout << "after foo" << std::endl;
 
    return 0;
}

EDIT: dodaje output z gdb

->  12       exit(1); // with boo(); I can jump over it, but with exit() I cannot
     13      std::cout << "world" << std::endl; // this line is not available when previous line calls exit function
     14      return ;
     15  }
     16
     17  int main(int argc, char *argv[]) {
------------------------------------------------------------------
gef> b +1
Breakpoint 2 at 0x4008af: file main.cpp, ******line 18.******

break jest ustawiany na lini 18'tej podczas gdy powinien być na 13'tej.

2

No ciężko trochę, bo dead code zwykle po prostu wylatuje z binarki i tyle. Obawiam sie że może być trudno temu zapobiec. Popatrz sobie na godbolta albo deasembluj binarkę i zobaczysz co faktycznie "zostaje" w kodzie.

2

To jest trochę szeroki temat z tym usuwaniem dead code'u. Możesz kombinować z -fno-dce i podobnymi, jednakże: https://stackoverflow.com/a/39835400/4885321
Exit jest funkcją o tyle specyficzną, że jest ona (z reguły) explicite oznaczona jako "noreturn", więc kompilator dostaje jasną informację, że potem ma już nic nie być.

1 użytkowników online, w tym zalogowanych: 0, gości: 1