YARA規則摘要

原文鏈接:https://yara.readthedocs.io/en/v3.7.0/writingrules.html

一個簡單的yara規則示範:

rule ExampleRule
{
    strings:
        $my_text_string = "text here"
        $my_hex_string = { E2 34 A1 C8 23 FB }

    condition:
        $my_text_string or $my_hex_string
}

yara規則由rule引導,後跟一個類似C語言變量格式的字符串作爲規則名稱,長度不能超過128字節。花括號定義規則內容。

規則中用戶定義的字符串變量由$字符引導,變量由字母、數字或下劃線組成,不能是保留的關鍵字。

yara規則中的關鍵字:

all and any ascii at condition contains
entrypoint false filesize fullword for global in
import include int8 int16 int32 int8be int16be
int32be matches meta nocase not or of
private rule strings them true uint8 uint16
uint32 uint8be uint16be uint32be wide

字符串變量可以是由雙引號""界定的文本內容,也可以是花括號{}界定的十六進制字符串。

註釋

類似於C語言,支持行註釋//和塊註釋/**/

字符串

十六進制字符串

  • 佔位符?
    示例:{ E2 34 ?? C8 A? FB }?代表任意值的半字節內容。

  • 範圍[x-y](0<=x<=y)
    示例:{ F4 23 [4-6] 62 B4 [6] EA BB [10-] FF [-]}
    [4-6]代表任意4-6個字節;
    [6][6-6]的簡寫形式,代表6個字節;
    [10-]代表10個字節及以上;
    [-]代表任意多個字節。

  • 多選|
    示例:{ F4 23 ( 62 B4 | 56 | 45 ?? 67 ) 45 }
    圓括號內使用|字符分隔的內容匹配任意一個即可。

文本字符串

雙引號界定的文本內容:"foobar"
轉義字符:

\" 雙引號
\\ 反斜槓
\t Tab
\n 換行符
\xdd 定義字節

字符串修飾

  • nocase
    查找時需要忽略大小寫:$text_string = "foobar" nocase
  • ascii
    默認定義的字符串爲ascii格式,可以省略。
  • wide
    定義寬字符:$wide_string = "Borland" wide。僅通過在ascii字符之間插入0字節實現,不支持非ascii字符。
    同時定義寬字符和ascii字符:$wide_and_ascii_string = "Borland" wide ascii
  • fullword
    全字搜索:$text_string = "foobar" fullword。搜索時確保字符串的前後字節不是字母。

正則表達式

元字符:

\ 轉義元字符
^ 匹配文件開頭
$ 匹配文件末尾
| 多選
() 分組
[] 字符集

量詞:

* 匹配0或多次
+ 匹配1或多次
? 匹配0或1次
{n} 匹配n次
{n,} 匹配至少n次
{,m} 匹配最多m次
{n,m} 匹配n到m次

默認使用貪婪模式匹配,在量詞後面追加?字符切換爲非貪婪模式。

其它轉義字符:

\t Tab
\n 換行
\r 回車
\f 換頁
\a Alarm
\xNN 定義字節

字符類:

\w 匹配一個字母數字下劃線中的字符
\W 匹配一個非字母數字下劃線中的字符
\s 匹配一個空白字符
\S 匹配一個非空白字符
\d 匹配一個數字字符
\D 匹配個非數字字符
\b 匹配一個字的邊界(3.3.0)
\B 匹配一個非字邊界(3.3.0)

條件

類似於編程語言的布爾表達式,支持邏輯運算符:and,or,not,關係運算符:>=,<=,<,>,==,~=,算術運算符:+,-,*,\,%,位運算符:&,|,<<,>>,~,^。條件中出現的數字默認爲十進制,如果要使用十六進制需要加上前導內容0x

字符串變量可以直接作爲布爾值使用,存在匹配時爲true,否則爲false
示例:

rule Example
{
    strings:
        $a = "text1"
        $b = "text2"
        $c = "text3"
        $d = "text4"

    condition:
        ($a or $b) and ($c or $d)
}

匹配次數

字符串變量的前導字符$替換成#,代表該字符串在目標(文件或進程)出現的次數,可以直接在條件表達式中使用。

rule CountExample
{
    strings:
        $a = "dummy1"
        $b = "dummy2"

    condition:
        #a == 6 and #b > 10
}

匹配文件偏移或虛擬地址

使用at指定字符串在指定位置進行匹配。

rule AtExample
{
    strings:
        $a = "dummy1"
        $b = "dummy2"

    condition:
        $a at 100 and $b at 200
        //或在指定的範圍內匹配
        //$a in (0..100) and $b in (100..filesize)
}

@a[i]:獲取第i個匹配的偏移或地址。i從1開始計數。如果i超出範圍則返回一個空值。
!a[i]:獲取第i個匹配結果的長度。i從1開始計數。!a代表第一個匹配結果的長度。

File size

filesize代表目標文件的長度字節,如果目標是進程則該變量無意義。

rule FileSizeExample
{
    condition:
       filesize > 200KB
}

KB前面的數字只能是十進制,還支持MB。(GB是否支持文檔沒說)

取值

int8(<offset or virtual address>)
int16(<offset or virtual address>)
int32(<offset or virtual address>)
uint8(<offset or virtual address>)
uint16(<offset or virtual address>)
uint32(<offset or virtual address>)
int8be(<offset or virtual address>)
int16be(<offset or virtual address>)
int32be(<offset or virtual address>)
uint8be(<offset or virtual address>)
uint16be(<offset or virtual address>)
uint32be(<offset or virtual address>)

