ReverseEngineering
1.32K subscribers
50 photos
11 videos
108 files
895 links
Download Telegram
خب حالا میخام نظر همه تون رو بدونم راجب اینجوری توضیح دادن چطوره خوبه یا چی؟

So now I want to know everyone's opinion on explaining this way, is it good or not?
Anonymous Poll
66%
Yes 😂
34%
No 👎🏻
👏1
ReverseEngineering
خب حالا میخام نظر همه تون رو بدونم راجب اینجوری توضیح دادن چطوره خوبه یا چی؟

So now I want to know everyone's opinion on explaining this way, is it good or not?
بطور اضافیه این توضیح خودمون رو همیشه داریم این اضافه است اونم برای بعضی از توضیحات

Additionally, we always have this explanation of our own. This is an addition, and that's for some explanations.
❤4👍1
Forwarded from BlackOnion
❤2👍2
بخش شونزدهم بافر اورفلو


کشف بافر اورفلو در مهندسی معکوس با ابزارهای IDA و Ghidra و r2


توضیح:

توی این بخش یاد میگیریم وقتی یک باینری دستمون میاد چطور بفهمیم توش بافر اورفلو هست یا نه یعنی بدون داشتن سورس و فقط با آنالیز تابع‌ ها ورودی‌ های خطرناک و مسیرهای حساس رو پیدا میکنیم و فقط بررسی باینری انجام میدیم

قدم اول

تشخیص توابع خطرناک در باینری این یکی از سریعترین روش‌ هاست

ایده ساده:

اگه جایی تابع‌ هایی مثل strcpy sprintf gets memcpy بدون سایز مشخص وجود داشته باشه احتمال بافر اورفلو زیاده

توضیح فایل:

ما از یک باینری ساده برای آموزش استفاده میکنیم که توش strcpy و gets استفاده شده تا فقط مفهوم کشف آسیب‌پذیری رو تمرین کنیم
file10_copy_data.c

C

#include <stdio.h>
#include <string.h>

void read_name() {
    char name[32];
    gets(name);
    printf("hello %s\n", name);
}

void copy_data(char *s) {
    char buf[16];
    strcpy(buf, s);
    puts("done copy");
}

int main(int argc, char **argv) {
    if (argc > 1)
        copy_data(argv[1]);
    read_name();
    return 0;
}


قدم دوم

باز کردن باینری در IDA یا Ghidra
وقتی فایل رو داخل IDA باز میکنید دنبال اسک توابع خطرناک بگردید

مثال ساده:

اگه توی view functions ببینید gets یا strcpy هست همین خودش یک خطره
بعد برید داخل خود تابع و نگاه کنید سایز بافر چقدره و ورودی از کجا میاد

نکته:


وقتی دیدید strcpy(buf s) و buf اندازه ثابت داره ولی طول s از ورودی کاربر میاد خیلی احتمال بافر اورفلو هست
این الگو یکی از کلاسیک ترین نشونه هاست


قدم سوم

دیدن فریم تابع و محل بافر توی disassembly دنبال دستوراتی مثل


sub rsp, 0x20
push rbp
mov rbp, rsp


بگردید اینا مکان ساختن فضای لوکال روی استک رو نشون میدن

مثال ساده:

نمایش اسمبلی تابع copy_data وقتی disassemble کنیم تقریبا چیزی شبیه این میبینیم

Asm

push rbp
mov rbp, rsp
sub rsp, 0x20
mov rax, rdi
lea rdx, [rbp-0x10]
mov rsi, rax
call strcpy

توضیح کد زیر

اینجا واضح میبینید که بافر 16 بایته چون از rbp تا rbp-0x10 فاصله داره
و چون strcpy هیچ چک طولی نمیکنه اگه ورودی طولانی بیاد استک میتونه خراب بشه


مرحله چهارم

چک کردن مسیر ورودی کاربر این خیلی مهمه
اگه ورودی مستقیم از argv یا fgets یا read یا gets گرفته بشه و همون مستقیم به strcpy بره آسیب‌ پذیری تقریبا قطعی میشه هر ورودی = نگاه دقیق


