Subversion Repositories filter_foundry

Rev

Rev 507 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
267 daniel-mar 1
# Obfuscated filters
2
 
272 daniel-mar 3
## Resource location
267 daniel-mar 4
 
5
Obfuscated standalone filters:
375 daniel-mar 6
- Windows resource: OBFS\16\0 (previously RCDATA\16001\0)
7
- MacOS resource: 'obFS' 16 (previously 'DATA' 16001)
267 daniel-mar 8
 
9
Normal standalone filters:
375 daniel-mar 10
- Windows resource: PARM\16\0 (previously PARM\16000\0)
11
- MacOS resource: 'PARM' 16 (previously 'PARM' 16000)
267 daniel-mar 12
 
271 daniel-mar 13
## Implementation
270 daniel-mar 14
 
292 daniel-mar 15
Defined in **ff.h**, implemented in **obfusc.c**:
267 daniel-mar 16
 
508 daniel-mar 17
    // Implements Obfusc V7.
18
    // Returns a seed1 and seed2 which need to be stored in the executable code.
19
    obfusc(PARM_T* pparm, uint64_t* out_initial_seed, uint64_t* out_initial_seed2);
282 daniel-mar 20
 
21
    // In V1+V2: Seed is hardcoded
317 daniel-mar 22
    // In V3:    Seed is in PARM (field "unknown2")
508 daniel-mar 23
    // In V4-V7: Seed is in the program code and will me modified with a binary search+replace
271 daniel-mar 24
    void deobfusc(PARM_T* pparm);
25
 
508 daniel-mar 26
### Obfuscation "Version 7"
27
 
28
Introduced in **Filter Foundry 1.7.0.17**
29
 
30
Now, there are two 64-bit seeds:
31
 
32
Initial seed 1: `0x7416972a52830517` (is in the code segment)
33
Initial seed 2: `0xEF87A2F13E1F2186` (is in the data segment)
34
 
35
First, XOR-Shift64 using seed 2, then ROL shift, then XOR-Shift32 like in Obfusc V6.
36
 
347 daniel-mar 37
### Obfuscation "Version 6"
38
 
39
Introduced in **Filter Foundry 1.7.0.10**
40
 
441 daniel-mar 41
First, the fields `unknown1`, `unknown2`, aned `unknown3` are set to 0.
347 daniel-mar 42
 
348 daniel-mar 43
A 64 bit seed will be generated.
349 daniel-mar 44
On Windows, the seed is the ECMA 182 CRC64 checksum of the PARM.
507 daniel-mar 45
On Macintosh, it stays at the default value `0x38AD972A52830517` (before 1.7.0.17) or
46
`0x7416972a52830517` (beginning with 1.7.0.17).
349 daniel-mar 47
(because the manipulation of the binary code is not implemented).
348 daniel-mar 48
 
349 daniel-mar 49
Then, the CRC32b checksum of the PARM will be written to `unknown1`.
50
 
51
The PARM will then be XORed with a random data stream of the lower 32 bits of the 64 bit seed.
347 daniel-mar 52
The algorithm is the XORshift which was introcuced in obfuscation version 2.
53
Unlike obfuscation version 3-5, while generating and applying the random data
54
stream, no bytes are skipped.
55
 
348 daniel-mar 56
After this, PARM will be XORed with the 64 bit seed,
57
which will be ROLed by 1 bit after each byte:
347 daniel-mar 58
 
348 daniel-mar 59
    uint64_t rol_u64(uint64_t value, uint64_t by) {
60
        return value << by | value >> (sizeof(uint64_t) * 8 - by);
61
    }
62
 
63
The 64 bit seed is stored in the executable.
64
 
347 daniel-mar 65
The DWORD value `0x00000006` will be stored at field `unknown2`
66
(byte 0x30..0x33; the field is not used in the `PARM` resource).
67
 
68
During de-obfuscation, the program will check if the checksum in `unknown1`
69
matches. If it does not match, the data will be discarded.
70
 
292 daniel-mar 71
### Obfuscation "Version 5"
72
 
73
Introduced in **Filter Foundry 1.7.0.8**
74
 
75
Obfuscation version 5 is the same as version 4, but there is a constraint
311 daniel-mar 76
that the seed must be equal to the CRC32b checksum of the deobfuscated PARM.
292 daniel-mar 77
This is done to check the integrity of the deobfuscation.
311 daniel-mar 78
 
309 daniel-mar 79
Also, the xor-shifting is intentionally incompatible with version 4
311 daniel-mar 80
(to avoid downgrade-attacks) by XORing the initial seed with 0xFFFFFFFF.
292 daniel-mar 81
 
329 daniel-mar 82
The DWORD value `0x00000005` will be stored at field `unknown2`
83
(byte 0x30..0x33; the field is not used in the `PARM` resource).
84
 
85
While generating and applying the random data stream, the bytes
86
0x30..0x33 (the location where the version info is stored) are skipped,
87
like in version 3.
88
 
