Hello, analysts fighting on the front lines of security! 🛡️
When analyzing malware, there are times when you need to pinpoint “that specific one I was looking for” among thousands or tens of thousands of files. You can’t open them all one by one, and it’s even more daunting if it’s new malware that existing antivirus software can’t catch.
This is where YARA comes in. YARA is called “the regular expression for files” and is the most powerful tool for classifying files by defining malware patterns (signatures).
Today, we will thoroughly explore the basic syntax structure (3 main elements) and writing principles for creating YARA rules. Just by reading this article, you too can create your own antivirus engine! 🚀

1. Anatomy of a YARA Rule: Understanding the Framework 🦴
YARA rules have an intuitive structure similar to the C language. They are broadly divided into four parts: Header, Meta, Strings, and Condition.
rule Malware_Example_Rule // [Header] Rule name
{
meta: // [Meta] Description and information
author = "Security Analyst"
description = "This is a sample rule"
date = "2025-12-16"
strings: // [Strings] Pattern to search for
$text_string = "malicious_command"
$hex_string = { E2 34 A1 ?? 00 }
condition: // [Condition] Detection logic
$text_string or $hex_string
}
Shall we take a detailed look at what each section does? 🧐
2. First Element: Meta – “Business Card” 📝
The meta section does not affect the rule’s operation at all. However, in practice, it can be the most important. This is because it serves as a ‘comment’ and a ‘business card’ to record who created this rule and why.
- Key Keywords:
- author: Author’s name
- description: Description of the rule (what malware it catches)
- date: Creation or modification date
- hash: Hash value of the analyzed malware sample (very important! Used for later verification)
- version: Rule version
💡 Writing Tip: Even if you’re writing rules for yourself, make it a habit to include description and hash. It’s for your future self three months from now.
3. Second Element: Strings – “Evidence” 🧵
The strings section is where you define the ‘data you want to find’ within a file. It uses identifiers starting with a $ symbol, similar to variables.
There are three main types:
① Text Strings
Searches for common ASCII or Unicode strings. Uses double quotes (” “).
$s1 = "cmd.exe" ascii // General English string
$s2 = "Attack" wide // Unicode string (stored in 2-byte chunks)
$s3 = "Error" nocase // Case-insensitive (detects both error and ERROR)
$s4 = "hacker" fullword // Only when the whole word matches (does not detect yhacker)
② Hex Strings
Used to find binary code (machine code) or specific byte patterns. Uses curly braces ({ }).
$h1 = { E2 34 A1 C5 } // Exactly matching bytes
$h2 = { E2 34 ?? C5 } // Wildcard (??): anything can come in this position
$h3 = { E2 [2-4] C5 } // Jump: 2-4 bytes are skipped in the middle
- Wildcards (??) play a crucial role in catching variant malware!
③ Regular Expressions
Used to find complex patterns, but they are a major cause of performance degradation, so use them only when absolutely necessary. Uses slashes (/ /).
$r1 = /md5: [0-9a-fA-F]{32}/
4. Third Element: Condition – “Judge” ⚖️
The condition section is the logical area that combines the defined strings to decide “whether or not to finally judge it as malware.” If True is returned, it means it has been detected.
① Boolean Logic
condition:
($s1 and $s2) or $h1 // Detect if both s1 and s2 exist, or if h1 exists
② Counting Based
condition:
#s1 > 3 // Detect if string s1 appears more than 3 times in the file
③ File Size and Header Check (File Properties)
This is the most commonly used pattern. To reduce false positives, file size or header is checked first.
condition:
uint16(0) == 0x5A4D and filesize < 2MB // When it's an MZ header (exe file) and less than 2MB
- uint16(0): Read 16 bits (2 bytes) from the 0th address of the file. (Windows executable files always start with MZ, i.e., 0x5A4D)
5. Three Principles for Writing YARA Rules (Best Practices) ⭐
Poorly crafted YARA rules can halt systems or cause major incidents by flagging legitimate files as malicious. Remember these three things:
1️⃣ Avoid overly short strings! (Performance)
- Bad Example: $a = “55” (not a hex value, but the string “55”)
- Reason: The string “55” can appear tens of thousands of times in a file. Scan speed will be incredibly slow. Use unique strings of at least 5-6 bytes or more.
2️⃣ Beware of False Positives! (Specificity)
- Bad Example: $s = “CreateFile”
- Reason: CreateFile is a function used by many legitimate programs. If you use this as a condition, even Windows Notepad will be flagged as malware. Look for unique strings that only exist in malware (C2 addresses, typos, unusual mutexes, etc.).
3️⃣ Maintain the order of conditions! (Short-Circuit Evaluation)
- Good Example: uint16(0) == 0x5A4D and $s1
- Explanation: The computer checks conditions from left to right. If the file header is not MZ, the $s1 condition will not even be checked. By placing lighter conditions (file size, header) first and heavier conditions (string search) later, the speed will be significantly faster.
🎉 Conclusion: Now You’re a Rule Writer!
YARA rules may seem simple, but they are the result of an analyst’s insight in deciding ‘which strings to use as signatures.’
Keep the Meta (description), Strings (evidence), and Condition (judgment) structure you learned today in mind, and try to translate the characteristics of the malware you’ve analyzed into rules.
Next time, we will conduct a practical exercise to scan and detect actual malware files using the YARA rules we’ve written. Stay tuned! 👋
Leave a Reply