در مقالهی قبلی از سلام دیجی یاد گرفتیم که چیست و چطور نصب و اجرا میشودYARA .اما قدرت واقعی YARA در Rule های آن نهفته است.
هر Rule مثل یک قانون DNA برای شناسایی بدافزار است. اگر دقیق نوشته شود، میتواند گونههای جدید از همان خانوادهی بدافزار را هم شناسایی کند. حتی اگر کدشان تغییر کند.
در این مقاله به سراغ ساختار کامل Rule، ترفندهای پیشرفته، و نمونههای واقعی از محیط تهدیدهای سایبری می رویم .
🔹 ساختار کلی یک Rule در YARA
یک Rule از چهار بخش اصلی تشکیل شده:
بخش |
توضیح |
مثال |
rule header |
نام Rule و برچسبها |
rule trojan_sample : malware trojan { ... } |
meta |
توضیحات، نویسنده، منبع |
meta: author="abc" description="detects trojan variant" |
strings |
رشتههای جستجو (متنی، باینری، Regex) |
$s1 = "malware" یا $s2 = { 6A 40 68 ?? ?? 00 00 } |
condition |
شرط نهایی برای فعال شدن Rule |
condition: all of them |
برای درک بیشتریک مثال ملموس از چهار بخش اصلی می زنیم:
تصور کنید به دنبال بدافزاری میگردید که در گزارشها دیده شده: فایلها با یک رشتهی خاص و یک URL سختکد شده دارند و همیشه از توابع خاصی در PE استفاده میکنند. حالا YARA نیاز به «قانون» دارد تا آن بدافزار را از بین دهها هزار فایل تشخیص دهد. در ادامه یک Rule کامل و ملموس میآوریم که هر چهار بخش را نشان میدهد. سپس هر بخش را قدمبهقدم توضیح می دهیم.
import "pe"
rule Banking_Trojan_XYZ : trojan banking
{
meta:
author = "user 1"
date = "2025-10-12"
description = "Detects XYZ banking trojan by strings, C2 URL and PE imports"
strings:
$s1 = "GetAccountInfo" wide ascii
$s2 = "http://badbank.example.com/login"
$h1 = { 68 ?? ?? 00 00 6A 00 6A 00 E8 }
condition:
(any of ($s1, $s2) and $h1) and
pe.imports("kernel32.dll", "CreateRemoteThread")
}
حالا بیایم این مثال را با چهار بخش آن تطبیق بدیم:
- Header (نام Rule و تگها)
rule Banking_Trojan_XYZ : trojan banking
مثل نامگذاری یک پروندهی جنایی است مشخص میکند این Rule برای چه خانوادهای یا چه هدفی هست. تگها (trojan
, banking
) کمک میکنن Ruleها را دستهبندی و سریع فیلتر کنید.
- Meta (اطلاعات توصیفی)
meta:
author = "user 1"
date = "2025-10-12"
description = "Detects XYZ banking trojan..."
مثل برچسبهای پرونده: چه کسی این قانون را نوشته، چه زمانی و برای چه منظوری. برای مستندسازی، ردیابی و همکاری تیمی حیاتی است.
- Strings (رشتهها و امضاها)
strings:
$s1 = "GetAccountInfo" wide ascii
$s2 = "http://badbank.example.com/login"
$h1 = { 68 ?? ?? 00 00 6A 00 6A 00 E8 }
اینجا قلب تشخیص است:
$s1
یک نام تابع یا رشتهی متنی است که در نمونه بدافزار مشاهده شده؛$s2
یک URL سختکد شده (C2) است؛$h1
یک الگوی بایت (hex) با wildcard (??
) برای مقاومت در برابر تغییرات جزئی.
تصور کن اینها همان «ردپاهای دیجیتال» هستند که کارآگاه دنبالشان میگردد.
- Condition (شرط فعالشدن Rule)
condition:
(any of ($s1, $s2) and $h1) and
pe.imports("kernel32.dll", "CreateRemoteThread")
این جملهی آخر حکم «قانون اثبات در دادگاه» را دارد: فقط وقتی ترکیب خاصی از شواهد همزمان دیده شود، اعلام خطر کن. اینطوری از false positive جلوگیری میشود.
نمونه اجرای Rule :
yara Banking_Trojan_XYZ.yar /samples/suspected/
نمونه خروجی (نمایشی):
Banking_Trojan_XYZ /samples/suspected/malicious.exe
انواع دادهها در بخش strings
در بخش strings
از YARA، میتوان از سه نوع داده اصلی استفاده کرد:
- رشتههای متنی (Text Strings) : برای شناسایی کلمات، آدرسها، نام توابع و متنهای قابلخواندن در فایل (مثل
"cmd.exe"
یا http://example.com). - رشتههای باینری (Hex Strings) : برای تشخیص الگوهای بایت در فایلهای اجرایی یا رمزگذاریشده، مثل
{ 68 ?? ?? 00 00 E8 }
- رشتههای Regular Expression : برای جستجوی الگوهای پویا و پیچیدهتر در متن، مثل
/[A-Za-z0-9]{32}/
برای شناسایی توکنها یا هشها.
این سه نوع داده به شما اجازه میدهند Ruleهایی بنویسید که هم دقیق و هم انعطافپذیر باشند.
نوع داده |
مثال |
توضیح |
Text String |
$a = "malware" |
جستجوی رشتهی متنی ساده |
Hex String |
$b = { E2 34 56 ?? 90 } |
الگوی باینری (?? به معنی wildcard) |
Regular Expression |
$c = /Trojan:.*/ |
جستجوی رشتههای تطبیقی با regex |
Wide / Ascii / Nocase |
$a = "MZ" wide nocase |
کنترل حساسیت به حروف و یونیکد |
اپراتورها و شرطها در بخش condition
در YARA، شرطها دقیقاً قلب Rule هستند. چند مثال از پرکاربردترین شرطها:
نوع شرط |
مثال |
توضیح |
any of them |
any of ($a,$b,$c) |
اگر هرکدام از رشتهها پیدا شود |
all of them |
all of them |
اگر همه پیدا شوند |
تعداد خاصی |
#a > 3 |
اگر بیش از ۳ بار رشته $a تکرار شده |
محدوده بایت |
$a in (0..100) |
اگر در ۱۰۰ بایت اول فایل پیدا شود |
حجم فایل |
filesize < 500KB |
فقط برای فایلهای کوچکتر از ۵۰۰KB |
ترکیب منطقی |
($a or $b) and not $c |
شرطهای پیچیدهتر |
نمونههای واقعی از Ruleهای تخصصی
شناسایی فایل اجرایی آلوده با ساختار PE خاص
import "pe" rule Suspicious_PE_Imports { meta: description = "Detects executables importing VirtualAlloc and CreateProcessA" author = "abc user" condition: pe.imports("kernel32.dll", "VirtualAlloc") and pe.imports("kernel32.dll", "CreateProcessA") }
📘 توضیح: بدافزارهایی که حافظه جدید تخصیص میدهند و فرآیند جدیدی ایجاد میکنند، معمولاً رفتار اجرایی مخرب دارند.
تشخیص Backdoor با الگوی رشتهای و شرط ترکیبی
rule Backdoor_Connection { meta: description = "Detects hardcoded C2 domains" strings: $a = "connect" $b = "POST /api/v1/login" $c = "malicious-server.com" condition: ($a and $b) or $c }
📘 توضیح: این Rule ترکیب چند رفتار شبکهای را بررسی میکند تا Backdoorها را تشخیص دهد.
شناسایی فایل آلوده در محدوده خاص
rule Suspicious_Header { strings: $mz = "MZ" $p = { 50 45 00 00 4C 01 03 00 } condition: $mz at 0 and $p in (0..512) }
📘 توضیح: این Rule فقط فایلهایی را که signature اجرایی PE در ابتدای فایل دارند بررسی میکند — برای شناسایی فایلهای تزریقشده مناسب است.
🔹 جدول ویژگیهای پرکاربرد در YARA PE Module
ویژگی |
توضیح |
مثال |
pe.entry_point |
آدرس شروع اجرای فایل |
pe.entry_point == 0x1000 |
pe.imports() |
تابع واردشده از DLL خاص |
pe.imports("kernel32.dll", "LoadLibraryA") |
pe.sections[i].name |
نام سکشن خاص |
pe.sections[0].name == ".text" |
pe.number_of_sections |
تعداد سکشنها |
pe.number_of_sections > 5 |
pe.rich_signature.valid |
بررسی امضای RICH |
not pe.rich_signature.valid |
ترکیب YARA با تحلیل حافظه (Memory Forensics)
شما میتوانید Ruleهای YARA را در ابزارهایی مثل Volatility و Rekall برای اسکن dump حافظه اجرا کنید:
vol.py -f memory.raw yarascan --yara-rules=my_rules.yar
این قابلیت در Incident Response کاربرد زیادی دارد، چون ممکن است بدافزار در حافظه باشد ولی در دیسک نه.
ساخت مجموعه Ruleهای سازمانی (Corporate Rulebase)
برای سازمانها بهتر است Ruleها را در چند دسته نگهداری کنید:
دسته |
نوع Rule |
توضیح |
Generic |
شناسایی رفتارهای عمومی |
مثلاً APIهای مشکوک، اتصالات شبکهای |
Family-Specific |
بدافزارهای خاص |
مثلاً Emotet, TrickBot, AgentTesla |
IOC-Based |
Ruleهای موقت |
براساس IoCهای جدید از Threat Intel |
Whitelist |
فایلهای سالم |
جلوگیری از False Positive |
📌 توصیهRule: ها را نسخهگذاری (Versioning) کنید و در یک Git Repo ذخیره کنید.
هر Rule جدید باید در محیط تست بررسی شود قبل از انتشار سازمانی.
ترفندهای حرفهای در YARA Rule Writing
وقتی از مرحلهی نوشتن Ruleهای ساده عبور میکنید، زمانش میرسد که دقت و کارایی Ruleهایتان را مثل یه threat hunter واقعی بالا ببرید. در اینجا چند ترفند حرفهای برای نوشتن Rule های قدرتمندتر آورده ایم:
🔹 .1 استفاده از Wildcardها برای انعطاف در رشتههای باینری
در Hex patternها، از ??
برای جایگزینی هر بایت استفاده کنید.
مثلاً:
$code = { 68 ?? ?? 00 00 E8 ?? ?? ?? ?? }
با این روش Rule حتی اگر بخشی از کد تغییر کرده باشد (مثلاً با packer یا compiler متفاوت) همچنان آن را تشخیص میدهد.
🔹 .2 ترکیب رشتههای متعدد با شرطهای منطقی
به جای اینکه فقط بگویید:
any of them
میتوانید شرط دقیقتر بنویسید:
($url and $func) or ($string1 and $hex1)
این کار باعث میشود Rule فقط زمانی فعال شود که الگوی رفتاری خاصی از بدافزار وجود داشته باشد، نه هر تشابه سطحی.
🔹 .3 محدود کردن جستجو در بخشهای خاص فایل
میتوانید بگویید فقط در بخش خاصی از فایل دنبال الگو بگرد:
$h1 in (0..200)
یا:
$code in (pe.sections[1].raw_data_offset..pe.sections[1].raw_data_offset + pe.sections[1].raw_data_size)
این ترفند برای کاهش false positive عالی ست، چون فقط در بخشهای واقعی کد جستجو انجام میدهید.
🔹 .4استفاده از ماژولهای YARA برای تحلیل عمیقتر
ماژولها قدرت اصلی YARA هستند. مثلاً:
import "pe"
condition:
pe.imphash() == "a1b2c3d4e5f6g7h8i9"
یا:
import "math"
condition:
math.entropy(0, filesize) > 7.5
با math.entropy()
می توانید فایلهای فشرده یا رمزگذاریشده را شناسایی کنید — روشی محبوب برای شناسایی packed malware .
🔹 .5استفاده از meta هوشمند برای مدیریت Ruleها
در تیمهای بزرگ، داشتن meta تمیز و دقیق ضروری است:
meta:
author = "ThreatHunter Team"
malware_family = "AgentTesla"
last_update = "2025-10-12"
source = "Sandbox sample #147"
بعداً در سیستمهای SIEM یا Splunk میتوانید Ruleها را براساس meta فیلتر یا گزارش کنید.
🔹 .6جلوگیری از False Positive با Ruleهای چندمرحلهای
Ruleهایی بنویسید که فقط وقتی چند نشانه با هم دیده میشوند هشدار بدهند. مثلاً:
condition:
(all of ($url*, $func*, $cfg*)) and filesize < 1MB
این یعنی اگر فایل بسیار بزرگ بود یا فقط یکی از رشتهها وجود داشت، هشدار داده نمیشود.
🔹 .7 استفاده از Regex برای الگوهای پویا
برای شناسایی دامنهها یا کلیدهای API که فرمت ثابتی دارند:
$url = /http:\/\/[a-z0-9\-\.]+\.(ru|cn|tk)/
با این کار حتی اگر دامنهها تغییر کنند، Rule هنوز مؤثر باقی می ماند.
🔹 .8 تست و بهینهسازی Ruleها
قبل از اضافه کردن Rule به سیستم اصلی، حتماً با نمونههای سالم و آلوده تستش کنید:
yara -r myrules.yar /samples/
و برای مشاهده جزئیات تطبیق از:
yara -s myrules.yar sample.exe
استفاده کنید تا بفهمید کدام رشته باعث تشخیص شده.
🔹 .9 از Ruleهای جامعه امنیتی الهام بگیرید.
در مخازنی مثل YARA-Rules GitHub یا Florian Roth’s signatures، میتوانیدRuleهای فوقالعادهای ببینید و ساختار حرفهایشان را یاد بگیرید.
تکنیک |
توضیح |
Wildcard در بایتها |
برای تغییرات جزئی در امضاهای باینری |
استفاده از meta دقیق |
کمک به جستجو و مدیریت Ruleها |
تست روی فایل سالم و آلوده |
برای کاهش False Positive |
ترکیب شرطهای منطقی |
افزایش دقت تشخیص |
استفاده از Offset محدود |
برای جستجوی در محدوده خاص فایل |
ساخت Ruleهای چندبخشی (Chained) |
برای شناسایی بدافزارهای Modular |
خطاهای رایج در نوشتن Ruleها
خطا |
توضیح |
راهحل |
تشخیص اشتباه فایلهای سالم |
شرطها بیشازحد عمومی هستند |
از شرطهای ترکیبی دقیقتر استفاده کنید |
Rule بدون meta |
Ruleها قابل پیگیری نیستند |
همیشه meta بنویسید |
استفاده زیاد از any of them |
افزایش False Positive |
بهجای آن شرطهای دقیقتر تعریف کنید |
بررسی محدوده اشتباه |
استفاده از محدوده نادرست offset |
از دستور at یا in (range) استفاده کنید |
جمعبندی
YARA تنها وقتی واقعاً قدرتمند است که Ruleهای آن منطقی، دقیق، و تستشده باشند. در این مرحله شما از کاربر ساده به Rule Writer حرفهای تبدیل شدید.
در مقاله بعدی این مجموعه، به سراغ ادغام YARA با Sandbox میرویم تا Ruleها را بهصورت خودکار روی فایلهای مشکوک اجرا کنیم.