u開頭的讀取無符號整數,be結尾的按big-endian字節序讀取。
示例:

rule IsPE
{
  condition:
     // MZ signature at offset 0 and ...
     uint16(0) == 0x5A4D and
     // ... PE signature at offset stored in MZ header at 0x3C
     uint32(uint32(0x3C)) == 0x00004550
}

字符串集合

使用of關鍵字檢查任意或多個字符串的匹配。示例:

rule OfExample1
{
    strings:
        $foo1 = "dummy1"
        $foo2 = "dummy2"
        $bar1 = "dummy3"
        $bar2 = "dummy4"

    condition:
        2 of ($foo1,$foo2,$bar1,$bar2) //至少有兩個匹配
        //或使用以下形式匹配規則內字符串變量
        //2 of($foo*,$bar*)
        //或使用$*匹配規則內所有字符串變量($*與them相同)
        //2 of ($*)
        //2 of them
        //of前面的數字可以使用以下關鍵字:
        //any of them //匹配任意一個
        //all of them //匹配所有
        //all of ($foo*)
}

多個字符串應用同一個條件

語法:for expression of string_set : ( boolean_expression )
示例:

any of ($a,$b,$c)
for any of ($a,$b,$c) : ( $ )
for all of them : ( # > 3 )
for all of ($a*) : ( @ > @b )

圓括號中的佔位符功能:
$代表正在評估的字符串;
#代表正在評估的字符串出現的次數;
@代表正在評估的字符串第一個匹配所在的偏移或虛擬地址。

使用匿名變量

rule AnonymousStrings
{
    strings:
        $ = "dummy1"
        $ = "dummy2"

    condition:
        1 of them
}

匹配結果遍歷

語法:for expression identifier in indexes : ( boolean_expression )
示例:

rule Occurrences
{
    strings:
        $a = "dummy1"
        $b = "dummy2"

    condition:
        for all i in (1,2,3) : ( @a[i] + 10 == @b[i] )
        //也可寫爲
        //for all i in (1..3) : ( @a[i] + 10 == @b[i] )
        //可使用變量代替循環範圍
        //for all i in (1..#a) : ( @a[i] < 100 )
}

引用其它規則

示例:

rule Rule1
{
    strings:
        $a = "dummy1"

    condition:
        $a
}

rule Rule2
{
    strings:
        $a = "dummy2"

    condition:
        $a and Rule1
}

規則設置

全局規則

全局規則在所有其它規則之前評估,如果結果爲false則不會再評估其它規則。允許存在多個全局規則。
示例:

global rule SizeLimit
{
    condition:
        filesize < 2MB
}

私有規則

私有規則不會像全局規則一樣對結果產生影響,評估後也不會提交給yara,但可以與其它規則混合使用。
示例:

private rule PrivateRuleExample
{
    ...
}

可以對一個規則同時定義全局和私有屬性,評估後不會提交給yara,但必須滿足條件。

規則標籤

規則後面添加標籤,用於過濾輸出。在命令行使用時通過-t <tag>--tag=<tag>選項指定需要輸出的標籤。一個規則允許有多個標籤,使用空格隔開。標籤的名稱格式與變量相同。
示例:

rule TagsExample1 : Foo Bar Baz
{
    ...
}

rule TagsExample2 : Bar
{
    ...
}

元數據

僅用於存儲規則的附加信息,不能在條件中使用,支持文本、整數和布爾值字符串(true/false)。
示例:

rule MetadataExample
{
    meta:
        my_identifier_1 = "Some string data"
        my_identifier_2 = 24
        my_identifier_3 = true

    strings:
        $my_text_string = "text here"
        $my_hex_string = { E2 34 A1 C8 23 FB }

    condition:
        $my_text_string or $my_hex_string
}

使用模塊

必須在規則外部導入模塊:

import "pe"
import "cuckoo"

使用<module name>.引用模塊變量:

pe.entry_point == 0x1000
cuckoo.http_request(/someregexp/)

未定義的值

yara確保模塊中未定義的變量在使用時結果永遠爲undefinedpe.entry_point指向PE文件的入口地址,但是在掃描一個非PE文件時,該變量是沒有值的。示例:

import "pe"

rule Test
{
  strings:
      $a = "some string"

  condition:
      $a and pe.entry_point == 0x1000
}

該規則匹配結果始終爲undefined。但是如果將條件改爲$a or pe.entry_point == 0x1000,且目標不是PE文件,則以$a的結果爲準。

擴展變量

擴展變量由外部定義,可以在條件中直接使用。
示例1:

rule ExternalVariableExample1
{
    condition:
       ext_var == 10
}

示例2:

rule ExternalVariableExample3
{
    condition:
        string_ext_var contains "text"
}

rule ExternalVariableExample4
{
    condition:
        string_ext_var matches /[a-z]+/is
}

正則表達式末尾追加i表示忽略大小寫,追加s表示只在同一行進行匹配。

外部變量必須在運行時定義。yara-python中的compilematch函數的externals參數可以指定外部變量。外部變量的值支持文本、整數和布爾值。在命令行可以通過-d選項定義。

包含文件

使用include關鍵字包含其它規則文件。在Linux系統中允許使用相對路徑或絕對路徑,在windows中必須使用絕對路徑。
Linux系統示例:

include "./includes/other.yar"
include "../includes/other.yar"
include "/home/plusvic/yara/includes/other.yar"

Windows系統示例:

include "c:/yara/includes/other.yar"
include "c:\\yara\\includes\\other.yar"
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章