مرحله پنجم

تایید آسیب‌پذیری
تو این مرحله فقط یک کاری میکنیم که امن باشه
فقط ورودی خیلی بلند اجرا میکنیم تا ببینیم برنامه کرش میکنه یا نه
نه نیاز به محاسبه آفست هست نه اجرای کدی
فقط تایید وجود مشکل

نمونه خط اجرا
Bash


./a.out $(python3 -c "print('A'*200)")


اگر برنامه کرش کرد یعنی تشخیص ما درست بوده


برای تمرین برید دنبال فانکشن دیگه ای داخل همین باینری و سعی کنید آنالیز کنید که آیا اون تابع هم قابل سو استفاده هست یا نه
این تمرین باعث میشه کم کم چشمتون به الگوها عادت کنه



Part 16 Buffer Overflow


Discovering Buffer Overflow in Reverse Engineering with IDA, Ghidra, and R2 Tools

Explanation:

In this section, we will learn how to find out if a binary has a buffer overflow when we get it, that is, without having the source and only by analyzing the functions, we will find dangerous inputs and sensitive paths and we will only check the binary

Step 1

Detecting dangerous functions in the binary This is one of the fastest methods

Simple idea:

If there are functions like strcpy sprintf gets memcpy without a specified size, the probability of buffer overflow is high

File description:

We will use a simple binary for training in which strcpy and gets are used to practice the concept of vulnerability discovery
file10_copy_data.c

C

#include <stdio.h>
#include <string.h>

void read_name() {
    char name[32];
    get(name);
    printf("hello %s\n", name);
}

void copy_data(char *s) {
    char buf[16];
    strcpy(buf, s);
    puts("done copy");
}

int main(int argc, char **argv) {
    if (argc > 1)
        copy_data(argv[1]);
    read_name();
    return 0;
}


Step 2

Opening the binary in IDA or Ghidra
When you open the file in IDA, look for dangerous function scripts

Simple example:

If you see gets or strcpy in the view functions, that is a danger in itself

Then go into the function itself and see what is the buffer size and where the input comes from

Note:
❤1
When you see strcpy(buf s) and buf has a fixed size but the length s comes from the user input, it is very likely a buffer overflow

This pattern is one of the most classic signs

Step 3

See the function frame and the buffer location in the disassembly. Look for commands like

sub rsp, 0x20
push rbp
mov rbp, rsp


These show where local space is created on the stack

Simple example:

Showing the assembly of the copy_data function When we disassemble, we see something like this

Asm

push rbp
mov rbp, rsp
sub rsp, 0x20
mov rax, rdi
lea rdx, [rbp-0x10]
mov rsi, rax
call strcpy


Explanation of the code below

Here you can clearly see that the buffer is 16 bytes because it is from rbp to rbp-0x10
And since strcpy does not do any length check, if the input is long, the stack can be corrupted

Step 4

Checking the user input path This is very important
If the input is taken directly from argv or fgets or read or gets and goes directly to strcpy, the vulnerability is almost certain. Every input = close look

Step 5

Confirming the vulnerability
In this step, we only do one thing that is safe
We only execute very long input to see if the program crashes
No need to calculate the offset, no code execution
Just confirm the existence of the problem

Example execution line
Bash

./a.out $(python3 -c "print('A'*200)")


If the program crashes, it means our diagnosis was correct

For practice, look for another function in the same binary and try to analyze whether that function can also be exploited or not
This exercise will gradually get your eyes used to the patterns

@reverseengine
❤2
PPID Spoofing

PPID

هر پروسه در ویندوز یک Parent Process ID (PPID) دارد که نشون میده توسط چه پروسه‌ ای ایجاد شده

مثال:

explorer.exe
notepad.exe


در اینجا explorer.exe والد (Parent) و notepad.exe فرزند (Child) هست

چرا تحلیل PPID مهم است؟

