1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
|
/*
Definitions for the REGF registry file format as used by
Windows NT4 and above.
Copyright (C) 2005 Jelmer Vernooij, jelmer@samba.org
Copyright (C) 2006 Wilco Baan Hofman, wilco@baanhofman.nl
Based on two files from Samba 3:
regedit.c by Richard Sharpe
regfio.c by Jerry Carter
*/
interface regf
{
const int REGF_OFFSET_NONE = 0xffffffff;
/*
* Registry version number
* 1.2.0.1 for WinNT 3.51
* 1.3.0.1 for WinNT 4
* 1.5.0.1 for WinXP
*/
[noprint] struct regf_version {
[value(1)] uint32 major;
[value(3)] uint32 minor;
[value(0)] uint32 release;
[value(1)] uint32 build;
};
/*
"regf" is obviously the abbreviation for "Registry file". "regf" is the
signature of the header-block which is always 4kb in size, although only
the first 64 bytes seem to be used and a checksum is calculated over
the first 0x200 bytes only!
*/
[public,noprint] struct regf_hdr {
[charset(DOS)] uint8 REGF_ID[4]; /* 'regf' */
uint32 update_counter1;
uint32 update_counter2;
NTTIME modtime;
regf_version version;
uint32 data_offset;
uint32 last_block;
[value(1)] uint32 uk7; /* 1 */
[charset(UTF16)] uint16 description[0x40];
uint32 padding[83]; /* Padding */
/* Checksum of first 0x200 bytes XOR-ed */
uint32 chksum;
};
/*
hbin probably means hive-bin (i.e. hive-container)
This block is always a multiple
of 4kb in size.
*/
[public,noprint] struct hbin_block {
[charset(DOS)] uint8 HBIN_ID[4]; /* hbin */
uint32 offset_from_first; /* Offset from 1st hbin-Block */
uint32 offset_to_next; /* Offset to the next hbin-Block */
uint32 unknown[2];
NTTIME last_change;
uint32 block_size; /* Block size (including the header!) */
uint8 data[offset_to_next-0x20];
/* data is filled with:
uint32 length;
Negative if in used, positive otherwise
Always a multiple of 8
uint8_t data[length];
Free space marker if 0xffffffff
*/
};
[noprint] enum reg_key_type {
REG_ROOT_KEY = 0x20,
REG_SUB_KEY = 0x2C,
REG_SYM_LINK = 0x10
};
/*
The nk-record can be treated as a combination of tree-record and
key-record of the win 95 registry.
*/
[public,noprint] struct nk_block {
[charset(DOS)] uint8 header[2];
reg_key_type type;
NTTIME last_change;
uint32 uk1;
uint32 parent_offset;
uint32 num_subkeys;
uint32 uk2;
uint32 subkeys_offset;
uint32 unknown_offset;
uint32 num_values;
uint32 values_offset; /* Points to a list of offsets of vk-records */
uint32 sk_offset;
uint32 clsname_offset;
uint32 unk3[5];
[value(strlen(key_name))] uint16 name_length;
uint16 clsname_length;
[charset(DOS)] uint8 key_name[name_length];
};
/* sk (? Security Key ?) is the ACL of the registry. */
[noprint,public] struct sk_block {
[charset(DOS)] uint8 header[2];
uint16 tag;
uint32 prev_offset;
uint32 next_offset;
uint32 ref_cnt;
uint32 rec_size;
uint8 sec_desc[rec_size];
};
[noprint] struct lh_hash {
uint32 nk_offset;
uint32 base37; /* base37 of key name */
};
/* Subkey listing with hash of first 4 characters */
[public,noprint] struct lh_block {
[charset(DOS)] uint8 header[2];
uint16 key_count;
lh_hash hr[key_count];
};
[public,noprint] struct li_block {
[charset(DOS)] uint8 header[2];
uint16 key_count;
uint32 nk_offset[key_count];
};
[public,noprint] struct ri_block {
[charset(DOS)] uint8 header[2];
uint16 key_count;
uint32 offset[key_count]; /* li/lh offset */
};
/* The vk-record consists information to a single value (value key). */
[public,noprint] struct vk_block {
[charset(DOS)] uint8 header[2];
[value(strlen(data_name))] uint16 name_length;
uint32 data_length; /* If top-bit set, offset contains the data */
uint32 data_offset;
uint32 data_type;
uint16 flag; /* =1, has name, else no name (=Default). */
uint16 unk1;
[charset(DOS)] uint8 data_name[name_length];
};
[noprint] struct hash_record {
uint32 nk_offset;
[charset(DOS)] uint8 hash[4];
};
/*
The lf-record is the counterpart to the RGKN-record (the
hash-function)
*/
[public,noprint] struct lf_block {
[charset(DOS)] uint8 header[2];
uint16 key_count;
hash_record hr[key_count]; /* Array of hash records, depending on key_count */
};
}
|