Шеллкод в C - Что это значит?

Я действительно не понимаю, как этот код делает то, что он делает:

char shellcode[] = "\xbb\x00\x00\x00\x00"           
                   "\xb8\x01\x00\x00\x00"                  
                   "\xcd\x80";                  

int main()
{
    int *ret;
    ret = (int *)&ret + 2;
    (*ret) = (int)shellcode;
}

Хорошо, я знаю:

int *ret;

устанавливает указатель на int. и:

ret = (int *)&ret + 2;

задает адрес ret и 2 байта (я думаю.)

Но я не понимаю, что это значит:

(int *)&ret

Я знаю, что означает &ret, а не то, что означает (int *)&ret. Кроме того, как он выполняет шеллкод, назначая значение shellcode на ret?

UPDATE: В чем разница между:

(int *)&ret  + 2

и

&ret + 2

Ответы

Ответ 1

"string" shellcode содержит некоторый машинный код.

int *ret; определяет переменную ret, которая является указателем на int.

Назначение ret = (int *)&ret + 2; означает, что ret указывает на местоположение размером два int из своего собственного фактического местоположения (или адреса); это адрес в стеке, предположительно, где обратный адрес функции (main()) сохраняется в стеке.

Назначение *ret = (int)shellcode; присваивает адрес кода оболочки обратному адресу. Поэтому, когда функция main() завершается, обратный адрес - это код оболочки, который делает все, что он делает, вместо обычного выхода из программы.

Отбрасывает множество грехов. Код делает большое количество неперспективных предположений, которые, вероятно, оправданы в целевой среде, но не обязательно в другом месте.


Какая разница между: &ret+2 и (int *)&ret + 2?

Тип, в основном; это одно из множества грехов, упомянутых ранее. &ret имеет тип int ** (указатель на указатель на int) вместо int *, который является типом ret. Поскольку sizeof(int *) == sizeof(int **) на всех реальных машинах, приведение просто подавляет жалобу от компилятора (о назначении неправильного типа указателя на ret) без изменения числового результата.