Coverage Report

Created: 2025-10-14 07:00

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/libodraw/libodraw/libodraw_track_value.c
Line
Count
Source
1
/*
2
 * Track value functions
3
 *
4
 * Copyright (C) 2010-2024, Joachim Metz <joachim.metz@gmail.com>
5
 *
6
 * Refer to AUTHORS for acknowledgements.
7
 *
8
 * This program is free software: you can redistribute it and/or modify
9
 * it under the terms of the GNU Lesser General Public License as published by
10
 * the Free Software Foundation, either version 3 of the License, or
11
 * (at your option) any later version.
12
 *
13
 * This program is distributed in the hope that it will be useful,
14
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16
 * GNU General Public License for more details.
17
 *
18
 * You should have received a copy of the GNU Lesser General Public License
19
 * along with this program.  If not, see <https://www.gnu.org/licenses/>.
20
 */
21
22
#include <common.h>
23
#include <memory.h>
24
#include <types.h>
25
26
#include "libodraw_definitions.h"
27
#include "libodraw_libcerror.h"
28
#include "libodraw_track_value.h"
29
30
/* Creates a track value
31
 * Make sure the value track_value is referencing, is set to NULL
32
 * Returns 1 if successful or -1 on error
33
 */
34
int libodraw_track_value_initialize(
35
     libodraw_track_value_t **track_value,
36
     libcerror_error_t **error )
37
25.4k
{
38
25.4k
  static char *function = "libodraw_track_value_initialize";
39
40
25.4k
  if( track_value == NULL )
41
0
  {
42
0
    libcerror_error_set(
43
0
     error,
44
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
45
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
46
0
     "%s: invalid track value.",
47
0
     function );
48
49
0
    return( -1 );
50
0
  }
51
25.4k
  if( *track_value != NULL )
52
0
  {
53
0
    libcerror_error_set(
54
0
     error,
55
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
56
0
     LIBCERROR_RUNTIME_ERROR_VALUE_ALREADY_SET,
57
0
     "%s: invalid track value value already set.",
58
0
     function );
59
60
0
    return( -1 );
61
0
  }
62
25.4k
  *track_value = memory_allocate_structure(
63
25.4k
      libodraw_track_value_t );
64
65
25.4k
  if( *track_value == NULL )
66
0
  {
67
0
    libcerror_error_set(
68
0
     error,
69
0
     LIBCERROR_ERROR_DOMAIN_MEMORY,
70
0
     LIBCERROR_MEMORY_ERROR_INSUFFICIENT,
71
0
     "%s: unable to create track value.",
72
0
     function );
73
74
0
    goto on_error;
75
0
  }
76
25.4k
  if( memory_set(
77
25.4k
       *track_value,
78
25.4k
       0,
79
25.4k
       sizeof( libodraw_track_value_t ) ) == NULL )
80
0
  {
81
0
    libcerror_error_set(
82
0
     error,
83
0
     LIBCERROR_ERROR_DOMAIN_MEMORY,
84
0
     LIBCERROR_MEMORY_ERROR_SET_FAILED,
85
0
     "%s: unable to clear track value.",
86
0
     function );
87
88
0
    goto on_error;
89
0
  }
90
25.4k
  return( 1 );
91
92
0
on_error:
93
0
  if( *track_value != NULL )
94
0
  {
95
0
    memory_free(
96
0
     *track_value );
97
98
0
    *track_value = NULL;
99
0
  }
100
0
  return( -1 );
101
25.4k
}
102
103
/* Frees a track value
104
 * Returns 1 if successful or -1 on error
105
 */
106
int libodraw_track_value_free(
107
     libodraw_track_value_t **track_value,
108
     libcerror_error_t **error )
109
25.4k
{
110
25.4k
  static char *function = "libodraw_track_value_free";
111
112
25.4k
  if( track_value == NULL )
113
0
  {
114
0
    libcerror_error_set(
115
0
     error,
116
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
117
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
118
0
     "%s: invalid track value.",
119
0
     function );
120
121
0
    return( -1 );
122
0
  }
123
25.4k
  if( *track_value != NULL )
124
25.4k
  {
125
25.4k
    memory_free(
126
25.4k
     *track_value );
127
128
25.4k
    *track_value = NULL;
129
25.4k
  }
130
25.4k
  return( 1 );
131
25.4k
}
132
133
/* Retrieves a track value
134
 * Returns 1 if successful or -1 on error
135
 */
136
int libodraw_track_value_get(
137
     libodraw_track_value_t *track_value,
138
     uint64_t *start_sector,
139
     uint64_t *number_of_sectors,
140
     uint8_t *type,
141
     int *data_file_index,
142
     uint64_t *data_file_start_sector,
143
     libcerror_error_t **error )
