yara-ffi 1.0.0 → 2.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/yara/ffi.rb +6 -1
- data/lib/yara/scan_result.rb +105 -0
- data/lib/yara/version.rb +1 -1
- data/lib/yara/yr_meta.rb +4 -1
- data/lib/yara/yr_rule.rb +2 -2
- data/lib/yara/yr_string.rb +11 -1
- data/lib/yara.rb +17 -18
- metadata +3 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: ac111338f4038017b3eb887d2bfcea73c2a2aa5a9b409370e13cfd01985276df
|
4
|
+
data.tar.gz: 353ab52ebe038b8fbd2b3c9ce35436df1b4fb20cad1cfa0b3019e678291e0f0b
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 96a2ede305474b3457dcaf4256e3b57fa28becae0abc51eb3e45897667f5a971ba818a45a6b945b15d02208c2eee6adad43ff416c31d9528083ed7dd5a317046
|
7
|
+
data.tar.gz: 6b1a3fa08e02123b655d140f30fa531494d585276591f5758b6f8c26636ea0fe388eef7fa5e6253d9fce42221b19729eab0960684a87eaf95e96f701eacd4fb7
|
data/lib/yara/ffi.rb
CHANGED
@@ -35,6 +35,11 @@ module Yara
|
|
35
35
|
:pointer, # compiler_pointer
|
36
36
|
], :void
|
37
37
|
|
38
|
+
# int yr_rules_destroy(YR_RULES* rules)
|
39
|
+
attach_function :yr_rules_destroy, [
|
40
|
+
:pointer, # rules_pointer
|
41
|
+
], :void
|
42
|
+
|
38
43
|
# void callback_function(
|
39
44
|
# int error_level,
|
40
45
|
# const char* file_name,
|
@@ -100,7 +105,7 @@ module Yara
|
|
100
105
|
# int timeout)
|
101
106
|
attach_function :yr_rules_scan_mem, [
|
102
107
|
:pointer, # rules_pointer*
|
103
|
-
:
|
108
|
+
:pointer, # buffer (aka test subject)
|
104
109
|
:size_t, # buffer size (String#bytesize)
|
105
110
|
:int, # flags
|
106
111
|
:scan_callback, # proc
|
@@ -0,0 +1,105 @@
|
|
1
|
+
module Yara
|
2
|
+
class ScanResult
|
3
|
+
RULE_MATCHING = 1
|
4
|
+
RULE_NOT_MATCHING = 2
|
5
|
+
|
6
|
+
META_FLAGS_LAST_IN_RULE = 1
|
7
|
+
|
8
|
+
META_TYPE_INTEGER = 1
|
9
|
+
META_TYPE_STRING = 2
|
10
|
+
META_TYPE_BOOLEAN = 3
|
11
|
+
|
12
|
+
STRING_FLAGS_LAST_IN_RULE = 0
|
13
|
+
|
14
|
+
STRING_LENGTH = 4
|
15
|
+
STRING_POINTER = 5
|
16
|
+
|
17
|
+
RULE_IDENTIFIER = 1
|
18
|
+
METAS_IDENTIFIER = 3
|
19
|
+
STRING_IDENTIFIER = 4
|
20
|
+
|
21
|
+
attr_reader :callback_type, :rule
|
22
|
+
|
23
|
+
def initialize(callback_type, rule_ptr)
|
24
|
+
@callback_type = callback_type
|
25
|
+
@rule = YrRule.new(rule_ptr)
|
26
|
+
end
|
27
|
+
|
28
|
+
def rule_name
|
29
|
+
@rule.values[RULE_IDENTIFIER]
|
30
|
+
end
|
31
|
+
|
32
|
+
def rule_meta
|
33
|
+
metas = {}
|
34
|
+
reading_metas = true
|
35
|
+
meta_index = 0
|
36
|
+
meta_pointer = @rule.values[METAS_IDENTIFIER]
|
37
|
+
while reading_metas do
|
38
|
+
meta = YrMeta.new(meta_pointer + meta_index * YrMeta.size)
|
39
|
+
metas.merge!(meta_as_hash(meta))
|
40
|
+
flags = meta.values.last
|
41
|
+
if flags == META_FLAGS_LAST_IN_RULE
|
42
|
+
reading_metas = false
|
43
|
+
else
|
44
|
+
meta_index += 1
|
45
|
+
end
|
46
|
+
end
|
47
|
+
metas
|
48
|
+
end
|
49
|
+
|
50
|
+
def rule_strings
|
51
|
+
strings = {}
|
52
|
+
reading_strings = true
|
53
|
+
string_index = 0
|
54
|
+
string_pointer = @rule.values[STRING_IDENTIFIER]
|
55
|
+
while reading_strings do
|
56
|
+
string = YrString.new(string_pointer + string_index * YrString.size)
|
57
|
+
string_length = string.values[STRING_LENGTH]
|
58
|
+
flags = string.values.first
|
59
|
+
if flags == STRING_FLAGS_LAST_IN_RULE
|
60
|
+
reading_strings = false
|
61
|
+
else
|
62
|
+
strings.merge!(string_as_hash(string)) unless string_length == 0
|
63
|
+
string_index += 1
|
64
|
+
end
|
65
|
+
end
|
66
|
+
strings
|
67
|
+
end
|
68
|
+
|
69
|
+
def scan_complete?
|
70
|
+
callback_type == SCAN_FINISHED
|
71
|
+
end
|
72
|
+
|
73
|
+
def rule_outcome?
|
74
|
+
[RULE_MATCHING, RULE_NOT_MATCHING].include?(callback_type)
|
75
|
+
end
|
76
|
+
|
77
|
+
def match?
|
78
|
+
callback_type == RULE_MATCHING
|
79
|
+
end
|
80
|
+
|
81
|
+
private
|
82
|
+
|
83
|
+
def meta_as_hash(meta)
|
84
|
+
name, string_value, int_value, type, _flags = meta.values
|
85
|
+
value = meta_value(string_value, int_value, type)
|
86
|
+
{ name.to_sym => value }
|
87
|
+
end
|
88
|
+
|
89
|
+
def string_as_hash(yr_string)
|
90
|
+
string_pointer = yr_string.values[STRING_POINTER]
|
91
|
+
string_identifier = yr_string.values.last
|
92
|
+
{ string_identifier.to_sym => string_pointer.read_string }
|
93
|
+
end
|
94
|
+
|
95
|
+
def meta_value(string_value, int_value, type)
|
96
|
+
if type == META_TYPE_INTEGER
|
97
|
+
int_value
|
98
|
+
elsif type == META_TYPE_BOOLEAN
|
99
|
+
int_value == 1
|
100
|
+
else
|
101
|
+
string_value
|
102
|
+
end
|
103
|
+
end
|
104
|
+
end
|
105
|
+
end
|
data/lib/yara/version.rb
CHANGED
data/lib/yara/yr_meta.rb
CHANGED
data/lib/yara/yr_rule.rb
CHANGED
data/lib/yara/yr_string.rb
CHANGED
@@ -1,5 +1,15 @@
|
|
1
1
|
module Yara
|
2
2
|
class YrString < FFI::Struct
|
3
|
-
layout
|
3
|
+
layout \
|
4
|
+
:flags, :uint32_t,
|
5
|
+
:idx, :uint32_t,
|
6
|
+
:fixed_offset, :int64_t,
|
7
|
+
:rule_idx, :uint32_t,
|
8
|
+
:length, :int32_t,
|
9
|
+
:string, :pointer,
|
10
|
+
:chained_to, :pointer,
|
11
|
+
:chain_gap_min, :int32_t,
|
12
|
+
:chain_gap_max, :int32_t,
|
13
|
+
:identifier, :string
|
4
14
|
end
|
5
15
|
end
|
data/lib/yara.rb
CHANGED
@@ -2,22 +2,17 @@
|
|
2
2
|
|
3
3
|
require "ffi"
|
4
4
|
require "pry"
|
5
|
-
require_relative "yara/version"
|
6
5
|
require_relative "yara/ffi"
|
6
|
+
require_relative "yara/scan_result"
|
7
|
+
require_relative "yara/version"
|
7
8
|
|
8
|
-
# TBD
|
9
9
|
module Yara
|
10
|
-
|
11
|
-
|
12
|
-
CALLBACK_MSG_RULE_MATCHING = 1
|
13
|
-
CALLBACK_MSG_RULE_NOT_MATCHING = 2
|
14
|
-
CALLBACK_MSG_SCAN_FINISHED = 3
|
10
|
+
SCAN_FINISHED = 3
|
15
11
|
|
16
|
-
|
12
|
+
class Error < StandardError; end
|
17
13
|
|
18
14
|
def self.test(rule_string, test_string)
|
19
15
|
user_data = UserData.new
|
20
|
-
user_data[:number] = 42
|
21
16
|
scanning = true
|
22
17
|
results = []
|
23
18
|
|
@@ -38,23 +33,25 @@ module Yara
|
|
38
33
|
Yara::FFI.yr_compiler_get_rules(compiler_pointer, rules_pointer)
|
39
34
|
rules_pointer = rules_pointer.get_pointer(0)
|
40
35
|
|
41
|
-
result_callback = proc do |context_ptr,
|
42
|
-
|
43
|
-
|
44
|
-
case message
|
45
|
-
when CALLBACK_MSG_RULE_MATCHING
|
46
|
-
results << rule.values[RULE_IDENTIFIER]
|
47
|
-
when CALLBACK_MSG_SCAN_FINISHED
|
36
|
+
result_callback = proc do |context_ptr, callback_type, rule_ptr, user_data_ptr|
|
37
|
+
if callback_type == SCAN_FINISHED
|
48
38
|
scanning = false
|
39
|
+
else
|
40
|
+
result = ScanResult.new(callback_type, rule_ptr)
|
41
|
+
results << result if result.rule_outcome?
|
49
42
|
end
|
50
43
|
|
51
44
|
0 # ERROR_SUCCESS
|
52
45
|
end
|
53
46
|
|
47
|
+
test_string_bytesize = test_string.bytesize
|
48
|
+
test_string_pointer = ::FFI::MemoryPointer.new(:char, test_string_bytesize)
|
49
|
+
test_string_pointer.put_bytes(0, test_string)
|
50
|
+
|
54
51
|
Yara::FFI.yr_rules_scan_mem(
|
55
52
|
rules_pointer,
|
56
|
-
|
57
|
-
|
53
|
+
test_string_pointer,
|
54
|
+
test_string_bytesize,
|
58
55
|
0,
|
59
56
|
result_callback,
|
60
57
|
user_data,
|
@@ -66,6 +63,8 @@ module Yara
|
|
66
63
|
|
67
64
|
results
|
68
65
|
ensure
|
66
|
+
Yara::FFI.yr_rules_destroy(rules_pointer)
|
67
|
+
Yara::FFI.yr_compiler_destroy(compiler_pointer)
|
69
68
|
Yara::FFI.yr_finalize
|
70
69
|
end
|
71
70
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: yara-ffi
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 2.1.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jonathan Hoyt
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-08-
|
11
|
+
date: 2021-08-31 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: ffi
|
@@ -45,6 +45,7 @@ files:
|
|
45
45
|
- bin/setup
|
46
46
|
- lib/yara.rb
|
47
47
|
- lib/yara/ffi.rb
|
48
|
+
- lib/yara/scan_result.rb
|
48
49
|
- lib/yara/user_data.rb
|
49
50
|
- lib/yara/version.rb
|
50
51
|
- lib/yara/yr_meta.rb
|