libhfs.h revision 1.2.4.2 1 1.2.4.2 rmind /* $NetBSD: libhfs.h,v 1.2.4.2 2007/03/12 06:14:55 rmind Exp $ */
2 1.2.4.2 rmind
3 1.2.4.2 rmind /*-
4 1.2.4.2 rmind * Copyright (c) 2005, 2007 The NetBSD Foundation, Inc.
5 1.2.4.2 rmind * All rights reserved.
6 1.2.4.2 rmind *
7 1.2.4.2 rmind * This code is derived from software contributed to The NetBSD Foundation
8 1.2.4.2 rmind * by Yevgeny Binder and Dieter Baron.
9 1.2.4.2 rmind *
10 1.2.4.2 rmind * Redistribution and use in source and binary forms, with or without
11 1.2.4.2 rmind * modification, are permitted provided that the following conditions
12 1.2.4.2 rmind * are met:
13 1.2.4.2 rmind * 1. Redistributions of source code must retain the above copyright
14 1.2.4.2 rmind * notice, this list of conditions and the following disclaimer.
15 1.2.4.2 rmind * 2. Redistributions in binary form must reproduce the above copyright
16 1.2.4.2 rmind * notice, this list of conditions and the following disclaimer in the
17 1.2.4.2 rmind * documentation and/or other materials provided with the distribution.
18 1.2.4.2 rmind *
19 1.2.4.2 rmind * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 1.2.4.2 rmind * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 1.2.4.2 rmind * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 1.2.4.2 rmind * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 1.2.4.2 rmind * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 1.2.4.2 rmind * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 1.2.4.2 rmind * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 1.2.4.2 rmind * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 1.2.4.2 rmind * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 1.2.4.2 rmind * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 1.2.4.2 rmind * POSSIBILITY OF SUCH DAMAGE.
30 1.2.4.2 rmind */
31 1.2.4.2 rmind
32 1.2.4.2 rmind #ifndef _FS_HFS_LIBHFS_H_
33 1.2.4.2 rmind #define _FS_HFS_LIBHFS_H_
34 1.2.4.2 rmind
35 1.2.4.2 rmind #include <sys/endian.h>
36 1.2.4.2 rmind #include <sys/param.h>
37 1.2.4.2 rmind #include <sys/mount.h> /* needs to go after sys/param.h or compile fails */
38 1.2.4.2 rmind #include <sys/types.h>
39 1.2.4.2 rmind #if defined(_KERNEL)
40 1.2.4.2 rmind #include <sys/kernel.h>
41 1.2.4.2 rmind #include <sys/systm.h>
42 1.2.4.2 rmind #include <machine/stdarg.h>
43 1.2.4.2 rmind #include <sys/fcntl.h>
44 1.2.4.2 rmind #endif /* defined(_KERNEL) */
45 1.2.4.2 rmind
46 1.2.4.2 rmind #if !defined(_KERNEL) && !defined(STANDALONE)
47 1.2.4.2 rmind #include <fcntl.h>
48 1.2.4.2 rmind #include <iconv.h>
49 1.2.4.2 rmind #include <stdarg.h>
50 1.2.4.2 rmind #include <stdint.h>
51 1.2.4.2 rmind #include <stdio.h>
52 1.2.4.2 rmind #include <stdlib.h>
53 1.2.4.2 rmind #include <unistd.h>
54 1.2.4.2 rmind #endif /* !defined(_KERNEL) && !defined(STANDALONE) */
55 1.2.4.2 rmind
56 1.2.4.2 rmind #ifndef va_list
57 1.2.4.2 rmind #define va_list _BSD_VA_LIST_
58 1.2.4.2 rmind #endif /* !va_list */
59 1.2.4.2 rmind
60 1.2.4.2 rmind #define max(A,B) ((A) > (B) ? (A):(B))
61 1.2.4.2 rmind #define min(A,B) ((A) < (B) ? (A):(B))
62 1.2.4.2 rmind
63 1.2.4.2 rmind
64 1.2.4.2 rmind /* Macros to handle errors in this library. Not recommended outside libhfs.c */
65 1.2.4.2 rmind #define HFS_LIBERR(format, ...) \
66 1.2.4.2 rmind do{ hfslib_error(format, __FILE__, __LINE__ , ##__VA_ARGS__); \
67 1.2.4.2 rmind goto error; } while(/*CONSTCOND*/ 0)
68 1.2.4.2 rmind
69 1.2.4.2 rmind #if 0
70 1.2.4.2 rmind #pragma mark Constants (on-disk)
71 1.2.4.2 rmind #endif
72 1.2.4.2 rmind
73 1.2.4.2 rmind
74 1.2.4.2 rmind enum
75 1.2.4.2 rmind {
76 1.2.4.2 rmind HFS_SIG_HFSP = 0x482B, /* 'H+' */
77 1.2.4.2 rmind HFS_SIG_HFSX = 0x4858, /* 'HX' */
78 1.2.4.2 rmind HFS_SIG_HFS = 0x4244 /* 'BD' */
79 1.2.4.2 rmind }; /* volume signatures */
80 1.2.4.2 rmind
81 1.2.4.2 rmind typedef enum
82 1.2.4.2 rmind {
83 1.2.4.2 rmind /* bits 0-6 are reserved */
84 1.2.4.2 rmind HFS_VOL_HWLOCK = 7,
85 1.2.4.2 rmind HFS_VOL_UNMOUNTED = 8,
86 1.2.4.2 rmind HFS_VOL_BADBLOCKS = 9,
87 1.2.4.2 rmind HFS_VOL_NOCACHE = 10,
88 1.2.4.2 rmind HFS_VOL_DIRTY = 11,
89 1.2.4.2 rmind HFS_VOL_CNIDS_RECYCLED = 12,
90 1.2.4.2 rmind HFS_VOL_JOURNALED = 13,
91 1.2.4.2 rmind /* bit 14 is reserved */
92 1.2.4.2 rmind HFS_VOL_SWLOCK = 15
93 1.2.4.2 rmind /* bits 16-31 are reserved */
94 1.2.4.2 rmind } hfs_volume_attribute_bit; /* volume header attribute bits */
95 1.2.4.2 rmind
96 1.2.4.2 rmind typedef enum
97 1.2.4.2 rmind {
98 1.2.4.2 rmind HFS_LEAFNODE = -1,
99 1.2.4.2 rmind HFS_INDEXNODE = 0,
100 1.2.4.2 rmind HFS_HEADERNODE = 1,
101 1.2.4.2 rmind HFS_MAPNODE = 2
102 1.2.4.2 rmind } hfs_node_kind; /* btree node kinds */
103 1.2.4.2 rmind
104 1.2.4.2 rmind enum
105 1.2.4.2 rmind {
106 1.2.4.2 rmind HFS_BAD_CLOSE_MASK = 0x00000001,
107 1.2.4.2 rmind HFS_BIG_KEYS_MASK = 0x00000002,
108 1.2.4.2 rmind HFS_VAR_INDEX_KEYS_MASK = 0x00000004
109 1.2.4.2 rmind }; /* btree header attribute masks */
110 1.2.4.2 rmind
111 1.2.4.2 rmind typedef enum
112 1.2.4.2 rmind {
113 1.2.4.2 rmind HFS_CNID_ROOT_PARENT = 1,
114 1.2.4.2 rmind HFS_CNID_ROOT_FOLDER = 2,
115 1.2.4.2 rmind HFS_CNID_EXTENTS = 3,
116 1.2.4.2 rmind HFS_CNID_CATALOG = 4,
117 1.2.4.2 rmind HFS_CNID_BADBLOCKS = 5,
118 1.2.4.2 rmind HFS_CNID_ALLOCATION = 6,
119 1.2.4.2 rmind HFS_CNID_STARTUP = 7,
120 1.2.4.2 rmind HFS_CNID_ATTRIBUTES = 8,
121 1.2.4.2 rmind /* CNIDs 9-13 are reserved */
122 1.2.4.2 rmind HFS_CNID_REPAIR = 14,
123 1.2.4.2 rmind HFS_CNID_TEMP = 15,
124 1.2.4.2 rmind HFS_CNID_USER = 16
125 1.2.4.2 rmind } hfs_special_cnid; /* special CNID values */
126 1.2.4.2 rmind
127 1.2.4.2 rmind typedef enum
128 1.2.4.2 rmind {
129 1.2.4.2 rmind HFS_REC_FLDR = 0x0001,
130 1.2.4.2 rmind HFS_REC_FILE = 0x0002,
131 1.2.4.2 rmind HFS_REC_FLDR_THREAD = 0x0003,
132 1.2.4.2 rmind HFS_REC_FILE_THREAD = 0x0004
133 1.2.4.2 rmind } hfs_catalog_rec_kind; /* catalog record types */
134 1.2.4.2 rmind
135 1.2.4.2 rmind enum
136 1.2.4.2 rmind {
137 1.2.4.2 rmind HFS_JOURNAL_ON_DISK_MASK = 0x00000001, /* journal on same volume */
138 1.2.4.2 rmind HFS_JOURNAL_ON_OTHER_MASK = 0x00000002, /* journal elsewhere */
139 1.2.4.2 rmind HFS_JOURNAL_NEEDS_INIT_MASK = 0x00000004
140 1.2.4.2 rmind }; /* journal flag masks */
141 1.2.4.2 rmind
142 1.2.4.2 rmind enum
143 1.2.4.2 rmind {
144 1.2.4.2 rmind HFS_JOURNAL_HEADER_MAGIC = 0x4a4e4c78,
145 1.2.4.2 rmind HFS_JOURNAL_ENDIAN_MAGIC = 0x12345678
146 1.2.4.2 rmind }; /* journal magic numbers */
147 1.2.4.2 rmind
148 1.2.4.2 rmind enum
149 1.2.4.2 rmind {
150 1.2.4.2 rmind HFS_DATAFORK = 0x00,
151 1.2.4.2 rmind HFS_RSRCFORK = 0xFF
152 1.2.4.2 rmind }; /* common fork types */
153 1.2.4.2 rmind
154 1.2.4.2 rmind enum
155 1.2.4.2 rmind {
156 1.2.4.2 rmind HFS_KEY_CASEFOLD = 0xCF,
157 1.2.4.2 rmind HFS_KEY_BINARY = 0XBC
158 1.2.4.2 rmind }; /* catalog key comparison method types */
159 1.2.4.2 rmind
160 1.2.4.2 rmind enum
161 1.2.4.2 rmind {
162 1.2.4.2 rmind HFS_MIN_CAT_KEY_LEN = 6,
163 1.2.4.2 rmind HFS_MAX_CAT_KEY_LEN = 516,
164 1.2.4.2 rmind HFS_MAX_EXT_KEY_LEN = 10
165 1.2.4.2 rmind };
166 1.2.4.2 rmind
167 1.2.4.2 rmind enum {
168 1.2.4.2 rmind HFS_HARD_LINK_FILE_TYPE = 0x686C6E6B, /* 'hlnk' */
169 1.2.4.2 rmind HFS_HFSLUS_CREATOR = 0x6866732B /* 'hfs+' */
170 1.2.4.2 rmind };
171 1.2.4.2 rmind
172 1.2.4.2 rmind
173 1.2.4.2 rmind #if 0
174 1.2.4.2 rmind #pragma mark -
175 1.2.4.2 rmind #pragma mark Constants (custom)
176 1.2.4.2 rmind #endif
177 1.2.4.2 rmind
178 1.2.4.2 rmind
179 1.2.4.2 rmind /* number of bytes between start of volume and volume header */
180 1.2.4.2 rmind #define HFS_VOLUME_HEAD_RESERVE_SIZE 1024
181 1.2.4.2 rmind
182 1.2.4.2 rmind typedef enum
183 1.2.4.2 rmind {
184 1.2.4.2 rmind HFS_CATALOG_FILE = 1,
185 1.2.4.2 rmind HFS_EXTENTS_FILE = 2,
186 1.2.4.2 rmind HFS_ATTRIBUTES_FILE = 3
187 1.2.4.2 rmind } hfs_btree_file_type; /* btree file kinds */
188 1.2.4.2 rmind
189 1.2.4.2 rmind
190 1.2.4.2 rmind #if 0
191 1.2.4.2 rmind #pragma mark -
192 1.2.4.2 rmind #pragma mark On-Disk Types (Mac OS specific)
193 1.2.4.2 rmind #endif
194 1.2.4.2 rmind
195 1.2.4.2 rmind typedef uint32_t hfs_macos_type_code; /* four 1-byte char field */
196 1.2.4.2 rmind
197 1.2.4.2 rmind typedef struct
198 1.2.4.2 rmind {
199 1.2.4.2 rmind int16_t v;
200 1.2.4.2 rmind int16_t h;
201 1.2.4.2 rmind } hfs_macos_point_t;
202 1.2.4.2 rmind
203 1.2.4.2 rmind typedef struct
204 1.2.4.2 rmind {
205 1.2.4.2 rmind int16_t t; /* top */
206 1.2.4.2 rmind int16_t l; /* left */
207 1.2.4.2 rmind int16_t b; /* bottom */
208 1.2.4.2 rmind int16_t r; /* right */
209 1.2.4.2 rmind } hfs_macos_rect_t;
210 1.2.4.2 rmind
211 1.2.4.2 rmind typedef struct
212 1.2.4.2 rmind {
213 1.2.4.2 rmind hfs_macos_type_code file_type;
214 1.2.4.2 rmind hfs_macos_type_code file_creator;
215 1.2.4.2 rmind uint16_t finder_flags;
216 1.2.4.2 rmind hfs_macos_point_t location;
217 1.2.4.2 rmind uint16_t reserved;
218 1.2.4.2 rmind } hfs_macos_file_info_t;
219 1.2.4.2 rmind
220 1.2.4.2 rmind typedef struct
221 1.2.4.2 rmind {
222 1.2.4.2 rmind int16_t reserved[4];
223 1.2.4.2 rmind uint16_t extended_finder_flags;
224 1.2.4.2 rmind int16_t reserved2;
225 1.2.4.2 rmind int32_t put_away_folder_cnid;
226 1.2.4.2 rmind } hfs_macos_extended_file_info_t;
227 1.2.4.2 rmind
228 1.2.4.2 rmind typedef struct
229 1.2.4.2 rmind {
230 1.2.4.2 rmind hfs_macos_rect_t window_bounds;
231 1.2.4.2 rmind uint16_t finder_flags;
232 1.2.4.2 rmind hfs_macos_point_t location;
233 1.2.4.2 rmind uint16_t reserved;
234 1.2.4.2 rmind } hfs_macos_folder_info_t;
235 1.2.4.2 rmind
236 1.2.4.2 rmind typedef struct
237 1.2.4.2 rmind {
238 1.2.4.2 rmind hfs_macos_point_t scroll_position;
239 1.2.4.2 rmind int32_t reserved;
240 1.2.4.2 rmind uint16_t extended_finder_flags;
241 1.2.4.2 rmind int16_t reserved2;
242 1.2.4.2 rmind int32_t put_away_folder_cnid;
243 1.2.4.2 rmind } hfs_macos_extended_folder_info_t;
244 1.2.4.2 rmind
245 1.2.4.2 rmind
246 1.2.4.2 rmind #if 0
247 1.2.4.2 rmind #pragma mark -
248 1.2.4.2 rmind #pragma mark On-Disk Types
249 1.2.4.2 rmind #endif
250 1.2.4.2 rmind
251 1.2.4.2 rmind typedef uint16_t unichar_t;
252 1.2.4.2 rmind
253 1.2.4.2 rmind typedef uint32_t hfs_cnid_t;
254 1.2.4.2 rmind
255 1.2.4.2 rmind
256 1.2.4.2 rmind typedef struct
257 1.2.4.2 rmind {
258 1.2.4.2 rmind uint16_t length;
259 1.2.4.2 rmind unichar_t unicode[255];
260 1.2.4.2 rmind } hfs_unistr255_t;
261 1.2.4.2 rmind
262 1.2.4.2 rmind typedef struct
263 1.2.4.2 rmind {
264 1.2.4.2 rmind uint32_t start_block;
265 1.2.4.2 rmind uint32_t block_count;
266 1.2.4.2 rmind } hfs_extent_descriptor_t;
267 1.2.4.2 rmind
268 1.2.4.2 rmind typedef hfs_extent_descriptor_t hfs_extent_record_t[8];
269 1.2.4.2 rmind
270 1.2.4.2 rmind typedef struct hfs_fork_t
271 1.2.4.2 rmind {
272 1.2.4.2 rmind uint64_t logical_size;
273 1.2.4.2 rmind uint32_t clump_size;
274 1.2.4.2 rmind uint32_t total_blocks;
275 1.2.4.2 rmind hfs_extent_record_t extents;
276 1.2.4.2 rmind } hfs_fork_t;
277 1.2.4.2 rmind
278 1.2.4.2 rmind typedef struct
279 1.2.4.2 rmind {
280 1.2.4.2 rmind uint16_t signature;
281 1.2.4.2 rmind uint16_t version;
282 1.2.4.2 rmind uint32_t attributes;
283 1.2.4.2 rmind uint32_t last_mounting_version;
284 1.2.4.2 rmind uint32_t journal_info_block;
285 1.2.4.2 rmind
286 1.2.4.2 rmind uint32_t date_created;
287 1.2.4.2 rmind uint32_t date_modified;
288 1.2.4.2 rmind uint32_t date_backedup;
289 1.2.4.2 rmind uint32_t date_checked;
290 1.2.4.2 rmind
291 1.2.4.2 rmind uint32_t file_count;
292 1.2.4.2 rmind uint32_t folder_count;
293 1.2.4.2 rmind
294 1.2.4.2 rmind uint32_t block_size;
295 1.2.4.2 rmind uint32_t total_blocks;
296 1.2.4.2 rmind uint32_t free_blocks;
297 1.2.4.2 rmind
298 1.2.4.2 rmind uint32_t next_alloc_block;
299 1.2.4.2 rmind uint32_t rsrc_clump_size;
300 1.2.4.2 rmind uint32_t data_clump_size;
301 1.2.4.2 rmind hfs_cnid_t next_cnid;
302 1.2.4.2 rmind
303 1.2.4.2 rmind uint32_t write_count;
304 1.2.4.2 rmind uint64_t encodings;
305 1.2.4.2 rmind
306 1.2.4.2 rmind uint32_t finder_info[8];
307 1.2.4.2 rmind
308 1.2.4.2 rmind hfs_fork_t allocation_file;
309 1.2.4.2 rmind hfs_fork_t extents_file;
310 1.2.4.2 rmind hfs_fork_t catalog_file;
311 1.2.4.2 rmind hfs_fork_t attributes_file;
312 1.2.4.2 rmind hfs_fork_t startup_file;
313 1.2.4.2 rmind } hfs_volume_header_t;
314 1.2.4.2 rmind
315 1.2.4.2 rmind typedef struct
316 1.2.4.2 rmind {
317 1.2.4.2 rmind uint32_t flink;
318 1.2.4.2 rmind uint32_t blink;
319 1.2.4.2 rmind int8_t kind;
320 1.2.4.2 rmind uint8_t height;
321 1.2.4.2 rmind uint16_t num_recs;
322 1.2.4.2 rmind uint16_t reserved;
323 1.2.4.2 rmind } hfs_node_descriptor_t;
324 1.2.4.2 rmind
325 1.2.4.2 rmind typedef struct
326 1.2.4.2 rmind {
327 1.2.4.2 rmind uint16_t tree_depth;
328 1.2.4.2 rmind uint32_t root_node;
329 1.2.4.2 rmind uint32_t leaf_recs;
330 1.2.4.2 rmind uint32_t first_leaf;
331 1.2.4.2 rmind uint32_t last_leaf;
332 1.2.4.2 rmind uint16_t node_size;
333 1.2.4.2 rmind uint16_t max_key_len;
334 1.2.4.2 rmind uint32_t total_nodes;
335 1.2.4.2 rmind uint32_t free_nodes;
336 1.2.4.2 rmind uint16_t reserved;
337 1.2.4.2 rmind uint32_t clump_size; /* misaligned */
338 1.2.4.2 rmind uint8_t btree_type;
339 1.2.4.2 rmind uint8_t keycomp_type;
340 1.2.4.2 rmind uint32_t attributes; /* long aligned again */
341 1.2.4.2 rmind uint32_t reserved2[16];
342 1.2.4.2 rmind } hfs_header_record_t;
343 1.2.4.2 rmind
344 1.2.4.2 rmind typedef struct
345 1.2.4.2 rmind {
346 1.2.4.2 rmind uint16_t key_len;
347 1.2.4.2 rmind hfs_cnid_t parent_cnid;
348 1.2.4.2 rmind hfs_unistr255_t name;
349 1.2.4.2 rmind } hfs_catalog_key_t;
350 1.2.4.2 rmind
351 1.2.4.2 rmind typedef struct
352 1.2.4.2 rmind {
353 1.2.4.2 rmind uint16_t key_length;
354 1.2.4.2 rmind uint8_t fork_type;
355 1.2.4.2 rmind uint8_t padding;
356 1.2.4.2 rmind hfs_cnid_t file_cnid;
357 1.2.4.2 rmind uint32_t start_block;
358 1.2.4.2 rmind } hfs_extent_key_t;
359 1.2.4.2 rmind
360 1.2.4.2 rmind typedef struct
361 1.2.4.2 rmind {
362 1.2.4.2 rmind uint32_t owner_id;
363 1.2.4.2 rmind uint32_t group_id;
364 1.2.4.2 rmind uint8_t admin_flags;
365 1.2.4.2 rmind uint8_t owner_flags;
366 1.2.4.2 rmind uint16_t file_mode;
367 1.2.4.2 rmind union
368 1.2.4.2 rmind {
369 1.2.4.2 rmind uint32_t inode_num;
370 1.2.4.2 rmind uint32_t link_count;
371 1.2.4.2 rmind uint32_t raw_device;
372 1.2.4.2 rmind } special;
373 1.2.4.2 rmind } hfs_bsd_data_t;
374 1.2.4.2 rmind
375 1.2.4.2 rmind typedef struct
376 1.2.4.2 rmind {
377 1.2.4.2 rmind int16_t rec_type;
378 1.2.4.2 rmind uint16_t flags;
379 1.2.4.2 rmind uint32_t valence;
380 1.2.4.2 rmind hfs_cnid_t cnid;
381 1.2.4.2 rmind uint32_t date_created;
382 1.2.4.2 rmind uint32_t date_content_mod;
383 1.2.4.2 rmind uint32_t date_attrib_mod;
384 1.2.4.2 rmind uint32_t date_accessed;
385 1.2.4.2 rmind uint32_t date_backedup;
386 1.2.4.2 rmind hfs_bsd_data_t bsd;
387 1.2.4.2 rmind hfs_macos_folder_info_t user_info;
388 1.2.4.2 rmind hfs_macos_extended_folder_info_t finder_info;
389 1.2.4.2 rmind uint32_t text_encoding;
390 1.2.4.2 rmind uint32_t reserved;
391 1.2.4.2 rmind } hfs_folder_record_t;
392 1.2.4.2 rmind
393 1.2.4.2 rmind typedef struct
394 1.2.4.2 rmind {
395 1.2.4.2 rmind int16_t rec_type;
396 1.2.4.2 rmind uint16_t flags;
397 1.2.4.2 rmind uint32_t reserved;
398 1.2.4.2 rmind hfs_cnid_t cnid;
399 1.2.4.2 rmind uint32_t date_created;
400 1.2.4.2 rmind uint32_t date_content_mod;
401 1.2.4.2 rmind uint32_t date_attrib_mod;
402 1.2.4.2 rmind uint32_t date_accessed;
403 1.2.4.2 rmind uint32_t date_backedup;
404 1.2.4.2 rmind hfs_bsd_data_t bsd;
405 1.2.4.2 rmind hfs_macos_file_info_t user_info;
406 1.2.4.2 rmind hfs_macos_extended_file_info_t finder_info;
407 1.2.4.2 rmind uint32_t text_encoding;
408 1.2.4.2 rmind uint32_t reserved2;
409 1.2.4.2 rmind hfs_fork_t data_fork;
410 1.2.4.2 rmind hfs_fork_t rsrc_fork;
411 1.2.4.2 rmind } hfs_file_record_t;
412 1.2.4.2 rmind
413 1.2.4.2 rmind typedef struct
414 1.2.4.2 rmind {
415 1.2.4.2 rmind int16_t rec_type;
416 1.2.4.2 rmind int16_t reserved;
417 1.2.4.2 rmind hfs_cnid_t parent_cnid;
418 1.2.4.2 rmind hfs_unistr255_t name;
419 1.2.4.2 rmind } hfs_thread_record_t;
420 1.2.4.2 rmind
421 1.2.4.2 rmind typedef struct
422 1.2.4.2 rmind {
423 1.2.4.2 rmind uint32_t flags;
424 1.2.4.2 rmind uint32_t device_signature[8];
425 1.2.4.2 rmind uint64_t offset;
426 1.2.4.2 rmind uint64_t size;
427 1.2.4.2 rmind uint64_t reserved[32];
428 1.2.4.2 rmind } hfs_journal_info_t;
429 1.2.4.2 rmind
430 1.2.4.2 rmind typedef struct
431 1.2.4.2 rmind {
432 1.2.4.2 rmind uint32_t magic;
433 1.2.4.2 rmind uint32_t endian;
434 1.2.4.2 rmind uint64_t start;
435 1.2.4.2 rmind uint64_t end;
436 1.2.4.2 rmind uint64_t size;
437 1.2.4.2 rmind uint32_t blocklist_header_size;
438 1.2.4.2 rmind uint32_t checksum;
439 1.2.4.2 rmind uint32_t journal_header_size;
440 1.2.4.2 rmind } hfs_journal_header_t;
441 1.2.4.2 rmind
442 1.2.4.2 rmind #if 0
443 1.2.4.2 rmind #pragma mark -
444 1.2.4.2 rmind #pragma mark Custom Types
445 1.2.4.2 rmind #endif
446 1.2.4.2 rmind
447 1.2.4.2 rmind typedef struct
448 1.2.4.2 rmind {
449 1.2.4.2 rmind hfs_volume_header_t vh; /* volume header */
450 1.2.4.2 rmind hfs_header_record_t chr; /* catalog file header node record*/
451 1.2.4.2 rmind hfs_header_record_t ehr; /* extent overflow file header node record*/
452 1.2.4.2 rmind uint8_t catkeysizefieldsize; /* size of catalog file key_len field in
453 1.2.4.2 rmind * bytes (1 or 2); always 2 for HFS+ */
454 1.2.4.2 rmind uint8_t extkeysizefieldsize; /* size of extent file key_len field in
455 1.2.4.2 rmind * bytes (1 or 2); always 2 for HFS+ */
456 1.2.4.2 rmind hfs_unistr255_t name; /* volume name */
457 1.2.4.2 rmind
458 1.2.4.2 rmind /* pointer to catalog file key comparison function */
459 1.2.4.2 rmind int (*keycmp) (const void*, const void*);
460 1.2.4.2 rmind
461 1.2.4.2 rmind int journaled; /* 1 if volume is journaled, else 0 */
462 1.2.4.2 rmind hfs_journal_info_t jib; /* journal info block */
463 1.2.4.2 rmind hfs_journal_header_t jh; /* journal header */
464 1.2.4.2 rmind
465 1.2.4.2 rmind int readonly; /* 0 if mounted r/w, 1 if mounted r/o */
466 1.2.4.2 rmind void* cbdata; /* application-specific data; allocated, defined and
467 1.2.4.2 rmind * used (if desired) by the program, usually within
468 1.2.4.2 rmind * callback routines */
469 1.2.4.2 rmind } hfs_volume;
470 1.2.4.2 rmind
471 1.2.4.2 rmind typedef union
472 1.2.4.2 rmind {
473 1.2.4.2 rmind /* for leaf nodes */
474 1.2.4.2 rmind int16_t type; /* type of record: folder, file, or thread */
475 1.2.4.2 rmind hfs_folder_record_t folder;
476 1.2.4.2 rmind hfs_file_record_t file;
477 1.2.4.2 rmind hfs_thread_record_t thread;
478 1.2.4.2 rmind
479 1.2.4.2 rmind /* for pointer nodes */
480 1.2.4.2 rmind /* (using this large union for just one tiny field is not memory-efficient,
481 1.2.4.2 rmind * so change this if it becomes problematic) */
482 1.2.4.2 rmind uint32_t child; /* node number of this node's child node */
483 1.2.4.2 rmind } hfs_catalog_keyed_record_t;
484 1.2.4.2 rmind
485 1.2.4.2 rmind /*
486 1.2.4.2 rmind * These arguments are passed among libhfs without any inspection. This struct
487 1.2.4.2 rmind * is accepted by all public functions of libhfs, and passed to each callback.
488 1.2.4.2 rmind * An application dereferences each pointer to its own specific struct of
489 1.2.4.2 rmind * arguments. Callbacks must be prepared to deal with NULL values for any of
490 1.2.4.2 rmind * these fields (by providing default values to be used in lieu of that
491 1.2.4.2 rmind * argument). However, a NULL pointer to this struct is an error.
492 1.2.4.2 rmind *
493 1.2.4.2 rmind * It was decided to make one unified argument structure, rather than many
494 1.2.4.2 rmind * separate, operand-specific structures, because, when this structure is passed
495 1.2.4.2 rmind * to a public function (e.g., hfslib_open_volume()), the function may make
496 1.2.4.2 rmind * several calls (and subcalls) to various facilities, e.g., read(), malloc(),
497 1.2.4.2 rmind * and free(), all of which require their own particular arguments. The
498 1.2.4.2 rmind * facilities to be used are quite impractical to foreshadow, so the application
499 1.2.4.2 rmind * takes care of all possible calls at once. This also reinforces the idea that
500 1.2.4.2 rmind * a public call is an umbrella to a set of system calls, and all of these calls
501 1.2.4.2 rmind * must be passed arguments which do not change within the context of this
502 1.2.4.2 rmind * umbrella. (E.g., if a public function makes two calls to read(), one call
503 1.2.4.2 rmind * should not be passed a uid of root and the other passed a uid of daemon.)
504 1.2.4.2 rmind */
505 1.2.4.2 rmind typedef struct
506 1.2.4.2 rmind {
507 1.2.4.2 rmind /* The 'error' function does not take an argument. All others do. */
508 1.2.4.2 rmind
509 1.2.4.2 rmind void* allocmem;
510 1.2.4.2 rmind void* reallocmem;
511 1.2.4.2 rmind void* freemem;
512 1.2.4.2 rmind void* openvol;
513 1.2.4.2 rmind void* closevol;
514 1.2.4.2 rmind void* read;
515 1.2.4.2 rmind } hfs_callback_args;
516 1.2.4.2 rmind
517 1.2.4.2 rmind typedef struct
518 1.2.4.2 rmind {
519 1.2.4.2 rmind /* error(in_format, in_file, in_line, in_args) */
520 1.2.4.2 rmind void (*error) (const char*, const char*, int, va_list);
521 1.2.4.2 rmind
522 1.2.4.2 rmind /* allocmem(in_size, cbargs) */
523 1.2.4.2 rmind void* (*allocmem) (size_t, hfs_callback_args*);
524 1.2.4.2 rmind
525 1.2.4.2 rmind /* reallocmem(in_ptr, in_size, cbargs) */
526 1.2.4.2 rmind void* (*reallocmem) (void*, size_t, hfs_callback_args*);
527 1.2.4.2 rmind
528 1.2.4.2 rmind /* freemem(in_ptr, cbargs) */
529 1.2.4.2 rmind void (*freemem) (void*, hfs_callback_args*);
530 1.2.4.2 rmind
531 1.2.4.2 rmind /* openvol(in_volume, in_devicepath, in_offset, cbargs)
532 1.2.4.2 rmind * returns 0 on success */
533 1.2.4.2 rmind int (*openvol) (hfs_volume*, const char*, uint64_t, hfs_callback_args*);
534 1.2.4.2 rmind
535 1.2.4.2 rmind /* closevol(in_volume, cbargs) */
536 1.2.4.2 rmind void (*closevol) (hfs_volume*, hfs_callback_args*);
537 1.2.4.2 rmind
538 1.2.4.2 rmind /* read(in_volume, out_buffer, in_length, in_offset, cbargs)
539 1.2.4.2 rmind * returns 0 on success */
540 1.2.4.2 rmind int (*read) (hfs_volume*, void*, uint64_t, uint64_t,
541 1.2.4.2 rmind hfs_callback_args*);
542 1.2.4.2 rmind
543 1.2.4.2 rmind } hfs_callbacks;
544 1.2.4.2 rmind
545 1.2.4.2 rmind hfs_callbacks hfs_gcb; /* global callbacks */
546 1.2.4.2 rmind
547 1.2.4.2 rmind /*
548 1.2.4.2 rmind * global case folding table
549 1.2.4.2 rmind * (lazily initialized; see comments at bottom of hfs_open_volume())
550 1.2.4.2 rmind */
551 1.2.4.2 rmind unichar_t* hfs_gcft;
552 1.2.4.2 rmind
553 1.2.4.2 rmind #if 0
554 1.2.4.2 rmind #pragma mark -
555 1.2.4.2 rmind #pragma mark Functions
556 1.2.4.2 rmind #endif
557 1.2.4.2 rmind
558 1.2.4.2 rmind void hfslib_init(hfs_callbacks*);
559 1.2.4.2 rmind void hfslib_done(void);
560 1.2.4.2 rmind void hfslib_init_cbargs(hfs_callback_args*);
561 1.2.4.2 rmind
562 1.2.4.2 rmind int hfslib_open_volume(const char*, uint64_t, int, hfs_volume*,
563 1.2.4.2 rmind hfs_callback_args*);
564 1.2.4.2 rmind void hfslib_close_volume(hfs_volume*, hfs_callback_args*);
565 1.2.4.2 rmind
566 1.2.4.2 rmind int hfslib_path_to_cnid(hfs_volume*, hfs_cnid_t, char**, uint16_t*,
567 1.2.4.2 rmind hfs_callback_args*);
568 1.2.4.2 rmind hfs_cnid_t hfslib_find_parent_thread(hfs_volume*, hfs_cnid_t,
569 1.2.4.2 rmind hfs_thread_record_t*, hfs_callback_args*);
570 1.2.4.2 rmind int hfslib_find_catalog_record_with_cnid(hfs_volume*, hfs_cnid_t,
571 1.2.4.2 rmind hfs_catalog_keyed_record_t*, hfs_catalog_key_t*, hfs_callback_args*);
572 1.2.4.2 rmind int hfslib_find_catalog_record_with_key(hfs_volume*, hfs_catalog_key_t*,
573 1.2.4.2 rmind hfs_catalog_keyed_record_t*, hfs_callback_args*);
574 1.2.4.2 rmind int hfslib_find_extent_record_with_key(hfs_volume*, hfs_extent_key_t*,
575 1.2.4.2 rmind hfs_extent_record_t*, hfs_callback_args*);
576 1.2.4.2 rmind int hfslib_get_directory_contents(hfs_volume*, hfs_cnid_t,
577 1.2.4.2 rmind hfs_catalog_keyed_record_t**, hfs_unistr255_t**, uint32_t*,
578 1.2.4.2 rmind hfs_callback_args*);
579 1.2.4.2 rmind int hfslib_is_journal_clean(hfs_volume*);
580 1.2.4.2 rmind int hfslib_is_private_file(hfs_catalog_key_t*);
581 1.2.4.2 rmind
582 1.2.4.2 rmind int hfslib_get_hardlink(hfs_volume *, uint32_t,
583 1.2.4.2 rmind hfs_catalog_keyed_record_t *, hfs_callback_args *);
584 1.2.4.2 rmind
585 1.2.4.2 rmind size_t hfslib_read_volume_header(void*, hfs_volume_header_t*);
586 1.2.4.2 rmind size_t hfslib_reada_node(void*, hfs_node_descriptor_t*, void***, uint16_t**,
587 1.2.4.2 rmind hfs_btree_file_type, hfs_volume*, hfs_callback_args*);
588 1.2.4.2 rmind size_t hfslib_reada_node_offsets(void*, uint16_t*);
589 1.2.4.2 rmind size_t hfslib_read_header_node(void**, uint16_t*, uint16_t,
590 1.2.4.2 rmind hfs_header_record_t*, void*, void*);
591 1.2.4.2 rmind size_t hfslib_read_catalog_keyed_record(void*, hfs_catalog_keyed_record_t*,
592 1.2.4.2 rmind int16_t*, hfs_catalog_key_t*, hfs_volume*);
593 1.2.4.2 rmind size_t hfslib_read_extent_record(void*, hfs_extent_record_t*, hfs_node_kind,
594 1.2.4.2 rmind hfs_extent_key_t*, hfs_volume*);
595 1.2.4.2 rmind void hfslib_free_recs(void***, uint16_t**, uint16_t*, hfs_callback_args*);
596 1.2.4.2 rmind
597 1.2.4.2 rmind size_t hfslib_read_fork_descriptor(void*, hfs_fork_t*);
598 1.2.4.2 rmind size_t hfslib_read_extent_descriptors(void*, hfs_extent_record_t*);
599 1.2.4.2 rmind size_t hfslib_read_unistr255(void*, hfs_unistr255_t*);
600 1.2.4.2 rmind size_t hfslib_read_bsd_data(void*, hfs_bsd_data_t*);
601 1.2.4.2 rmind size_t hfslib_read_file_userinfo(void*, hfs_macos_file_info_t*);
602 1.2.4.2 rmind size_t hfslib_read_file_finderinfo(void*, hfs_macos_extended_file_info_t*);
603 1.2.4.2 rmind size_t hfslib_read_folder_userinfo(void*, hfs_macos_folder_info_t*);
604 1.2.4.2 rmind size_t hfslib_read_folder_finderinfo(void*, hfs_macos_extended_folder_info_t*);
605 1.2.4.2 rmind size_t hfslib_read_journal_info(void*, hfs_journal_info_t*);
606 1.2.4.2 rmind size_t hfslib_read_journal_header(void*, hfs_journal_header_t*);
607 1.2.4.2 rmind
608 1.2.4.2 rmind uint16_t hfslib_make_catalog_key(hfs_cnid_t, uint16_t, unichar_t*,
609 1.2.4.2 rmind hfs_catalog_key_t*);
610 1.2.4.2 rmind uint16_t hfslib_make_extent_key(hfs_cnid_t, uint8_t, uint32_t,
611 1.2.4.2 rmind hfs_extent_key_t*);
612 1.2.4.2 rmind uint16_t hfslib_get_file_extents(hfs_volume*, hfs_cnid_t, uint8_t,
613 1.2.4.2 rmind hfs_extent_descriptor_t**, hfs_callback_args*);
614 1.2.4.2 rmind int hfslib_readd_with_extents(hfs_volume*, void*, uint64_t*, uint64_t,
615 1.2.4.2 rmind uint64_t, hfs_extent_descriptor_t*, uint16_t, hfs_callback_args*);
616 1.2.4.2 rmind
617 1.2.4.2 rmind int hfslib_compare_catalog_keys_cf(const void*, const void*);
618 1.2.4.2 rmind int hfslib_compare_catalog_keys_bc(const void*, const void*);
619 1.2.4.2 rmind int hfslib_compare_extent_keys(const void*, const void*);
620 1.2.4.2 rmind
621 1.2.4.2 rmind
622 1.2.4.2 rmind /* callback wrappers */
623 1.2.4.2 rmind void hfslib_error(const char*, const char*, int, ...) __attribute__ ((format (printf, 1, 4)));
624 1.2.4.2 rmind void* hfslib_malloc(size_t, hfs_callback_args*);
625 1.2.4.2 rmind void* hfslib_realloc(void*, size_t, hfs_callback_args*);
626 1.2.4.2 rmind void hfslib_free(void*, hfs_callback_args*);
627 1.2.4.2 rmind int hfslib_openvoldevice(hfs_volume*, const char*, uint64_t,hfs_callback_args*);
628 1.2.4.2 rmind void hfslib_closevoldevice(hfs_volume*, hfs_callback_args*);
629 1.2.4.2 rmind int hfslib_readd(hfs_volume*, void*, uint64_t, uint64_t, hfs_callback_args*);
630 1.2.4.2 rmind
631 1.2.4.2 rmind #endif /* !_FS_HFS_LIBHFS_H_ */
632