276 daniel-mar 89
### Obfuscation "Version 4"
90
 
292 daniel-mar 91
Introduced in **Filter Foundry 1.7.0.7**
276 daniel-mar 92
 
93
It is not compiler-dependant, but different between every standalone filter.
94
 
277 daniel-mar 95
Windows version:
276 daniel-mar 96
The binary code of the 8BF file will be manipulated during building
282 daniel-mar 97
to store the seed into the `deobfusc()` function.
98
The placeholder value is `OBFUSC_V4_DEFAULT_SEED 0x52830517`
99
This allows that 32-bit and 64-bit filters are "cross built".
276 daniel-mar 100
 
277 daniel-mar 101
(Theoretical) Macintosh version:
329 daniel-mar 102
Obfuscation and deobfuscation has the seed `0x52830517`, since the
277 daniel-mar 103
manipulation of the binary code is not implemented.
104
 
282 daniel-mar 105
Algorithm: XOR-Shift like in version 2, but the seed is individual for
276 daniel-mar 106
each individual built standalone filter.
107
 
329 daniel-mar 108
The DWORD value `0x00000004` will be stored at field `unknown2`
109
(byte 0x30..0x33; the field is not used in the `PARM` resource).
276 daniel-mar 110
 
329 daniel-mar 111
While generating and applying the random data stream, the bytes
112
0x30..0x33 (the location where the version info is stored) are skipped,
113
like in version 3.
114
 
271 daniel-mar 115
### Obfuscation "Version 3"
116
 
292 daniel-mar 117
Introduced in **Filter Foundry 1.7.0.5**
267 daniel-mar 118
 
329 daniel-mar 119
A random seed is chosen and written to field `unknown2` (byte 0x30..0x33).
267 daniel-mar 120
 
329 daniel-mar 121
Then, the `PARM` resource will be obfuscated by applying an XOR operation to a random data stream:
267 daniel-mar 122
 
329 daniel-mar 123
    unsigned char *p;
124
    *p++ ^= (int)(rand() * 1.0 / (RAND_MAX + 1) * 256);
125
 
126
Bytes 0x30..0x33 (the location where the seed is stored) are skipped.
127
 
128
The `rand()` operation is compiler-dependant, and therefore the resource cannot be exchanged between plugins.
129
 
270 daniel-mar 130
32 bit plugin is built with OpenWatcom (for Win95 compatibility) which has following formula:
131
 
132
    int rand_openwatcom(unsigned int* seed) {
133
            *seed = *seed * 1103515245L + 12345L;
134
            return (*seed >> 16) & 0x7fff; /* Scale between 0 and RAND_MAX */
135
    }
136
 
271 daniel-mar 137
64 bit plugin is built with Visual C++ which has following formula:
270 daniel-mar 138
 
139
    int rand_msvcc(unsigned int* seed) {
272 daniel-mar 140
            *seed = *seed * 214013L + 2531011L;
141
            return (*seed >> 16) & 0x7fff; /* Scale between 0 and RAND_MAX */
270 daniel-mar 142
    }
143
 
271 daniel-mar 144
### Obfuscation "Version 2"
267 daniel-mar 145
 
292 daniel-mar 146
Introduced in **Filter Foundry 1.7b1**
267 daniel-mar 147
 
329 daniel-mar 148
It is compiler-independent!
267 daniel-mar 149
 
150
Algorithm: [XOR-Shift](https://de.wikipedia.org/wiki/Xorshift "XOR-Shift") with hardcoded seed `0x95d4a68f`.
151
 
152
    x32 = 0x95d4a68f;
153
    for(i = size, p = pparm; i--;) {
272 daniel-mar 154
            x32 ^= x32 << 13;
155
            x32 ^= x32 >> 17;
156
            x32 ^= x32 << 5;
157
            *p++ ^= x32;
267 daniel-mar 158
    }
159
 
271 daniel-mar 160
### Obfuscation "Version 1"
267 daniel-mar 161
 
162
Introduced in **Filter Foundry 1.4b8,9,10**
163
 
329 daniel-mar 164
It is compiler-dependant, and therefore the resource cannot be exchanged between plugins!
267 daniel-mar 165
 
166
Algorithm: XOR with `rand()`-stream with hardcoded seed `0xdc43df3c`.
167
 
168
    srand(0xdc43df3c);
169
    for(i = size, p = pparm; i--;) {
272 daniel-mar 170
            *p++ ^= rand();
271 daniel-mar 171
    }
172
 
173
The plugin is built with Visual C++ which has following formula:
174
 
175
    int rand_msvcc(unsigned int* seed) {
272 daniel-mar 176
            *seed = *seed * 214013L + 2531011L;
177
            return (*seed >> 16) & 0x7fff; /* Scale between 0 and RAND_MAX */
271 daniel-mar 178
    }
179