File: h10db.h

package info (click to toggle)
easyh10 1.5-4
  • links: PTS
  • area: main
  • in suites: buster, stretch
  • size: 2,400 kB
  • ctags: 1,022
  • sloc: ansic: 9,050; sh: 8,387; makefile: 77
file content (485 lines) | stat: -rw-r--r-- 15,534 bytes parent folder | download | duplicates (5)
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
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
/*
 *      H10 database parser/writer.
 *
 *      Copyright (c) 2005 Nyaochi
 *		Copyright (c) 2005 Toby Corkindale (iRiver.pm).
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA, or visit
 * http://www.gnu.org/copyleft/gpl.html .
 *
 */

/* $Id: h10db.h,v 1.21 2006/02/07 00:47:53 nyaochi Exp $ */

#ifndef	__H10DB_H__
#define	__H10DB_H__

#include <time.h>

#ifdef	__cplusplus
extern "C" {
#endif/*__cplusplus*/


#define	H10DB_PATHLENGTH		0x100		/**< Maximum length of path/file name. */
#define	H10DB_NUM_DAT_FIELDS	22			/**< The number of fields in h10db_dat excluding status and unknown1. */

struct bfile;

/**
 * Structure of field descriptor.
 */
struct tag_h10db_fd {
	uint32_t	id;				/**< Field identifier. */
	uint32_t	field_type;		/**< 1: UCS2-LE String; 2: uint32_t AFAIK. */
	uint32_t	max_length;		/**< Maximum length of the field */
	uint32_t	unknown4;
	uint32_t	unknown5;
	uint32_t	has_index;		/**< 1 if this field needs an index (*.idx), otherwise 0. */
	uint32_t	unknown6;
	uint32_t	unknown7;
	ucs2_char_t index_pathname[H10DB_PATHLENGTH];	/**< Pathname of the index file */
};
typedef struct tag_h10db_fd h10db_fd_t;



/**
 * Field offset array.
 */
typedef uint16_t h10db_field_offsets_t[H10DB_NUM_DAT_FIELDS];



/**
 * Structure of H10DB.hdr
 */
struct tag_h10db_hdr {
	uint32_t	unknown1;							/**< 0 AFAIK */
	uint32_t	unknown2;							/**< 0 AFAIK */
	ucs2_char_t	pathname_dat[H10DB_PATHLENGTH];		/**< Pathname of H10DB.dat file */
	uint32_t	unknown3;							/**< 1 AFAIK */
	ucs2_char_t pathname_hdr[H10DB_PATHLENGTH];		/**< Pathname of H10DB.hdr file */
	uint32_t	unknown4;							/**< Version of the database specification? (0x0000042C) */
	uint32_t	num_dat_entries;					/**< Number of entries in H10DB.DAT */
	uint32_t	num_dat_inactive_entries;			/**< Number of inactive entries in H10DB.DAT */
	uint32_t	num_dat_fields;						/**< H10DB_NUM_DAT_FIELDS (22) AFAIK */
	h10db_fd_t	fd[H10DB_NUM_DAT_FIELDS];			/**< Field descriptors. */
													/**< 1032 bytes padding. */
	uint32_t	max_dat_field_size[H10DB_NUM_DAT_FIELDS];
	uint32_t	dat_size;							/**< Size of H10DB.dat file */
	uint32_t	unknown5;							/**< 1 AFAIK (This field exists only in 20GB MTP 2.50) */
	h10db_field_offsets_t *dat_field_offset;		/* [H10DB_MAX_ENTRY] */
	uint32_t	*dat_entry_offset;					/* [H10DB_MAX_ENTRY+1] */

	/* These fields are not serizlied in H10DB.hdr */
	uint32_t	max_entries;
	uint32_t	padding_size;
	uint32_t	has_unknown5;
};
typedef struct tag_h10db_hdr h10db_hdr_t;



/**
 * Structure of an entry in H10DB.dat.
 */
struct tag_h10db_dat {
	uint32_t	status;			/**< 0 if the element is active, otherwise 1. */
	uint32_t	unknown1;		/**< 0 (Reserved?) */

	/* The "field descriptor" in H10DB.hdr defines the following 22 members. */
	uint32_t	unknown2;		/**< ??? */
	ucs2_char_t *file_path;		/**< Path to the music file. */
	ucs2_char_t *file_name;		/**< Name of the music file. */
	uint32_t	media_type;		/**< 0: music, 1: picture */
	ucs2_char_t	*title;			/**< Track title. */
	ucs2_char_t	*artist;		/**< Artist name. */
	ucs2_char_t	*album;			/**< Album name. */
	ucs2_char_t	*genre;			/**< Genre. */
	uint32_t	rating;			/**< Rating. (0 to 5) */
	uint32_t	revision;		/**< Revision number. */
	uint32_t	recent_play;	/**< Recent playback time (elapsed time in seconds from "Sat Jan 01 00:00:00 2000") */
	uint32_t	unknown4;		/**< ??? */
	uint32_t	number;			/**< Track number. */
	uint32_t	year;			/**< Year. */
	uint32_t	filesize;		/**< File size. */
	uint32_t	duration;		/**< Duration in seconds (represented by UCS-2 string in H10DB.dat). */
	uint32_t	samplerate;		/**< Sample rate in [Hz]. */
	uint32_t	bitrate;		/**< Bitrate in [bps]. */
	uint32_t	unknown5;		/**< ??? */
	ucs2_char_t *unknown6;		/**< ??? */
	uint32_t	unknown7;		/**< ??? */
	ucs2_char_t *unknown8;		/**< ??? */
};
typedef struct tag_h10db_dat h10db_dat_t;



/**
 * Structure of an index in H10DB_*.idx.
 */
struct tag_h10db_idx {
	uint32_t status;		/**< 0 if the element is active, otherwise 1. */
	uint32_t index;			/**< index number pointing to the entry in H10DB.dat. */
	uint32_t check_value;	/**< check value of the relevant field in the H10DB.dat entry. */
};
typedef struct tag_h10db_idx h10db_idx_t;



struct tag_h10db_type {
	uint16_t	version;
	uint16_t	model;
	uint16_t	fw_major_min;
	uint16_t	fw_minor_min;
	uint16_t	fw_major_max;
	uint16_t	fw_minor_max;
};
typedef struct tag_h10db_type h10db_type_t;

int h10db_model_findchunk(struct bfile *bfp, const char *chunk_name, uint32_t* chunk_size);
int h10db_model_writechunk(struct bfile *bfp, const char *chunk_name, uint32_t chunk_size, long* offset);
int h10db_model_writechunksize(struct bfile *bfp, long offset, uint32_t chunk_size);

uint32_t h10db_model_get_padding(h10db_type_t* type);
uint32_t h10db_model_get_maxentries(h10db_type_t* type);
uint32_t h10db_model_has_hdr_unknown5(h10db_type_t* type);

void h10db_type_init(h10db_type_t* type, uint32_t h10db_flag);
int h10db_type_read(struct bfile *bfp, h10db_type_t* type);
int h10db_type_write(struct bfile *bfp, h10db_type_t* type);





/*
 * H10DB.hdr
 */
void h10db_hdr_init(h10db_hdr_t* hdr, uint32_t max_entries, uint32_t padding_size, uint32_t has_unknown5);
void h10db_hdr_finish(h10db_hdr_t* hdr);
int h10db_hdr_serialize(struct bfile *bfp, h10db_hdr_t* hdr, int is_storing, int is_template);
void h10db_hdr_repr(FILE *fp, const h10db_hdr_t* hdr);



/*
 * Field descriptor in H10DB.hdr
 */
void h10db_fd_init(h10db_fd_t* hdr_idx);
void h10db_fd_finish(h10db_fd_t* hdr_idx);
int h10db_fd_serialize(struct bfile *bfp, h10db_fd_t* hdr_idx, int is_storing);



/*
 * H10DB.dat
 */
void h10db_dat_init(h10db_dat_t* item);
void h10db_dat_finish(h10db_dat_t* item);
int h10db_dat_serialize(struct bfile *bfp, h10db_dat_t* item, h10db_field_offsets_t offsets, h10db_fd_t* fd, int is_storing);
void h10db_dat_swap(h10db_dat_t* x, h10db_dat_t* y);
void h10db_dat_repr(FILE *fp, const h10db_dat_t* item);
void h10db_dat_validate(FILE *fp, const h10db_dat_t* item);
uint32_t h10db_dat_calculate_checkvalue(const h10db_dat_t* item, int field_index);
int h10db_dat_read(struct bfile *bfp, h10db_dat_t** array_ptr, uint32_t* num_ptr, const h10db_hdr_t* hdr);
int h10db_dat_write(struct bfile *bfp, const h10db_dat_t* array, int num, h10db_hdr_t* hdr);
void h10db_dat_delete(h10db_dat_t* array, int num);



/**
 * \defgroup IDXLowLevel	Low level interface for H10DB_*.idx.
 */
/*@{*/

void h10db_idx_init(h10db_idx_t* item);
int h10db_idx_serialize(struct bfile *bfp, h10db_idx_t* item, int is_storing);
void h10db_idx_swap(h10db_idx_t* x, h10db_idx_t* y);
void h10db_idx_repr(FILE *fp, const h10db_idx_t* item);
int h10db_idx_read(struct bfile *bfp, h10db_idx_t** array_ptr, int* num_ptr);
int h10db_idx_write(struct bfile *bfp, const h10db_idx_t* array, int num);

/*@}*/




/*
 * H10DB.upd
 */
struct tag_h10db_upd_entry {
	uint32_t crc;
	time_t ft;
};
typedef struct tag_h10db_upd_entry h10db_upd_entry_t;

struct tag_h10db_upd {
	uint32_t num;
	h10db_upd_entry_t *array;
};
typedef struct tag_h10db_upd h10db_upd_t;

int h10db_upd_read(h10db_upd_t* upd, struct bfile *bfp);
int h10db_upd_is_updated(h10db_upd_t* upd, uint32_t entry, h10db_dat_t* item, const ucs2_char_t *filename);
int h10db_upd_write(const h10db_upd_t* upd, struct bfile *bfp);


/**
 * \defgroup HighLevelInterface	High Level Interface for H10DB.
 */
/*@{*/

enum {
	H10DB_PROGRESS_NONE = 0,

	H10DB_PROGRESS_IDX_COUNT,

	H10DB_PROGRESS_READ_START,			/* progress: 0, max_progress: 0 */
	H10DB_PROGRESS_READ_END,			/* progress: 0, max_progress: 0 */
	H10DB_PROGRESS_UPDATE_START,
	H10DB_PROGRESS_UPDATE_END,
	H10DB_PROGRESS_WRITE_START,
	H10DB_PROGRESS_WRITE_END,

	H10DB_PROGRESS_READ_HDR,
	H10DB_PROGRESS_PARSE_HDR,
	H10DB_PROGRESS_READ_DAT,	
	H10DB_PROGRESS_PARSE_DAT,
	H10DB_PROGRESS_READ_IDX,
	H10DB_PROGRESS_PARSE_IDX,
	H10DB_PROGRESS_READ_UPD,
	H10DB_PROGRESS_PARSE_UPD,

	H10DB_PROGRESS_UPDATE_CLEAN,
	H10DB_PROGRESS_UPDATE_IDX,

	H10DB_PROGRESS_GENERATE_IDX,
	H10DB_PROGRESS_WRITE_IDX,
	H10DB_PROGRESS_GENERATE_DAT,
	H10DB_PROGRESS_WRITE_DAT,
	H10DB_PROGRESS_GENERATE_HDR,
	H10DB_PROGRESS_WRITE_HDR,
	H10DB_PROGRESS_GENERATE_UPD,
	H10DB_PROGRESS_WRITE_UPD,

	H10DB_PROGRESS_READ_TEMPLATE,
	H10DB_PROGRESS_WRITE_TEMPLATE,
};


typedef int (*h10db_progress_callback)(void *instance, int msg, int progress, int max_progress);
typedef int (*h10db_error_callback)(void *instance, int code, const char *msg);

struct tag_h10db {
	h10db_type_t*	type;
	h10db_hdr_t*	hdr;
	h10db_dat_t*	dat;
	h10db_idx_t**	idx;
	h10db_upd_t*	upd;

	int flags;

	h10db_progress_callback	progress_func;
	h10db_error_callback error_func;
	void *instance;
	int msg;
};
typedef struct tag_h10db h10db_t;

enum {
	H10DB_SUCCESS = 0,
	H10DBE_OUTOFMEMORY,
	H10DBE_DBINCONSISTENCY,

	H10DBE_HDR_OPENR,
	H10DBE_HDR_OPENW,
	H10DBE_HDR_READ,
	H10DBE_HDR_WRITE,

	H10DBE_DAT_OPENR,
	H10DBE_DAT_OPENW,
	H10DBE_DAT_READ,
	H10DBE_DAT_WRITE,
	H10DBE_DAT_ENTRYOFFSET,
	H10DBE_DAT_FIELDOFFSET,

	H10DBE_IDX_OPENR,
	H10DBE_IDX_OPENW,
	H10DBE_IDX_READ,
	H10DBE_IDX_WRITE,

	H10DBE_UPD_OPENR,
	H10DBE_UPD_OPENW,
	H10DBE_UPD_READ,
	H10DBE_UPD_WRITE,

	H10DBE_MODEL_OPENR,
	H10DBE_MODEL_OPENW,
	H10DBE_MODEL_READ,
	H10DBE_MODEL_WRITE,
	H10DBE_MODEL_FINDCHUNK,
};

enum {
	H10DB_UPDATEF_NONE =					0x00000000,
	H10DB_UPDATEF_CLEAN =					0x00010000,
	H10DB_FLAG_INCREMENTAL =				0x00100000,

	H10DB_FIRMWARE_UMS =					0x00000001,
	H10DB_FIRMWARE_MTP =					0x00000002,
	H10DB_FIRMWARE_MTP_2_50 =				0x00000003,
	H10DB_FIRMWARE_MASK =					0xFFFFFFF0,
	H10DB_FIRMWARE_UNMASK =					0x0000000F,

	H10DB_CAPACITY_1GB =					0x00000100,
	H10DB_CAPACITY_2GB =					0x00000200,
	H10DB_CAPACITY_5GB =					0x00000500,
	H10DB_CAPACITY_6GB =					0x00000600,
	H10DB_CAPACITY_20GB =					0x00001400,
	H10DB_CAPACITY_MASK =					0xFFFF00FF,
	H10DB_CAPACITY_UNMASK =					0x0000FF00,
};


/**
 * Create an instance of h10db_t.
 *	@param	flags			The flags.
 *	@return					The pointer to the instance if succeeded, otherwise NULL.
 */
h10db_t* h10db_new(int flags);

/**
 * Delete an h10db_t instance.
 *	@param	h10db			The pointer to the h10db_t instance.
 */
void h10db_delete(h10db_t* h10db);

/**
 * Set the instance value for callback.
 *	@param	h10db			The pointer to the h10db_t instance.
 *	@param	instance		The instance value that is to be sent to the callback function.
 */
void h10db_set_instance(h10db_t* h10db, void *instance);

/**
 * Register a callback function for progress notification.
 *	@param	h10db			The pointer to the h10db_t instance.
 *	@param	pfn				The pointer to a function that receives progress notification.
 */
void h10db_set_progress_callback(h10db_t* h10db, h10db_progress_callback pfn);

/**
 * Read an existing H10 database.
 *	@param	h10db			The pointer to the h10db_t instance.
 *	@param	path			The path to the H10 database.
 *	@return					0 if succeeded, otherwise -1.
 */
int h10db_read(h10db_t* h10db, const ucs2_char_t *path);

/**
 * Write an H10 database.
 *	@param	h10db			The pointer to the h10db_t instance.
 *	@param	path			The path to the H10 database.
 *	@return					0 if succeeded, otherwise -1.
 */
int h10db_write(h10db_t* h10db, const ucs2_char_t *path);

int h10db_load_model(h10db_t* h10db, const ucs2_char_t *filename);
h10db_type_t* h10db_access_type(h10db_t* h10db);
int h10db_store_model(h10db_t* h10db, const ucs2_char_t *filename);

/**
 * Update the H10 database.
 *	@param	h10db			The pointer to the h10db_t instance.
 *	@param	flags			The operation flags.
 *	@return					0 if succeeded, otherwise -1.
 */
int h10db_update(h10db_t* h10db, int flags);

int h10db_is_updated_item(h10db_t* h10db, int index, const ucs2_char_t *filename);

/**
 * Get the number of entries in H10 database.
 *	@param	h10db			The pointer to the h10db_t instance.
 *	@return					The number of entries.
 */
int h10db_get_size(h10db_t* h10db);

/**
 * Resize the array of entries in H10 database.
 *	@param	h10db			The pointer to the h10db_t instance.
 *	@param	size			The number of entries that the H10 database should store.
 *	@return					The nuw nunber of entries.
 */
int h10db_resize(h10db_t* h10db, int size);

/* Obsolute: delete this function in future. */
h10db_dat_t* h10db_access_item(h10db_t* h10db, int index);

int h10db_set_filepath(h10db_t* h10db, int index, const ucs2_char_t* value);
int h10db_set_filename(h10db_t* h10db, int index, const ucs2_char_t* value);
int h10db_set_title(h10db_t* h10db, int index, const ucs2_char_t* value);
int h10db_set_artist(h10db_t* h10db, int index, const ucs2_char_t* value);
int h10db_set_album(h10db_t* h10db, int index, const ucs2_char_t* value);
int h10db_set_genre(h10db_t* h10db, int index, const ucs2_char_t* value);
int h10db_set_unknown6(h10db_t* h10db, int index, const ucs2_char_t* value);
int h10db_set_unknown8(h10db_t* h10db, int index, const ucs2_char_t* value);
int h10db_set_tracknumber(h10db_t* h10db, int index, uint32_t tracknumber);
int h10db_set_year(h10db_t* h10db, int index, uint32_t year);
int h10db_set_filesize(h10db_t* h10db, int index, uint32_t filesize);
int h10db_set_duration(h10db_t* h10db, int index, uint32_t duration);
int h10db_set_samplerate(h10db_t* h10db, int index, uint32_t samplerate);
int h10db_set_bitrate(h10db_t* h10db, int index, uint32_t bitrate);
int h10db_set_unknown4(h10db_t* h10db, int index, uint32_t value);
int h10db_set_unknown5(h10db_t* h10db, int index, uint32_t value);

const ucs2_char_t* h10db_get_filepath(h10db_t* h10db, int index);
const ucs2_char_t* h10db_get_filename(h10db_t* h10db, int index);
const ucs2_char_t* h10db_get_title(h10db_t* h10db, int index);
const ucs2_char_t* h10db_get_artist(h10db_t* h10db, int index);
const ucs2_char_t* h10db_get_album(h10db_t* h10db, int index);
const ucs2_char_t* h10db_get_genre(h10db_t* h10db, int index);
const ucs2_char_t* h10db_get_unknown6(h10db_t* h10db, int index);
const ucs2_char_t* h10db_get_unknown8(h10db_t* h10db, int index);
uint32_t h10db_get_tracknumber(h10db_t* h10db, int index);
uint32_t h10db_get_year(h10db_t* h10db, int index);
uint32_t h10db_get_filesize(h10db_t* h10db, int index);
uint32_t h10db_get_duration(h10db_t* h10db, int index);
uint32_t h10db_get_samplerate(h10db_t* h10db, int index);
uint32_t h10db_get_bitrate(h10db_t* h10db, int index);
uint32_t h10db_get_unknown4(h10db_t* h10db, int index);
uint32_t h10db_get_unknown5(h10db_t* h10db, int index);

void h10db_fit_fields(h10db_t* h10db, int index);
void h10db_righttoleft_encode_fields(h10db_t* h10db, int index);
void h10db_righttoleft_decode_fields(h10db_t* h10db, int index);

uint16_t h10db_get_model(h10db_t* h10db);
uint16_t h10db_get_capacity(h10db_t* h10db);
uint16_t h10db_get_type(h10db_t* h10db);
uint16_t h10db_get_fw_major_min(h10db_t* h10db);
uint16_t h10db_get_fw_minor_min(h10db_t* h10db);
uint16_t h10db_get_fw_major_max(h10db_t* h10db);
uint16_t h10db_get_fw_minor_max(h10db_t* h10db);

/*@}*/

#ifdef	__cplusplus
}
#endif/*__cplusplus*/

#endif/*__H10DB_H__*/