144
0
{
145
0
  static char *function = "libodraw_track_value_get";
146
147
0
  if( track_value == NULL )
148
0
  {
149
0
    libcerror_error_set(
150
0
     error,
151
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
152
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
153
0
     "%s: invalid track value.",
154
0
     function );
155
156
0
    return( -1 );
157
0
  }
158
0
  if( start_sector == NULL )
159
0
  {
160
0
    libcerror_error_set(
161
0
     error,
162
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
163
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
164
0
     "%s: invalid start sector.",
165
0
     function );
166
167
0
    return( -1 );
168
0
  }
169
0
  if( number_of_sectors == NULL )
170
0
  {
171
0
    libcerror_error_set(
172
0
     error,
173
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
174
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
175
0
     "%s: invalid number of sectors.",
176
0
     function );
177
178
0
    return( -1 );
179
0
  }
180
0
  if( type == NULL )
181
0
  {
182
0
    libcerror_error_set(
183
0
     error,
184
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
185
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
186
0
     "%s: invalid type.",
187
0
     function );
188
189
0
    return( -1 );
190
0
  }
191
0
  if( data_file_index == NULL )
192
0
  {
193
0
    libcerror_error_set(
194
0
     error,
195
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
196
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
197
0
     "%s: invalid data file index.",
198
0
     function );
199
200
0
    return( -1 );
201
0
  }
202
0
  if( data_file_start_sector == NULL )
203
0
  {
204
0
    libcerror_error_set(
205
0
     error,
206
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
207
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
208
0
     "%s: invalid data file start sector.",
209
0
     function );
210
211
0
    return( -1 );
212
0
  }
213
0
  *start_sector           = track_value->start_sector;
214
0
  *number_of_sectors      = track_value->number_of_sectors;
215
0
  *type                   = track_value->type;
216
0
  *data_file_index        = track_value->data_file_index;
217
0
  *data_file_start_sector = track_value->data_file_start_sector;
218
219
0
  return( 1 );
220
0
}
221
222
/* Sets a track value
223
 * Returns 1 if successful or -1 on error
224
 */
225
int libodraw_track_value_set(
226
     libodraw_track_value_t *track_value,
227
     uint64_t start_sector,
228
     uint64_t number_of_sectors,
229
     uint8_t type,
230
     int data_file_index,
231
     uint64_t data_file_start_sector,
232
     libcerror_error_t **error )