ابزارهای امنیتی از رابطه والد و فرزند برای شناسایی رفتار های غیر عادی استفاده میکنن

مثلا:
winword.exe  powershell.exe
cmd.exe


یا:

excel.exe
rundll32.exe


این زنجیره‌ ها میتونن برای تیم امنیتی مشکوک باشن


هدف مهاجمان از PPID Spoofing چیست؟

بعضی حملات مهاجم تلاش میکنن رابطه والد-فرزند رو طوری نمایش دهد که فعالیتش عادی به نظر برسد

هدف معمولا:

مخفی کردن مرکز واقعی اجرای یک پروسه
پیچیده‌تر کردن تحلیل Incident Response

دشوارتر کردن Threat Hunting

روش‌های تشخیص

تیم‌های دفاعی معمولا فقط به PPID اعتماد نمیکنن و موارد زیر رو نیز بررسی میکنن

1 Command Line Analysis

بررسی آرگومان‌ های اجرا شده

مثال:

explorer.exe powershell.exe

EncodedCommand


2 Image Path Analysis

بررسی مسیر فایل اجرایی
مثال:


C:\Users\Public\svchost.exe



به شدت مشکوکه

3 Behavioral Correlation

بررسی:
ایجاد Thread
دسترسی به حافظه سایر پروسه‌ها
بارگذاری DLLهای غیرعادی
ارتباطات شبکه
4 Sysmon Logging

ابزارهایی مثل:

میتونن روابط والد-فرزند رو ثبت و تحلیل کنن

Indicator
های رایج برای Threat Hunting


winword.exe → powershell.exe
excel.exe → cmd.exe
outlook.exe → rundll32.exe
wscript.exe → powershell.exe
mshta.exe → cmd.exe


راهکار های دفاعی

فعال‌سازی Sysmon و جمع‌آوری Eventهای Process Creation

مانیتور کردن Parent/Child Relationship

استفاده از EDR برای Behavioral Detection

ساخت Detection Rule برای زنجیره‌ های غیرعادی

Threat Hunting
بر اساس Process Tree




PPID Spoofing

PPID

Every process in Windows has a Parent Process ID (PPID) that indicates which process created it

Example:

explorer.exe

notepad.exe


Here explorer.exe is the parent and notepad.exe is the child

Why is PPID analysis important?

Security tools use the parent-child relationship to identify abnormal behavior

For example:

winword.exe powershell.exe

cmd.exe



Or:

excel.exe

rundll32.exe


These chains can be suspicious to the security team

What is the attackers’ goal with PPID Spoofing?


Some attackers attempt to disguise the parent-child relationship in a way that makes it look normal

Usually aim to:

Hide the true center of a process' execution

Make Incident Response analysis more complex

Make Threat Hunting more difficult

Detection methods

Defense teams usually do not rely only on PPID and also check the following:

1 Command Line Analysis

Check the arguments executed

Example:

explorer.exe powershell.exe


EncodedCommand

2 Image Path Analysis

Check the path of the executable file

Example:

C:\Users\Public\svchost.exe


Highly suspicious

3 Behavioral Correlation

Check:
Thread creation

Access to memory of other processes

Loading unusual DLLs

Network communications

4 Sysmon Logging

Tools such as:

Can record and analyze parent-child relationships

Common Indicators for Threat Hunting

winword.exe → powershell.exe
excel.exe → cmd.exe
outlook.exe → rundll32.exe
wscript.exe → powershell.exe
mshta.exe → cmd.exe


Defense Solutions

Enabling Sysmon and Collecting Process Creation Events

Monitoring Parent/Child Relationship

Using EDR for Behavioral Detection

Building Detection Rules for Abnormal Chains

Threat Hunting
Based on Process Tree


@reverseengine
❤1
برای درک اینکه یک فرآیند چیه باید وضعیت دستگاه رو درک کنیم:

یک برنامه هنگام اجرا چه چیزی رو میتونه بخونه یا اپدیت کنه