233
25.4k
{
234
25.4k
  static char *function = "libodraw_track_value_set";
235
236
25.4k
  if( track_value == NULL )
237
0
  {
238
0
    libcerror_error_set(
239
0
     error,
240
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
241
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
242
0
     "%s: invalid track value.",
243
0
     function );
244
245
0
    return( -1 );
246
0
  }
247
25.4k
  if( start_sector > (uint64_t) INT64_MAX )
248
0
  {
249
0
    libcerror_error_set(
250
0
     error,
251
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
252
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_EXCEEDS_MAXIMUM,
253
0
     "%s: invalid start sector value exceeds maximum.",
254
0
     function );
255
256
0
    return( -1 );
257
0
  }
258
25.4k
  if( number_of_sectors > (uint64_t) INT64_MAX )
259
0
  {
260
0
    libcerror_error_set(
261
0
     error,
262
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
263
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_EXCEEDS_MAXIMUM,
264
0
     "%s: invalid number of sectors value exceeds maximum.",
265
0
     function );
266
267
0
    return( -1 );
268
0
  }
269
25.4k
  if( ( type != LIBODRAW_TRACK_TYPE_UNKNOWN )
270
3.74k
   && ( type != LIBODRAW_TRACK_TYPE_AUDIO )
271
1.88k
   && ( type != LIBODRAW_TRACK_TYPE_CDG )
272
1.56k
   && ( type != LIBODRAW_TRACK_TYPE_MODE1_2048 )
273
1.36k
   && ( type != LIBODRAW_TRACK_TYPE_MODE1_2352 )
274
1.16k
   && ( type != LIBODRAW_TRACK_TYPE_MODE2_2048 )
275
973
   && ( type != LIBODRAW_TRACK_TYPE_MODE2_2324 )
276
778
   && ( type != LIBODRAW_TRACK_TYPE_MODE2_2336 )
277
584
   && ( type != LIBODRAW_TRACK_TYPE_MODE2_2352 )
278
390
   && ( type != LIBODRAW_TRACK_TYPE_CDI_2336 )
279
195
   && ( type != LIBODRAW_TRACK_TYPE_CDI_2352 ) )
280
0
  {
281
0
    libcerror_error_set(
282
0
     error,
283
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
284
0
     LIBCERROR_ARGUMENT_ERROR_UNSUPPORTED_VALUE,
285
0
     "%s: unsupported type.",
286
0
     function );
287
288
0
    return( -1 );
289
0
  }
290
25.4k
  if( data_file_index < 0 )
291
50
  {
292
50
    libcerror_error_set(
293
50
     error,
294
50
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
295
50
     LIBCERROR_ARGUMENT_ERROR_VALUE_LESS_THAN_ZERO,
296
50
     "%s: invalid data file index value less than zero.",
297
50
     function );
298
299
50
    return( -1 );
300
50
  }
301
25.4k
  if( data_file_start_sector > (uint64_t) INT64_MAX )
302
27
  {
303
27
    libcerror_error_set(
304
27
     error,
305
27
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
306
27
     LIBCERROR_ARGUMENT_ERROR_VALUE_EXCEEDS_MAXIMUM,
307
27
     "%s: invalid data file start sector value exceeds maximum.",
308
27
     function );
309
310
27
    return( -1 );
311
27
  }
312
25.3k
  if( data_file_start_sector > start_sector )
313
0
  {
314
0
    libcerror_error_set(
315
0
     error,
316
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
317
0
     LIBCERROR_RUNTIME_ERROR_VALUE_OUT_OF_BOUNDS,
318
0
     "%s: data file start sector value out of bounds.",
319
0
     function );
320
321
0
    return( -1 );
322
0
  }
323
25.3k
  switch( type )
324
25.3k
  {
325
193
    case LIBODRAW_TRACK_TYPE_MODE1_2048:
326
386
    case LIBODRAW_TRACK_TYPE_MODE2_2048:
327
386
      track_value->bytes_per_sector = 2048;
328
329
386
      break;
330
331
194
    case LIBODRAW_TRACK_TYPE_MODE2_2324:
332
194
      track_value->bytes_per_sector = 2324;
333
334
194
      break;
335
336
193
    case LIBODRAW_TRACK_TYPE_MODE2_2336:
337
387
    case LIBODRAW_TRACK_TYPE_CDI_2336:
338
387
      track_value->bytes_per_sector = 2336;
339
340
387
      break;
341
342
1.85k
    case LIBODRAW_TRACK_TYPE_AUDIO:
343
2.05k
    case LIBODRAW_TRACK_TYPE_MODE1_2352:
344
2.25k
    case LIBODRAW_TRACK_TYPE_MODE2_2352:
345
2.44k
    case LIBODRAW_TRACK_TYPE_CDI_2352:
346
2.44k
      track_value->bytes_per_sector = 2352;
347
348
2.44k
      break;
349
350
322
    case LIBODRAW_TRACK_TYPE_CDG:
351
322
      track_value->bytes_per_sector = 2448;
352
353
322
      break;
354
25.3k
  }
355
25.3k
  track_value->start_sector           = start_sector;
356
25.3k
  track_value->end_sector             = start_sector + number_of_sectors;
357
25.3k
  track_value->number_of_sectors      = number_of_sectors;
358
25.3k
  track_value->type                   = type;
359
25.3k
  track_value->data_file_index        = data_file_index;
360
25.3k
  track_value->data_file_start_sector = data_file_start_sector;
361
25.3k
  track_value->data_file_offset       = data_file_start_sector * track_value->bytes_per_sector;
362
363
25.3k
  return( 1 );
364
25.3k
}
365
366
/* Retrieves the bytes per sector
367
 * Returns 1 if successful or -1 on error
368
 */
369
int libodraw_track_value_get_bytes_per_sector(
370
     libodraw_track_value_t *track_value,
371
     uint32_t *bytes_per_sector,
372
     libcerror_error_t **error )
373
0
{
374
0
  static char *function = "libodraw_track_value_get_bytes_per_sector";
375
376
0
  if( track_value == NULL )
377
0
  {
378
0
    libcerror_error_set(
379
0
     error,
380
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
381
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
382
0
     "%s: invalid track value.",
383
0
     function );
384
385
0
    return( -1 );
386
0
  }
387
0
  if( bytes_per_sector == NULL )
388
0
  {
389
0
    libcerror_error_set(
390
0
     error,
391
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
392
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
393
0
     "%s: invalid bytes per sector.",
394
0
     function );
395
396
0
    return( -1 );
397
0
  }
398
0
  *bytes_per_sector = track_value->bytes_per_sector;
399
400
0
  return( 1 );
401
0
}
402