در هر زمان چه بخش‌هایی از دستگاه برای اجرای این برنامه مهمن؟

یکی از اجزای بارز وضعیت دستگاه که یک فرآیند رو تشکیل میده حافظه اونه

دستورالعمل‌ ها در حافظه قرار دارن داده‌ هایی که برنامه در حال اجرا میخونه و مینویسه هم در حافظه قرار دارن پس حافظه‌ ای که فرآیند میتونه به اون آدرس بده به اسم فضای آدرس اونه بخشی از فرآینده


همچنین بخشی از وضعیت دستگاه فرآیند رجیستر ها هستن بیشتر دستور العمل‌ها به درستی رجیستر ها رو میخونن یا اپدیت می‌
کنن پس به وضوح برای اجرای فرآیند مهمن توجه داشته باشید که برخی رجیسترهای خاص وجود دارند که بخشی از این حالت ماشین رو تشکیل میدن

مثال:

شمارنده برنامه (PC) (که بعضی وقتا اشاره‌ گر دستورالعمل یا IP بهش میگن



To understand what a process is we need to understand the state of the machine:

What can a program read or update while it is running?

What parts of the machine are important to the execution of the program at any given time?

One of the most obvious components of the machine state that makes up a process is its memory

Instructions are in memory The data that the program reads and writes while it is running is also in memory So the memory that a process can address is called its address space

Also part of the state of the machine are the registers Most instructions read or update registers so it is important to understand that there are certain registers that make up this state of the machine

For example:

The program counter (PC) (sometimes called the instruction pointer or IP)

@reverseengine
❤1
Mergen

Mergen is a deobfuscation tool that leverages LLVM IR and assembly parsing to reverse engineer obfuscated code.

https://github.com/NaC-L/Mergen

@reverseengine
Analyzing the PayloadRestrictions.dll Export Address Filtering

https://windows-internals.com/an-exercise-in-dynamic-analysis

@reverseengine
LOLEXFIL

Living off the land Data Exfiltration methods

https://lolexfil.github.io

@reverseengine
DllShimmer

DllShimmer is a tool for rapidly creating and injecting backdoors into DLLs, facilitating remote control and exploitation of target processes. It simplifies the process of DLL hijacking for security research and potentially malicious activity.

https://github.com/Print3M/DllShimmer

@reverseengine
کرنل چیه؟

تا اینجا گفتیم سیستم‌ عامل بین برنامه‌ها و سخت‌افزار قرار میگیره

اما سوال مهم:

آیا کل سیستم‌ عامل همیشه در حال اجراست؟

نه

در قلب هر سیستم‌ عامل یک بخش بسیار مهم وجود داره به نام Kernel یا هسته
کرنل مهم‌ترین قسمت سیستم‌ عامله و مستقیما با سخت‌افزار کار میکنه

یک مثال ساده:

فرض کنید یک شرکت بزرگ داریم:

کارمندان = برنامه‌ها

ساختمان و تجهیزات = سخت‌افزار

مدیرعامل = Kernel

کارمندها نمیتونن هر کاری خواستن انجام بدن
مثلا نمیتونن مستقیم وارد اتاق سرور بشن یا تجهیزات رو بردارن
باید درخواست شون رو به مدیر عامل یا سیستم مدیریتی بدن
کرنل هم دقیقا همین نقش رو داره

کرنل چه کارهایی انجام میده؟

مدیریت پردازنده (CPU)

تصمیم می‌گیرد:

کدوم برنامه اجرا بشه؟
چه مدت اجرا بشه؟
چه زمانی متوقف بشه؟

مدیریت حافظه (RAM)

تصمیم می‌گیرد:

هر برنامه چقدر حافظه بگیره؟
حافظه برنامه‌ها از هم جدا بمونه
یک برنامه نتونه حافظه برنامه دیگه ای رو بخونه

مدیریت فایل‌ها

وقتی برنامه‌ای فایل باز میکنه:

Plain text

read()

write()

open()

در نهایت کرنل مسئول انجام این عملیاته

مدیریت دستگاه‌ها

مثل:
کیبورد
ماوس
هارد
کارت شبکه
USB
همه از طریق کرنل کنترل میشن


User Mode و Kernel Mode

یکی از مهم‌ترین مفاهیم کل سیستم‌
عامل همینجاست

پردازنده معمولا دو حالت اجرا داره:

User Mode

جایی که برنامه‌های عادی اجرا میشن

مثل:
Chrome

Firefox

Telegram

Notepad


در این حالت برنامه محدودیت داره

Kernel Mode

جایی که کرنل اجرا میشه

در این حالت تقریبا دسترسی کامل به سیستم وجود دارد.

چرا این جداسازی مهمه؟

فرض کنید یک برنامه باگ داشته باشه

اگر مستقیم به سخت‌افزار دسترسی کامل داشته باشه:

سیستم کرش میکنه
اطلاعات خراب میشن
امنیت از بین میره

برای همین سیستم‌عامل برنامه‌ها رو در User Mode نگه میداره


ارتباط برنامه با کرنل چجوریه؟

از طریق System Call

مثلا وقتی برنامه میخاد:

فایل باز کنه
حافظه بگیره
پردازه جدید بسازه

در واقع از کرنل درخواست کمک میکنه


نکته مهم برای مهندسی معکوس:

وقتی داخل دیباگر توابعی مثل اینها رو میبینید:
C

CreateProcess

CreateThread

VirtualAlloc

ReadFile

WriteFile


پشت صحنه تقریبا همه اونا در نهایت به کرنل میرسن

به همین دلیل مهندس معکوس باید همیشه بدوند:

الان کد در User Mode اجرا میشه یا در Kernel Mode؟

این سوال پایه بسیاری از مباحث بعدی مثل:


Process

Memory

System Call

Driver

Windows Internals

هست


What is a kernel?

So far, we have said that the operating system is located between the programs and the hardware

But the important question:

Is the entire operating system always running?

No

At the heart of every operating system is a very important part called the Kernel

The kernel is the most important part of the operating system and works directly with the hardware

A simple example:

Let's assume we have a large company:

Employees = programs

Buildings and equipment = hardware

CEO = Kernel

Employees cannot do whatever they want

For example, they cannot directly enter the server room or remove equipment

They must direct their requests to the CEO or system management

The kernel has exactly the same role

What does the kernel do?

Processor (CPU) management

Decides:

Which program to run?

How long to run?

When to stop?

Memory Management (RAM)

Decides:

How much memory should each program take?

Program memory should be kept separate

A program cannot read another program's memory

File Management

When a program opens a file:

Plain text

read()

write()

open()


Ultimately, the kernel is responsible for performing this operation

Device Management

For example:
Keyboard
Mouse
Hardware
Network Card
USB

All are controlled by the kernel

User Mode and Kernel Mode

One of the most important concepts of the entire operating system is here

The processor usually has two execution modes:

User Mode

Where normal programs are executed

For example:

Chrome

Firefox

Telegram

Notepad


In this mode, the program has restrictions

Kernel Mode

Where the kernel is executed

In this mode, there is almost complete access to the system.

Why is this separation important?

Suppose a program has a bug

If it has full access to the hardware directly:

The system crashes

Data gets corrupted

Security is lost

That's why the operating system keeps programs in User Mode
❤2
How does the program communicate with the kernel?

Through System Call

For example, when the program wants to:

Open a file

Get memory

Create a new process

It actually asks the kernel for help

Important point for reverse engineering:

When you see functions like these in the debugger:

C

CreateProcess

CreateThread

VirtualAlloc

ReadFile

WriteFile


Behind the scenes, almost all of them end up in the kernel

That's why the reverse engineer should always know:

Is the code currently running in User Mode or Kernel Mode?

This question is the basis for many subsequent topics such as:

Process

Memory

System Call

Driver

Windows Internals



@reverseengine
❤1