Coverage Report

Created: 2023-06-07 06:53

/src/libvslvm/libvslvm/libvslvm_metadata.c
Line
Count
Source (jump to first uncovered line)
1
/*
2
 * The metadata functions
3
 *
4
 * Copyright (C) 2014-2023, 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 <byte_stream.h>
24
#include <memory.h>
25
#include <narrow_string.h>
26
#include <types.h>
27
28
#include "libvslvm_checksum.h"
29
#include "libvslvm_definitions.h"
30
#include "libvslvm_libbfio.h"
31
#include "libvslvm_libcdata.h"
32
#include "libvslvm_libcerror.h"
33
#include "libvslvm_libcnotify.h"
34
#include "libvslvm_libcsplit.h"
35
#include "libvslvm_libfvalue.h"
36
#include "libvslvm_logical_volume_values.h"
37
#include "libvslvm_metadata.h"
38
#include "libvslvm_physical_volume.h"
39
#include "libvslvm_raw_location_descriptor.h"
40
#include "libvslvm_segment.h"
41
#include "libvslvm_stripe.h"
42
#include "libvslvm_volume_group.h"
43
44
/* Creates a metadata
45
 * Make sure the value metadata is referencing, is set to NULL
46
 * Returns 1 if successful or -1 on error
47
 */
48
int libvslvm_metadata_initialize(
49
     libvslvm_metadata_t **metadata,
50
     libcerror_error_t **error )
51
2.66k
{
52
2.66k
  static char *function = "libvslvm_metadata_initialize";
53
54
2.66k
  if( metadata == NULL )
55
0
  {
56
0
    libcerror_error_set(
57
0
     error,
58
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
59
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
60
0
     "%s: invalid metadata.",
61
0
     function );
62
63
0
    return( -1 );
64
0
  }
65
2.66k
  if( *metadata != NULL )
66
0
  {
67
0
    libcerror_error_set(
68
0
     error,
69
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
70
0
     LIBCERROR_RUNTIME_ERROR_VALUE_ALREADY_SET,
71
0
     "%s: invalid metadata value already set.",
72
0
     function );
73
74
0
    return( -1 );
75
0
  }
76
2.66k
  *metadata = memory_allocate_structure(
77
2.66k
               libvslvm_metadata_t );
78
79
2.66k
  if( *metadata == NULL )
80
0
  {
81
0
    libcerror_error_set(
82
0
     error,
83
0
     LIBCERROR_ERROR_DOMAIN_MEMORY,
84
0
     LIBCERROR_MEMORY_ERROR_INSUFFICIENT,
85
0
     "%s: unable to create metadata.",
86
0
     function );
87
88
0
    goto on_error;
89
0
  }
90
2.66k
  if( memory_set(
91
2.66k
       *metadata,
92
2.66k
       0,
93
2.66k
       sizeof( libvslvm_metadata_t ) ) == NULL )
94
0
  {
95
0
    libcerror_error_set(
96
0
     error,
97
0
     LIBCERROR_ERROR_DOMAIN_MEMORY,
98
0
     LIBCERROR_MEMORY_ERROR_SET_FAILED,
99
0
     "%s: unable to clear metadata.",
100
0
     function );
101
102
0
    memory_free(
103
0
     *metadata );
104
105
0
    *metadata = NULL;
106
107
0
    return( -1 );
108
0
  }
109
2.66k
  return( 1 );
110
111
0
on_error:
112
0
  if( *metadata != NULL )
113
0
  {
114
0
    memory_free(
115
0
     *metadata );
116
117
0
    *metadata = NULL;
118
0
  }
119
0
  return( -1 );
120
2.66k
}
121
122
/* Frees a metadata
123
 * Returns 1 if successful or -1 on error
124
 */
125
int libvslvm_metadata_free(
126
     libvslvm_metadata_t **metadata,
127
     libcerror_error_t **error )
128
2.66k
{
129
2.66k
  static char *function = "libvslvm_metadata_free";
130
2.66k
  int result            = 1;
131
132
2.66k
  if( metadata == NULL )
133
0
  {
134
0
    libcerror_error_set(
135
0
     error,
136
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
137
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
138
0
     "%s: invalid metadata.",
139
0
     function );
140
141
0
    return( -1 );
142
0
  }
143
2.66k
  if( *metadata != NULL )
144
2.66k
  {
145
2.66k
    if( ( *metadata )->volume_group != NULL )
146
2.01k
    {
147
2.01k
      if( libvslvm_internal_volume_group_free(
148
2.01k
           (libvslvm_internal_volume_group_t **) &( ( *metadata )->volume_group ),
149
2.01k
           error ) != 1 )
150
0
      {
151
0
        libcerror_error_set(
152
0
         error,
153
0
         LIBCERROR_ERROR_DOMAIN_RUNTIME,
154
0
         LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED,
155
0
         "%s: unable to free volume group.",
156
0
         function );
157
158
0
        result = -1;
159
0
      }
160
2.01k
    }
161
2.66k
    memory_free(
162
2.66k
     *metadata );
163
164
2.66k
    *metadata = NULL;
165
2.66k
  }
166
2.66k
  return( result );
167
2.66k
}
168
169
/* Reads the metadata
170
 * Returns 1 if successful or -1 on error
171
 */
172
int libvslvm_metadata_read_data(
173
     libvslvm_metadata_t *metadata,
174
     const uint8_t *data,
175
     size_t data_size,
176
     uint32_t stored_checksum,
177
     libcerror_error_t **error )
178
2.55k
{
179
2.55k
  libcsplit_narrow_split_string_t *lines = NULL;
180
2.55k
  static char *function                  = "libvslvm_metadata_read_data";
181
2.55k
  uint32_t calculated_checksum           = 0;
182
2.55k
  int line_index                         = 0;
183
2.55k
  int number_of_lines                    = 0;
184
185
2.55k
  if( metadata == NULL )
186
0
  {
187
0
    libcerror_error_set(
188
0
     error,
189
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
190
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
191
0
     "%s: invalid metadata.",
192
0
     function );
193
194
0
    return( -1 );
195
0
  }
196
2.55k
  if( data == NULL )
197
0
  {
198
0
    libcerror_error_set(
199
0
     error,
200
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
201
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
202
0
     "%s: invalid data.",
203
0
     function );
204
205
0
    return( -1 );
206
0
  }
207
2.55k
  if( ( data_size == 0 )
208
2.55k
   || ( data_size > (size_t) SSIZE_MAX ) )
209
0
  {
210
0
    libcerror_error_set(
211
0
     error,
212
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
213
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
214
0
     "%s: invalid data size value out of bounds.",
215
0
     function );
216
217
0
    return( -1 );
218
0
  }
219
2.55k
  if( libvslvm_checksum_calculate_weak_crc32(
220
2.55k
       &calculated_checksum,
221
2.55k
       data,
222
2.55k
       data_size,
223
2.55k
       0xf597a6cfUL,
224
2.55k
       error ) != 1 )
225
0
  {
226
0
    libcerror_error_set(
227
0
     error,
228
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
229
0
     LIBCERROR_RUNTIME_ERROR_SET_FAILED,
230
0
     "%s: unable to calculate CRC-32.",
231
0
     function );
232
233
0
    goto on_error;
234
0
  }
235
2.55k
  if( ( stored_checksum != 0 )
236
2.55k
   && ( stored_checksum != calculated_checksum ) )
237
57
  {
238
57
    libcerror_error_set(
239
57
     error,
240
57
     LIBCERROR_ERROR_DOMAIN_INPUT,
241
57
     LIBCERROR_INPUT_ERROR_CHECKSUM_MISMATCH,
242
57
     "%s: mismatch in checksum ( 0x%08" PRIx32 " != 0x%08" PRIx32 " ).",
243
57
     function,
244
57
     stored_checksum,
245
57
     calculated_checksum );
246
247
57
    goto on_error;
248
57
  }
249
#if defined( HAVE_DEBUG_OUTPUT )
250
  if( libcnotify_verbose != 0 )
251
  {
252
    libcnotify_printf(
253
     "%s: metadata:\n%s",
254
     function,
255
     data );
256
  }
257
#endif
258
2.49k
  if( libcsplit_narrow_string_split(
259
2.49k
       (char *) data,
260
2.49k
       data_size,
261
2.49k
       '\n',
262
2.49k
       &lines,
263
2.49k
       error ) != 1 )
264
0
  {
265
0
    libcerror_error_set(
266
0
     error,
267
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
268
0
     LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED,
269
0
     "%s: unable to split data into lines.",
270
0
     function );
271
272
0
    goto on_error;
273
0
  }
274
2.49k
  if( libcsplit_narrow_split_string_get_number_of_segments(
275
2.49k
       lines,
276
2.49k
       &number_of_lines,
277
2.49k
       error ) != 1 )
278
2
  {
279
2
    libcerror_error_set(
280
2
     error,
281
2
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
282
2
     LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED,
283
2
     "%s: unable to retrieve number of lines.",
284
2
     function );
285
286
2
    goto on_error;
287
2
  }
288
2.49k
  if( libvslvm_metadata_read_volume_group(
289
2.49k
       metadata,
290
2.49k
       lines,
291
2.49k
       number_of_lines,
292
2.49k
       &line_index,
293
2.49k
       error ) != 1 )
294
484
  {
295
484
    libcerror_error_set(
296
484
     error,
297
484
     LIBCERROR_ERROR_DOMAIN_IO,
298
484
     LIBCERROR_IO_ERROR_READ_FAILED,
299
484
     "%s: unable to read volume group.",
300
484
     function );
301
302
484
    goto on_error;
303
484
  }
304
2.01k
  if( libcsplit_narrow_split_string_free(
305
2.01k
       &lines,
306
2.01k
       error ) != 1 )
307
0
  {
308
0
    libcerror_error_set(
309
0
     error,
310
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
311
0
     LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED,
312
0
     "%s: unable to free lines.",
313
0
     function );
314
315
0
    goto on_error;
316
0
  }
317
2.01k
  return( 1 );
318
319
543
on_error:
320
543
  if( lines != NULL )
321
484
  {
322
484
    libcsplit_narrow_split_string_free(
323
484
     &lines,
324
484
     NULL );
325
484
  }
326
543
  return( -1 );
327
2.01k
}
328
329
/* Reads the metadata
330
 * Returns 1 if successful or -1 on error
331
 */
332
int libvslvm_metadata_read_file_io_handle(
333
     libvslvm_metadata_t *metadata,
334
     libbfio_handle_t *file_io_handle,
335
     off64_t file_offset,
336
     size64_t metadata_size,
337
     uint32_t stored_checksum,
338
     libcerror_error_t **error )
339
2.66k
{
340
2.66k
  uint8_t *data         = NULL;
341
2.66k
  static char *function = "libvslvm_metadata_read_file_io_handle";
342
2.66k
  ssize_t read_count    = 0;
343
344
2.66k
  if( metadata == NULL )
345
0
  {
346
0
    libcerror_error_set(
347
0
     error,
348
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
349
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
350
0
     "%s: invalid metadata.",
351
0
     function );
352
353
0
    return( -1 );
354
0
  }
355
2.66k
  if( ( metadata_size == 0 )
356
2.66k
   || ( metadata_size > (size64_t) MEMORY_MAXIMUM_ALLOCATION_SIZE ) )
357
38
  {
358
38
    libcerror_error_set(
359
38
     error,
360
38
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
361
38
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
362
38
     "%s: invalid metadata size value out of bounds.",
363
38
     function );
364
365
38
    goto on_error;
366
38
  }
367
#if defined( HAVE_DEBUG_OUTPUT )
368
  if( libcnotify_verbose != 0 )
369
  {
370
    libcnotify_printf(
371
     "%s: reading metadata at offset: %" PRIi64 " (0x%08" PRIx64 ")\n",
372
     function,
373
     file_offset,
374
     file_offset );
375
  }
376
#endif
377
2.63k
  data = (uint8_t *) memory_allocate(
378
2.63k
                      (size_t) metadata_size );
379
380
2.63k
  if( data == NULL )
381
0
  {
382
0
    libcerror_error_set(
383
0
     error,
384
0
     LIBCERROR_ERROR_DOMAIN_MEMORY,
385
0
     LIBCERROR_MEMORY_ERROR_INSUFFICIENT,
386
0
     "%s: unable to create data.",
387
0
     function );
388
389
0
    goto on_error;
390
0
  }
391
2.63k
  read_count = libbfio_handle_read_buffer_at_offset(
392
2.63k
                file_io_handle,
393
2.63k
                data,
394
2.63k
                (size_t) metadata_size,
395
2.63k
                file_offset,
396
2.63k
                error );
397
398
2.63k
  if( read_count != (ssize_t) metadata_size )
399
75
  {
400
75
    libcerror_error_set(
401
75
     error,
402
75
     LIBCERROR_ERROR_DOMAIN_IO,
403
75
     LIBCERROR_IO_ERROR_READ_FAILED,
404
75
     "%s: unable to read metadata at offset: %" PRIi64 " (0x%08" PRIx64 ").",
405
75
     function,
406
75
     file_offset,
407
75
     file_offset );
408
409
75
    goto on_error;
410
75
  }
411
2.55k
  if( libvslvm_metadata_read_data(
412
2.55k
       metadata,
413
2.55k
       data,
414
2.55k
       (size_t) metadata_size,
415
2.55k
       stored_checksum,
416
2.55k
       error ) != 1 )
417
543
  {
418
543
    libcerror_error_set(
419
543
     error,
420
543
     LIBCERROR_ERROR_DOMAIN_IO,
421
543
     LIBCERROR_IO_ERROR_READ_FAILED,
422
543
     "%s: unable to read metadata.",
423
543
     function );
424
425
543
    goto on_error;
426
543
  }
427
2.01k
  memory_free(
428
2.01k
   data );
429
430
2.01k
  return( 1 );
431
432
656
on_error:
433
656
  if( data != NULL )
434
618
  {
435
618
    memory_free(
436
618
     data );
437
618
  }
438
656
  return( -1 );
439
2.55k
}
440
441
/* Reads the volume group
442
 * Returns the 1 if succesful or -1 on error
443
 */
444
int libvslvm_metadata_read_volume_group(
445
     libvslvm_metadata_t *metadata,
446
     libcsplit_narrow_split_string_t *lines,
447
     int number_of_lines,
448
     int *line_index,
449
     libcerror_error_t **error )
450
2.49k
{
451
2.49k
  libvslvm_internal_volume_group_t *internal_volume_group = NULL;
452
2.49k
  char *line_string_segment                               = NULL;
453
2.49k
  char *value                                             = NULL;
454
2.49k
  char *value_identifier                                  = NULL;
455
2.49k
  static char *function                                   = "libvslvm_metadata_read_volume_group";
456
2.49k
  size_t line_string_segment_index                        = 0;
457
2.49k
  size_t line_string_segment_size                         = 0;
458
2.49k
  size_t value_identifier_length                          = 0;
459
2.49k
  size_t value_length                                     = 0;
460
2.49k
  uint64_t value_64bit                                    = 0;
461
462
2.49k
  if( metadata == NULL )
463
0
  {
464
0
    libcerror_error_set(
465
0
     error,
466
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
467
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
468
0
     "%s: invalid metadata.",
469
0
     function );
470
471
0
    return( -1 );
472
0
  }
473
2.49k
  if( metadata->volume_group != NULL )
474
0
  {
475
0
    libcerror_error_set(
476
0
     error,
477
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
478
0
     LIBCERROR_RUNTIME_ERROR_VALUE_ALREADY_SET,
479
0
     "%s: invalid metadata - volume group value already set.",
480
0
     function );
481
482
0
    return( -1 );
483
0
  }
484
2.49k
  if( line_index == NULL )
485
0
  {
486
0
    libcerror_error_set(
487
0
     error,
488
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
489
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
490
0
     "%s: invalid line index.",
491
0
     function );
492
493
0
    return( -1 );
494
0
  }
495
2.49k
  if( number_of_lines <= 0 )
496
0
  {
497
0
    libcerror_error_set(
498
0
     error,
499
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
500
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
501
0
     "%s: invalid number of lines value out of bounds.",
502
0
     function );
503
504
0
    return( -1 );
505
0
  }
506
2.49k
  if( ( *line_index < 0 )
507
2.49k
   || ( *line_index >= number_of_lines ) )
508
0
  {
509
0
    libcerror_error_set(
510
0
     error,
511
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
512
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
513
0
     "%s: invalid line index value out of bounds.",
514
0
     function );
515
516
0
    return( -1 );
517
0
  }
518
2.49k
  if( libcsplit_narrow_split_string_get_segment_by_index(
519
2.49k
       lines,
520
2.49k
       *line_index,
521
2.49k
       &line_string_segment,
522
2.49k
       &line_string_segment_size,
523
2.49k
       error ) != 1 )
524
0
  {
525
0
    libcerror_error_set(
526
0
     error,
527
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
528
0
     LIBCERROR_RUNTIME_ERROR_GET_FAILED,
529
0
     "%s: unable to retrieve line: %d.",
530
0
     function,
531
0
     *line_index );
532
533
0
    goto on_error;
534
0
  }
535
2.49k
  if( line_string_segment == NULL )
536
0
  {
537
0
    libcerror_error_set(
538
0
     error,
539
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
540
0
     LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
541
0
     "%s: missing line string segment: %d.",
542
0
     function,
543
0
     *line_index );
544
545
0
    goto on_error;
546
0
  }
547
  /* Ignore trailing white space
548
   */
549
2.49k
  if( line_string_segment_size >= 2 )
550
2.49k
  {
551
2.49k
    line_string_segment_index = line_string_segment_size - 2;
552
553
18.1k
    while( line_string_segment_index > 0 )
554
18.1k
    {
555
18.1k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
556
18.1k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
557
18.1k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
558
18.1k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
559
18.1k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
560
18.1k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
561
2.49k
      {
562
2.49k
        break;
563
2.49k
      }
564
15.6k
      line_string_segment_index--;
565
15.6k
      line_string_segment_size--;
566
15.6k
    }
567
2.49k
  }
568
  /* Ignore leading white space
569
   */
570
2.49k
  line_string_segment_index = 0;
571
572
20.4k
  while( line_string_segment_index < line_string_segment_size )
573
20.4k
  {
574
20.4k
    if( ( line_string_segment[ line_string_segment_index ] != '\t' )
575
20.4k
     && ( line_string_segment[ line_string_segment_index ] != '\n' )
576
20.4k
     && ( line_string_segment[ line_string_segment_index ] != '\f' )
577
20.4k
     && ( line_string_segment[ line_string_segment_index ] != '\v' )
578
20.4k
     && ( line_string_segment[ line_string_segment_index ] != '\r' )
579
20.4k
     && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
580
2.49k
    {
581
2.49k
      break;
582
2.49k
    }
583
17.9k
    line_string_segment_index++;
584
17.9k
  }
585
2.49k
  if( ( line_string_segment_size < 3 )
586
2.49k
   || ( line_string_segment[ line_string_segment_size - 3 ] != ' ' )
587
2.49k
   || ( line_string_segment[ line_string_segment_size - 2 ] != '{' ) )
588
75
  {
589
75
    libcerror_error_set(
590
75
     error,
591
75
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
592
75
     LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE,
593
75
     "%s: unsupported volume group signature.",
594
75
     function );
595
596
75
    goto on_error;
597
75
  }
598
2.42k
  if( libvslvm_volume_group_initialize(
599
2.42k
       &( metadata->volume_group ),
600
2.42k
       error ) != 1 )
601
0
  {
602
0
    libcerror_error_set(
603
0
     error,
604
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
605
0
     LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED,
606
0
     "%s: unable to create volume group.",
607
0
     function );
608
609
0
    goto on_error;
610
0
  }
611
2.42k
  internal_volume_group = (libvslvm_internal_volume_group_t *) metadata->volume_group;
612
613
2.42k
  if( ( line_string_segment_size < 2 )
614
2.42k
   || ( line_string_segment_index >= ( line_string_segment_size - 2 ) ) )
615
1
  {
616
1
    libcerror_error_set(
617
1
     error,
618
1
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
619
1
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
620
1
     "%s: invalid line string segment size value out of bounds.",
621
1
     function );
622
623
1
    goto on_error;
624
1
  }
625
2.42k
  if( libvslvm_internal_volume_group_set_name(
626
2.42k
       (libvslvm_internal_volume_group_t *) metadata->volume_group,
627
2.42k
       &( line_string_segment[ line_string_segment_index ] ),
628
2.42k
       line_string_segment_size - ( line_string_segment_index + 2 ),
629
2.42k
       error ) != 1 )
630
0
  {
631
0
    libcerror_error_set(
632
0
     error,
633
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
634
0
     LIBCERROR_RUNTIME_ERROR_SET_FAILED,
635
0
     "%s: unable to set volume group name.",
636
0
     function );
637
638
0
    goto on_error;
639
0
  }
640
#if defined( HAVE_DEBUG_OUTPUT )
641
  if( libcnotify_verbose != 0 )
642
  {
643
    libcnotify_printf(
644
     "%s: name\t\t\t\t: %s\n",
645
     function,
646
     internal_volume_group->name );
647
  }
648
#endif
649
2.42k
  *line_index += 1;
650
651
7.37M
  while( *line_index < number_of_lines )
652
7.37M
  {
653
7.37M
    if( libcsplit_narrow_split_string_get_segment_by_index(
654
7.37M
         lines,
655
7.37M
         *line_index,
656
7.37M
         &line_string_segment,
657
7.37M
         &line_string_segment_size,
658
7.37M
         error ) != 1 )
659
0
    {
660
0
      libcerror_error_set(
661
0
       error,
662
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
663
0
       LIBCERROR_RUNTIME_ERROR_GET_FAILED,
664
0
       "%s: unable to retrieve line: %d.",
665
0
       function,
666
0
       *line_index );
667
668
0
      goto on_error;
669
0
    }
670
7.37M
    if( line_string_segment == NULL )
671
0
    {
672
0
      libcerror_error_set(
673
0
       error,
674
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
675
0
       LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
676
0
       "%s: missing line string segment: %d.",
677
0
       function,
678
0
       *line_index );
679
680
0
      goto on_error;
681
0
    }
682
    /* Ignore trailing white space
683
     */
684
7.37M
    if( line_string_segment_size >= 2 )
685
109k
    {
686
109k
      line_string_segment_index = line_string_segment_size - 2;
687
688
434k
      while( line_string_segment_index > 0 )
689
398k
      {
690
398k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
691
398k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
692
398k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
693
398k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
694
398k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
695
398k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
696
73.2k
        {
697
73.2k
          break;
698
73.2k
        }
699
324k
        line_string_segment_index--;
700
324k
        line_string_segment_size--;
701
324k
      }
702
109k
    }
703
    /* Ignore leading white space
704
     */
705
7.37M
    line_string_segment_index = 0;
706
707
10.0M
    while( line_string_segment_index < line_string_segment_size )
708
10.0M
    {
709
10.0M
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
710
10.0M
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
711
10.0M
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
712
10.0M
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
713
10.0M
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
714
10.0M
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
715
7.37M
      {
716
7.37M
        break;
717
7.37M
      }
718
2.68M
      line_string_segment_index++;
719
2.68M
    }
720
    /* Skip an empty line
721
     */
722
7.37M
    if( ( line_string_segment_index >= line_string_segment_size )
723
7.37M
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
724
7.27M
    {
725
7.27M
      *line_index += 1;
726
727
7.27M
      continue;
728
7.27M
    }
729
    /* Check for the end of section
730
     */
731
103k
    if( ( ( line_string_segment_size - line_string_segment_index ) == 2 )
732
103k
     && ( line_string_segment[ line_string_segment_index ] == '}' ) )
733
12
    {
734
12
      *line_index += 1;
735
736
12
      break;
737
12
    }
738
    /* Check for the start of a sub section
739
     */
740
103k
    if( ( line_string_segment_size - line_string_segment_index ) == 18 )
741
3.48k
    {
742
3.48k
      if( narrow_string_compare(
743
3.48k
           &( line_string_segment[ line_string_segment_index ] ),
744
3.48k
           "logical_volumes {",
745
3.48k
           17 ) == 0 )
746
1.83k
      {
747
1.83k
        if( libvslvm_metadata_read_logical_volumes(
748
1.83k
             metadata,
749
1.83k
             metadata->volume_group,
750
1.83k
             lines,
751
1.83k
             number_of_lines,
752
1.83k
             line_index,
753
1.83k
             error ) != 1 )
754
309
        {
755
309
          libcerror_error_set(
756
309
           error,
757
309
           LIBCERROR_ERROR_DOMAIN_IO,
758
309
           LIBCERROR_IO_ERROR_READ_FAILED,
759
309
           "%s: unable to read logical volumes.",
760
309
           function );
761
762
309
          goto on_error;
763
309
        }
764
1.52k
        continue;
765
1.83k
      }
766
3.48k
    }
767
99.7k
    else if( ( line_string_segment_size - line_string_segment_index ) == 19 )
768
2.14k
    {
769
2.14k
      if( narrow_string_compare(
770
2.14k
           &( line_string_segment[ line_string_segment_index ] ),
771
2.14k
           "physical_volumes {",
772
2.14k
           18 ) == 0 )
773
1.34k
      {
774
1.34k
        if( libvslvm_metadata_read_physical_volumes(
775
1.34k
             metadata,
776
1.34k
             metadata->volume_group,
777
1.34k
             lines,
778
1.34k
             number_of_lines,
779
1.34k
             line_index,
780
1.34k
             error ) != 1 )
781
53
        {
782
53
          libcerror_error_set(
783
53
           error,
784
53
           LIBCERROR_ERROR_DOMAIN_IO,
785
53
           LIBCERROR_IO_ERROR_READ_FAILED,
786
53
           "%s: unable to read physical volumes.",
787
53
           function );
788
789
53
          goto on_error;
790
53
        }
791
1.29k
        continue;
792
1.34k
      }
793
2.14k
    }
794
    /* Determine the value identifier
795
     */
796
100k
    value_identifier        = &( line_string_segment[ line_string_segment_index ] );
797
100k
    value_identifier_length = 0;
798
799
7.27M
    while( line_string_segment_index < line_string_segment_size )
800
7.23M
    {
801
7.23M
      if( ( line_string_segment[ line_string_segment_index ] == '\t' )
802
7.23M
       || ( line_string_segment[ line_string_segment_index ] == '\n' )
803
7.23M
       || ( line_string_segment[ line_string_segment_index ] == '\f' )
804
7.23M
       || ( line_string_segment[ line_string_segment_index ] == '\v' )
805
7.23M
       || ( line_string_segment[ line_string_segment_index ] == '\r' )
806
7.23M
       || ( line_string_segment[ line_string_segment_index ] == ' ' )
807
7.23M
       || ( line_string_segment[ line_string_segment_index ] == '=' ) )
808
66.3k
      {
809
66.3k
        break;
810
66.3k
      }
811
7.16M
      value_identifier_length++;
812
813
7.16M
      line_string_segment_index++;
814
7.16M
    }
815
    /* Skip a line not containing a value
816
     */
817
100k
    if( ( line_string_segment_index >= line_string_segment_size )
818
100k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
819
33.7k
    {
820
33.7k
      *line_index += 1;
821
822
33.7k
      continue;
823
33.7k
    }
824
    /* Make sure the value identifier is terminated by an end of string
825
     */
826
66.3k
    line_string_segment[ line_string_segment_index ] = 0;
827
828
66.3k
    line_string_segment_index++;
829
830
    /* Ignore whitespace
831
     */
832
160k
    while( line_string_segment_index < line_string_segment_size )
833
148k
    {
834
148k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
835
148k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
836
148k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
837
148k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
838
148k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
839
148k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
840
53.7k
      {
841
53.7k
        break;
842
53.7k
      }
843
94.6k
      line_string_segment_index++;
844
94.6k
    }
845
66.3k
    if( line_string_segment[ line_string_segment_index ] == '=' )
846
8.83k
    {
847
8.83k
      line_string_segment_index++;
848
849
18.4k
      while( line_string_segment_index < line_string_segment_size )
850
15.9k
      {
851
15.9k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
852
15.9k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
853
15.9k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
854
15.9k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
855
15.9k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
856
15.9k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
857
6.32k
        {
858
6.32k
          break;
859
6.32k
        }
860
9.65k
        line_string_segment_index++;
861
9.65k
      }
862
8.83k
    }
863
    /* Skip a line not containing a value
864
     */
865
66.3k
    if( ( line_string_segment_index >= line_string_segment_size )
866
66.3k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
867
21.8k
    {
868
21.8k
      *line_index += 1;
869
870
21.8k
      continue;
871
21.8k
    }
872
    /* Determine the value
873
     */
874
44.5k
    value        = &( line_string_segment[ line_string_segment_index ] );
875
44.5k
    value_length = line_string_segment_size - 1;
876
877
    /* Ingore quotes at the beginning of the value data
878
     */
879
44.5k
    if( ( line_string_segment[ line_string_segment_index ] == '"' )
880
44.5k
     || ( line_string_segment[ line_string_segment_index ] == '\'' ) )
881
4.01k
    {
882
4.01k
      line_string_segment_index++;
883
4.01k
      value++;
884
4.01k
      value_length--;
885
4.01k
    }
886
    /* Ingore quotes at the end of the value data
887
     */
888
44.5k
    if( ( line_string_segment[ value_length - 1 ] == '"' )
889
44.5k
     || ( line_string_segment[ value_length - 1 ] == '\'' ) )
890
2.21k
    {
891
2.21k
      value_length--;
892
2.21k
    }
893
    /* Make sure the value is terminated by an end of string
894
     */
895
44.5k
    line_string_segment[ value_length ] = 0;
896
897
44.5k
    value_length -= line_string_segment_index;
898
899
44.5k
    if( value_identifier_length == 2 )
900
20.8k
    {
901
20.8k
      if( narrow_string_compare(
902
20.8k
           value_identifier,
903
20.8k
           "id",
904
20.8k
           2 ) == 0 )
905
240
      {
906
240
        if( libvslvm_volume_group_set_identifier(
907
240
             metadata->volume_group,
908
240
             value,
909
240
             value_length + 1,
910
240
             error ) != 1 )
911
18
        {
912
18
          libcerror_error_set(
913
18
           error,
914
18
           LIBCERROR_ERROR_DOMAIN_RUNTIME,
915
18
           LIBCERROR_RUNTIME_ERROR_SET_FAILED,
916
18
           "%s: unable to set volume group identifier.",
917
18
           function );
918
919
18
          goto on_error;
920
18
        }
921
#if defined( HAVE_DEBUG_OUTPUT )
922
        if( libcnotify_verbose != 0 )
923
        {
924
          libcnotify_printf(
925
           "%s: identifier\t\t\t\t: %s\n",
926
           function,
927
           internal_volume_group->identifier );
928
        }
929
#endif
930
240
      }
931
20.8k
    }
932
23.6k
    else if( value_identifier_length == 5 )
933
1.87k
    {
934
1.87k
      if( narrow_string_compare(
935
1.87k
           value_identifier,
936
1.87k
           "flags",
937
1.87k
           5 ) == 0 )
938
807
      {
939
#if defined( HAVE_DEBUG_OUTPUT )
940
        if( libcnotify_verbose != 0 )
941
        {
942
          libcnotify_printf(
943
           "%s: flags\t\t\t\t: %s\n",
944
           function,
945
           value );
946
        }
947
#endif
948
/* TODO */
949
807
      }
950
1.06k
      else if( narrow_string_compare(
951
1.06k
                value_identifier,
952
1.06k
                "seqno",
953
1.06k
                5 ) == 0 )
954
585
      {
955
#if defined( HAVE_DEBUG_OUTPUT )
956
        if( libcnotify_verbose != 0 )
957
        {
958
          libcnotify_printf(
959
           "%s: sequence number\t\t\t: %s\n",
960
           function,
961
           value );
962
        }
963
#endif
964
585
        if( libfvalue_utf8_string_copy_to_integer(
965
585
             (uint8_t *) value,
966
585
             value_length + 1,
967
585
             &value_64bit,
968
585
             32,
969
585
             LIBFVALUE_INTEGER_FORMAT_TYPE_DECIMAL_UNSIGNED,
970
585
             error ) != 1 )
971
5
        {
972
5
          libcerror_error_set(
973
5
           error,
974
5
           LIBCERROR_ERROR_DOMAIN_MEMORY,
975
5
           LIBCERROR_MEMORY_ERROR_SET_FAILED,
976
5
           "%s: unable to set sequence number.",
977
5
           function );
978
979
5
          goto on_error;
980
5
        }
981
580
        if( value_64bit > (uint64_t) UINT32_MAX )
982
3
        {
983
3
          libcerror_error_set(
984
3
           error,
985
3
           LIBCERROR_ERROR_DOMAIN_RUNTIME,
986
3
           LIBCERROR_RUNTIME_ERROR_VALUE_EXCEEDS_MAXIMUM,
987
3
           "%s: invalid sequence number value exceeds maximum.",
988
3
           function );
989
990
3
          goto on_error;
991
3
        }
992
577
        internal_volume_group->sequence_number = (uint32_t) value_64bit;
993
577
      }
994
1.87k
    }
995
21.8k
    else if( value_identifier_length == 6 )
996
494
    {
997
494
      if( narrow_string_compare(
998
494
           value_identifier,
999
494
           "max_lv",
1000
494
           6 ) == 0 )
1001
8
      {
1002
#if defined( HAVE_DEBUG_OUTPUT )
1003
        if( libcnotify_verbose != 0 )
1004
        {
1005
          libcnotify_printf(
1006
           "%s: max_lv\t\t\t\t: %s\n",
1007
           function,
1008
           value );
1009
        }
1010
#endif
1011
/* TODO */
1012
8
      }
1013
486
      else if( narrow_string_compare(
1014
486
                value_identifier,
1015
486
                "max_pv",
1016
486
                6 ) == 0 )
1017
1
      {
1018
#if defined( HAVE_DEBUG_OUTPUT )
1019
        if( libcnotify_verbose != 0 )
1020
        {
1021
          libcnotify_printf(
1022
           "%s: max_pv\t\t\t\t: %s\n",
1023
           function,
1024
           value );
1025
        }
1026
#endif
1027
/* TODO */
1028
1
      }
1029
485
      else if( narrow_string_compare(
1030
485
                value_identifier,
1031
485
                "status",
1032
485
                6 ) == 0 )
1033
55
      {
1034
#if defined( HAVE_DEBUG_OUTPUT )
1035
        if( libcnotify_verbose != 0 )
1036
        {
1037
          libcnotify_printf(
1038
           "%s: status flags\t\t\t: %s\n",
1039
           function,
1040
           value );
1041
        }
1042
#endif
1043
/* TODO */
1044
55
      }
1045
494
    }
1046
21.3k
    else if( value_identifier_length == 11 )
1047
2.36k
    {
1048
2.36k
      if( narrow_string_compare(
1049
2.36k
           value_identifier,
1050
2.36k
           "extent_size",
1051
2.36k
           11 ) == 0 )
1052
1.96k
      {
1053
#if defined( HAVE_DEBUG_OUTPUT )
1054
        if( libcnotify_verbose != 0 )
1055
        {
1056
          libcnotify_printf(
1057
           "%s: extent size\t\t\t: %s\n",
1058
           function,
1059
           value );
1060
        }
1061
#endif
1062
1.96k
        if( libfvalue_utf8_string_copy_to_integer(
1063
1.96k
             (uint8_t *) value,
1064
1.96k
             value_length + 1,
1065
1.96k
             &value_64bit,
1066
1.96k
             64,
1067
1.96k
             LIBFVALUE_INTEGER_FORMAT_TYPE_DECIMAL_UNSIGNED,
1068
1.96k
             error ) != 1 )
1069
7
        {
1070
7
          libcerror_error_set(
1071
7
           error,
1072
7
           LIBCERROR_ERROR_DOMAIN_MEMORY,
1073
7
           LIBCERROR_MEMORY_ERROR_SET_FAILED,
1074
7
           "%s: unable to set extent size.",
1075
7
           function );
1076
1077
7
          goto on_error;
1078
7
        }
1079
1.95k
        if( value_64bit > (uint64_t) ( UINT64_MAX / 512 ) )
1080
13
        {
1081
13
          libcerror_error_set(
1082
13
           error,
1083
13
           LIBCERROR_ERROR_DOMAIN_RUNTIME,
1084
13
           LIBCERROR_RUNTIME_ERROR_VALUE_EXCEEDS_MAXIMUM,
1085
13
           "%s: invalid extent size value exceeds maximum.",
1086
13
           function );
1087
1088
13
          goto on_error;
1089
13
        }
1090
1.94k
        value_64bit *= 512;
1091
1092
1.94k
        internal_volume_group->extent_size = value_64bit;
1093
1.94k
      }
1094
2.36k
    }
1095
18.9k
    else if( value_identifier_length == 15 )
1096
206
    {
1097
206
      if( narrow_string_compare(
1098
206
           value_identifier,
1099
206
           "metadata_copies",
1100
206
           15 ) == 0 )
1101
0
      {
1102
#if defined( HAVE_DEBUG_OUTPUT )
1103
        if( libcnotify_verbose != 0 )
1104
        {
1105
          libcnotify_printf(
1106
           "%s: metadata copies\t\t\t: %s\n",
1107
           function,
1108
           value );
1109
        }
1110
#endif
1111
/* TODO */
1112
0
      }
1113
206
    }
1114
#if defined( HAVE_DEBUG_OUTPUT )
1115
    else if( libcnotify_verbose != 0 )
1116
    {
1117
      libcnotify_printf(
1118
       "%s: value: %d\t\t\t: %s = %s\n",
1119
       function,
1120
       *line_index,
1121
       value_identifier,
1122
       value );
1123
    }
1124
#endif
1125
44.4k
    *line_index += 1;
1126
44.4k
  }
1127
#if defined( HAVE_DEBUG_OUTPUT )
1128
  if( libcnotify_verbose != 0 )
1129
  {
1130
    libcnotify_printf(
1131
     "\n" );
1132
  }
1133
#endif
1134
2.01k
  return( 1 );
1135
1136
484
on_error:
1137
484
  if( metadata->volume_group != NULL )
1138
409
  {
1139
409
    libvslvm_internal_volume_group_free(
1140
409
     (libvslvm_internal_volume_group_t **) &( metadata->volume_group ),
1141
409
     NULL );
1142
409
  }
1143
484
  return( -1 );
1144
2.42k
}
1145
1146
/* Reads the physical volumes
1147
 * Returns the 1 if succesful or -1 on error
1148
 */
1149
int libvslvm_metadata_read_physical_volumes(
1150
     libvslvm_metadata_t *metadata,
1151
     libvslvm_volume_group_t *volume_group,
1152
     libcsplit_narrow_split_string_t *lines,
1153
     int number_of_lines,
1154
     int *line_index,
1155
     libcerror_error_t **error )
1156
1.34k
{
1157
1.34k
  char *line_string_segment        = NULL;
1158
1.34k
  static char *function            = "libvslvm_metadata_read_physical_volumes";
1159
1.34k
  size_t line_string_segment_index = 0;
1160
1.34k
  size_t line_string_segment_size  = 0;
1161
1162
1.34k
  if( metadata == NULL )
1163
0
  {
1164
0
    libcerror_error_set(
1165
0
     error,
1166
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
1167
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
1168
0
     "%s: invalid metadata.",
1169
0
     function );
1170
1171
0
    return( -1 );
1172
0
  }
1173
1.34k
  if( line_index == NULL )
1174
0
  {
1175
0
    libcerror_error_set(
1176
0
     error,
1177
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
1178
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
1179
0
     "%s: invalid line index.",
1180
0
     function );
1181
1182
0
    return( -1 );
1183
0
  }
1184
1.34k
  if( number_of_lines <= 0 )
1185
0
  {
1186
0
    libcerror_error_set(
1187
0
     error,
1188
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
1189
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
1190
0
     "%s: invalid number of lines value out of bounds.",
1191
0
     function );
1192
1193
0
    return( -1 );
1194
0
  }
1195
1.34k
  if( ( *line_index < 0 )
1196
1.34k
   || ( *line_index >= number_of_lines ) )
1197
0
  {
1198
0
    libcerror_error_set(
1199
0
     error,
1200
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
1201
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
1202
0
     "%s: invalid line index value out of bounds.",
1203
0
     function );
1204
1205
0
    return( -1 );
1206
0
  }
1207
1.34k
  if( libcsplit_narrow_split_string_get_segment_by_index(
1208
1.34k
       lines,
1209
1.34k
       *line_index,
1210
1.34k
       &line_string_segment,
1211
1.34k
       &line_string_segment_size,
1212
1.34k
       error ) != 1 )
1213
0
  {
1214
0
    libcerror_error_set(
1215
0
     error,
1216
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
1217
0
     LIBCERROR_RUNTIME_ERROR_GET_FAILED,
1218
0
     "%s: unable to retrieve line: %d.",
1219
0
     function,
1220
0
     *line_index );
1221
1222
0
    return( -1 );
1223
0
  }
1224
1.34k
  if( line_string_segment == NULL )
1225
0
  {
1226
0
    libcerror_error_set(
1227
0
     error,
1228
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
1229
0
     LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
1230
0
     "%s: missing line string segment: %d.",
1231
0
     function,
1232
0
     *line_index );
1233
1234
0
    return( -1 );
1235
0
  }
1236
  /* Ignore trailing white space
1237
   */
1238
1.34k
  if( line_string_segment_size >= 2 )
1239
1.34k
  {
1240
1.34k
    line_string_segment_index = line_string_segment_size - 2;
1241
1242
80.3k
    while( line_string_segment_index > 0 )
1243
80.3k
    {
1244
80.3k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
1245
80.3k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
1246
80.3k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
1247
80.3k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
1248
80.3k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
1249
80.3k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
1250
1.34k
      {
1251
1.34k
        break;
1252
1.34k
      }
1253
79.0k
      line_string_segment_index--;
1254
79.0k
      line_string_segment_size--;
1255
79.0k
    }
1256
1.34k
  }
1257
  /* Ignore leading white space
1258
   */
1259
1.34k
  line_string_segment_index = 0;
1260
1261
838k
  while( line_string_segment_index < line_string_segment_size )
1262
838k
  {
1263
838k
    if( ( line_string_segment[ line_string_segment_index ] != '\t' )
1264
838k
     && ( line_string_segment[ line_string_segment_index ] != '\n' )
1265
838k
     && ( line_string_segment[ line_string_segment_index ] != '\f' )
1266
838k
     && ( line_string_segment[ line_string_segment_index ] != '\v' )
1267
838k
     && ( line_string_segment[ line_string_segment_index ] != '\r' )
1268
838k
     && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
1269
1.34k
    {
1270
1.34k
      break;
1271
1.34k
    }
1272
837k
    line_string_segment_index++;
1273
837k
  }
1274
1.34k
  if( ( ( line_string_segment_size - line_string_segment_index ) != 19 )
1275
1.34k
   || ( narrow_string_compare(
1276
1.34k
         &( line_string_segment[ line_string_segment_index ] ),
1277
1.34k
         "physical_volumes {",
1278
1.34k
         18 ) != 0 ) )
1279
0
  {
1280
0
    libcerror_error_set(
1281
0
     error,
1282
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
1283
0
     LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE,
1284
0
     "%s: unsupported physical volumes signature.",
1285
0
     function );
1286
1287
0
    return( -1 );
1288
0
  }
1289
1.34k
  *line_index += 1;
1290
1291
2.39M
  while( *line_index < number_of_lines )
1292
2.39M
  {
1293
2.39M
    if( libcsplit_narrow_split_string_get_segment_by_index(
1294
2.39M
         lines,
1295
2.39M
         *line_index,
1296
2.39M
         &line_string_segment,
1297
2.39M
         &line_string_segment_size,
1298
2.39M
         error ) != 1 )
1299
0
    {
1300
0
      libcerror_error_set(
1301
0
       error,
1302
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
1303
0
       LIBCERROR_RUNTIME_ERROR_GET_FAILED,
1304
0
       "%s: unable to retrieve line: %d.",
1305
0
       function,
1306
0
       *line_index );
1307
1308
0
      return( -1 );
1309
0
    }
1310
2.39M
    if( line_string_segment == NULL )
1311
0
    {
1312
0
      libcerror_error_set(
1313
0
       error,
1314
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
1315
0
       LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
1316
0
       "%s: missing line string segment: %d.",
1317
0
       function,
1318
0
       *line_index );
1319
1320
0
      return( -1 );
1321
0
    }
1322
    /* Ignore trailing white space
1323
     */
1324
2.39M
    if( line_string_segment_size >= 2 )
1325
37.1k
    {
1326
37.1k
      line_string_segment_index = line_string_segment_size - 2;
1327
1328
121k
      while( line_string_segment_index > 0 )
1329
106k
      {
1330
106k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
1331
106k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
1332
106k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
1333
106k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
1334
106k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
1335
106k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
1336
22.4k
        {
1337
22.4k
          break;
1338
22.4k
        }
1339
84.4k
        line_string_segment_index--;
1340
84.4k
        line_string_segment_size--;
1341
84.4k
      }
1342
37.1k
    }
1343
    /* Ignore leading white space
1344
     */
1345
2.39M
    line_string_segment_index = 0;
1346
1347
2.82M
    while( line_string_segment_index < line_string_segment_size )
1348
2.82M
    {
1349
2.82M
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
1350
2.82M
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
1351
2.82M
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
1352
2.82M
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
1353
2.82M
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
1354
2.82M
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
1355
2.39M
      {
1356
2.39M
        break;
1357
2.39M
      }
1358
426k
      line_string_segment_index++;
1359
426k
    }
1360
    /* Skip an empty line
1361
     */
1362
2.39M
    if( ( line_string_segment_index >= line_string_segment_size )
1363
2.39M
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
1364
2.36M
    {
1365
2.36M
      *line_index += 1;
1366
1367
2.36M
      continue;
1368
2.36M
    }
1369
    /* Check for the end of section
1370
     */
1371
32.8k
    if( ( ( line_string_segment_size - line_string_segment_index ) == 2 )
1372
32.8k
     && ( line_string_segment[ line_string_segment_index ] == '}' ) )
1373
700
    {
1374
700
      *line_index += 1;
1375
1376
700
      break;
1377
700
    }
1378
    /* Check for the start of a sub section
1379
     */
1380
32.1k
    if( ( line_string_segment_size >= 3 )
1381
32.1k
     && ( line_string_segment[ line_string_segment_size - 3 ] == ' ' )
1382
32.1k
     && ( line_string_segment[ line_string_segment_size - 2 ] == '{' ) )
1383
5.26k
    {
1384
5.26k
      if( libvslvm_metadata_read_physical_volume(
1385
5.26k
           metadata,
1386
5.26k
           volume_group,
1387
5.26k
           lines,
1388
5.26k
           number_of_lines,
1389
5.26k
           line_index,
1390
5.26k
           error ) != 1 )
1391
53
      {
1392
53
        libcerror_error_set(
1393
53
         error,
1394
53
         LIBCERROR_ERROR_DOMAIN_IO,
1395
53
         LIBCERROR_IO_ERROR_READ_FAILED,
1396
53
         "%s: unable to read physical volume.",
1397
53
         function );
1398
1399
53
        return( -1 );
1400
53
      }
1401
5.26k
    }
1402
26.8k
    else
1403
26.8k
    {
1404
/* TODO debug print other lines ? */
1405
26.8k
      *line_index += 1;
1406
26.8k
    }
1407
32.1k
  }
1408
1.29k
  return( 1 );
1409
1.34k
}
1410
1411
/* Reads the physical volume
1412
 * Returns the 1 if succesful or -1 on error
1413
 */
1414
int libvslvm_metadata_read_physical_volume(
1415
     libvslvm_metadata_t *metadata,
1416
     libvslvm_volume_group_t *volume_group,
1417
     libcsplit_narrow_split_string_t *lines,
1418
     int number_of_lines,
1419
     int *line_index,
1420
     libcerror_error_t **error )
1421
5.26k
{
1422
5.26k
  libvslvm_physical_volume_t *physical_volume = NULL;
1423
5.26k
  char *line_string_segment                   = NULL;
1424
5.26k
  char *value                                 = NULL;
1425
5.26k
  char *value_identifier                      = NULL;
1426
5.26k
  static char *function                       = "libvslvm_metadata_read_physical_volume";
1427
5.26k
  size_t line_string_segment_index            = 0;
1428
5.26k
  size_t line_string_segment_size             = 0;
1429
5.26k
  size_t value_identifier_length              = 0;
1430
5.26k
  size_t value_length                         = 0;
1431
5.26k
  uint64_t value_64bit                        = 0;
1432
1433
5.26k
  if( metadata == NULL )
1434
0
  {
1435
0
    libcerror_error_set(
1436
0
     error,
1437
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
1438
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
1439
0
     "%s: invalid metadata.",
1440
0
     function );
1441
1442
0
    return( -1 );
1443
0
  }
1444
5.26k
  if( volume_group == NULL )
1445
0
  {
1446
0
    libcerror_error_set(
1447
0
     error,
1448
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
1449
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
1450
0
     "%s: invalid volume group.",
1451
0
     function );
1452
1453
0
    return( -1 );
1454
0
  }
1455
5.26k
  if( line_index == NULL )
1456
0
  {
1457
0
    libcerror_error_set(
1458
0
     error,
1459
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
1460
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
1461
0
     "%s: invalid line index.",
1462
0
     function );
1463
1464
0
    return( -1 );
1465
0
  }
1466
5.26k
  if( number_of_lines <= 0 )
1467
0
  {
1468
0
    libcerror_error_set(
1469
0
     error,
1470
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
1471
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
1472
0
     "%s: invalid number of lines value out of bounds.",
1473
0
     function );
1474
1475
0
    return( -1 );
1476
0
  }
1477
5.26k
  if( ( *line_index < 0 )
1478
5.26k
   || ( *line_index >= number_of_lines ) )
1479
0
  {
1480
0
    libcerror_error_set(
1481
0
     error,
1482
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
1483
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
1484
0
     "%s: invalid line index value out of bounds.",
1485
0
     function );
1486
1487
0
    return( -1 );
1488
0
  }
1489
5.26k
  if( libcsplit_narrow_split_string_get_segment_by_index(
1490
5.26k
       lines,
1491
5.26k
       *line_index,
1492
5.26k
       &line_string_segment,
1493
5.26k
       &line_string_segment_size,
1494
5.26k
       error ) != 1 )
1495
0
  {
1496
0
    libcerror_error_set(
1497
0
     error,
1498
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
1499
0
     LIBCERROR_RUNTIME_ERROR_GET_FAILED,
1500
0
     "%s: unable to retrieve line: %d.",
1501
0
     function,
1502
0
     *line_index );
1503
1504
0
    goto on_error;
1505
0
  }
1506
5.26k
  if( line_string_segment == NULL )
1507
0
  {
1508
0
    libcerror_error_set(
1509
0
     error,
1510
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
1511
0
     LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
1512
0
     "%s: missing line string segment: %d.",
1513
0
     function,
1514
0
     *line_index );
1515
1516
0
    goto on_error;
1517
0
  }
1518
  /* Ignore trailing white space
1519
   */
1520
5.26k
  if( line_string_segment_size >= 2 )
1521
5.26k
  {
1522
5.26k
    line_string_segment_index = line_string_segment_size - 2;
1523
1524
49.5k
    while( line_string_segment_index > 0 )
1525
49.5k
    {
1526
49.5k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
1527
49.5k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
1528
49.5k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
1529
49.5k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
1530
49.5k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
1531
49.5k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
1532
5.26k
      {
1533
5.26k
        break;
1534
5.26k
      }
1535
44.2k
      line_string_segment_index--;
1536
44.2k
      line_string_segment_size--;
1537
44.2k
    }
1538
5.26k
  }
1539
  /* Ignore leading white space
1540
   */
1541
5.26k
  line_string_segment_index = 0;
1542
1543
26.4k
  while( line_string_segment_index < line_string_segment_size )
1544
26.4k
  {
1545
26.4k
    if( ( line_string_segment[ line_string_segment_index ] != '\t' )
1546
26.4k
     && ( line_string_segment[ line_string_segment_index ] != '\n' )
1547
26.4k
     && ( line_string_segment[ line_string_segment_index ] != '\f' )
1548
26.4k
     && ( line_string_segment[ line_string_segment_index ] != '\v' )
1549
26.4k
     && ( line_string_segment[ line_string_segment_index ] != '\r' )
1550
26.4k
     && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
1551
5.26k
    {
1552
5.26k
      break;
1553
5.26k
    }
1554
21.1k
    line_string_segment_index++;
1555
21.1k
  }
1556
5.26k
  if( ( line_string_segment_size < 3 )
1557
5.26k
   || ( line_string_segment[ line_string_segment_size - 3 ] != ' ' )
1558
5.26k
   || ( line_string_segment[ line_string_segment_size - 2 ] != '{' ) )
1559
0
  {
1560
0
    libcerror_error_set(
1561
0
     error,
1562
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
1563
0
     LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE,
1564
0
     "%s: unsupported physical volume signature.",
1565
0
     function );
1566
1567
0
    goto on_error;
1568
0
  }
1569
5.26k
  if( libvslvm_physical_volume_initialize(
1570
5.26k
       &physical_volume,
1571
5.26k
       error ) != 1 )
1572
0
  {
1573
0
    libcerror_error_set(
1574
0
     error,
1575
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
1576
0
     LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED,
1577
0
     "%s: unable to create physical volume.",
1578
0
     function );
1579
1580
0
    goto on_error;
1581
0
  }
1582
5.26k
  if( ( line_string_segment_size < 2 )
1583
5.26k
   || ( line_string_segment_index >= ( line_string_segment_size - 2 ) ) )
1584
2
  {
1585
2
    libcerror_error_set(
1586
2
     error,
1587
2
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
1588
2
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
1589
2
     "%s: invalid line string segment size value out of bounds.",
1590
2
     function );
1591
1592
2
    goto on_error;
1593
2
  }
1594
5.26k
  if( libvslvm_physical_volume_set_name(
1595
5.26k
       physical_volume,
1596
5.26k
       &( line_string_segment[ line_string_segment_index ] ),
1597
5.26k
       line_string_segment_size - ( line_string_segment_index + 2 ),
1598
5.26k
       error ) != 1 )
1599
0
  {
1600
0
    libcerror_error_set(
1601
0
     error,
1602
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
1603
0
     LIBCERROR_RUNTIME_ERROR_SET_FAILED,
1604
0
     "%s: unable to set physical volume name.",
1605
0
     function );
1606
1607
0
    goto on_error;
1608
0
  }
1609
#if defined( HAVE_DEBUG_OUTPUT )
1610
  if( libcnotify_verbose != 0 )
1611
  {
1612
    libcnotify_printf(
1613
     "\n" );
1614
1615
    libcnotify_printf(
1616
     "%s: name\t\t\t\t: %s\n",
1617
     function,
1618
     ( (libvslvm_internal_physical_volume_t *) physical_volume )->name );
1619
  }
1620
#endif
1621
5.26k
  *line_index += 1;
1622
1623
2.85M
  while( *line_index < number_of_lines )
1624
2.85M
  {
1625
2.85M
    if( libcsplit_narrow_split_string_get_segment_by_index(
1626
2.85M
         lines,
1627
2.85M
         *line_index,
1628
2.85M
         &line_string_segment,
1629
2.85M
         &line_string_segment_size,
1630
2.85M
         error ) != 1 )
1631
0
    {
1632
0
      libcerror_error_set(
1633
0
       error,
1634
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
1635
0
       LIBCERROR_RUNTIME_ERROR_GET_FAILED,
1636
0
       "%s: unable to retrieve line: %d.",
1637
0
       function,
1638
0
       *line_index );
1639
1640
0
      goto on_error;
1641
0
    }
1642
2.85M
    if( line_string_segment == NULL )
1643
0
    {
1644
0
      libcerror_error_set(
1645
0
       error,
1646
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
1647
0
       LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
1648
0
       "%s: missing line string segment: %d.",
1649
0
       function,
1650
0
       *line_index );
1651
1652
0
      goto on_error;
1653
0
    }
1654
    /* Ignore trailing white space
1655
     */
1656
2.85M
    if( line_string_segment_size >= 2 )
1657
49.2k
    {
1658
49.2k
      line_string_segment_index = line_string_segment_size - 2;
1659
1660
106k
      while( line_string_segment_index > 0 )
1661
85.3k
      {
1662
85.3k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
1663
85.3k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
1664
85.3k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
1665
85.3k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
1666
85.3k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
1667
85.3k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
1668
27.8k
        {
1669
27.8k
          break;
1670
27.8k
        }
1671
57.5k
        line_string_segment_index--;
1672
57.5k
        line_string_segment_size--;
1673
57.5k
      }
1674
49.2k
    }
1675
    /* Ignore leading white space
1676
     */
1677
2.85M
    line_string_segment_index = 0;
1678
1679
3.52M
    while( line_string_segment_index < line_string_segment_size )
1680
3.52M
    {
1681
3.52M
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
1682
3.52M
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
1683
3.52M
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
1684
3.52M
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
1685
3.52M
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
1686
3.52M
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
1687
2.85M
      {
1688
2.85M
        break;
1689
2.85M
      }
1690
675k
      line_string_segment_index++;
1691
675k
    }
1692
    /* Skip an empty line
1693
     */
1694
2.85M
    if( ( line_string_segment_index >= line_string_segment_size )
1695
2.85M
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
1696
2.80M
    {
1697
2.80M
      *line_index += 1;
1698
1699
2.80M
      continue;
1700
2.80M
    }
1701
    /* Check for the end of section
1702
     */
1703
46.6k
    if( ( ( line_string_segment_size - line_string_segment_index ) == 2 )
1704
46.6k
     && ( line_string_segment[ line_string_segment_index ] == '}' ) )
1705
4.74k
    {
1706
4.74k
      *line_index += 1;
1707
1708
4.74k
      break;
1709
4.74k
    }
1710
    /* Determine the value identifier
1711
     */
1712
41.8k
    value_identifier        = &( line_string_segment[ line_string_segment_index ] );
1713
41.8k
    value_identifier_length = 0;
1714
1715
9.06M
    while( line_string_segment_index < line_string_segment_size )
1716
9.04M
    {
1717
9.04M
      if( ( line_string_segment[ line_string_segment_index ] == '\t' )
1718
9.04M
       || ( line_string_segment[ line_string_segment_index ] == '\n' )
1719
9.04M
       || ( line_string_segment[ line_string_segment_index ] == '\f' )
1720
9.04M
       || ( line_string_segment[ line_string_segment_index ] == '\v' )
1721
9.04M
       || ( line_string_segment[ line_string_segment_index ] == '\r' )
1722
9.04M
       || ( line_string_segment[ line_string_segment_index ] == ' ' )
1723
9.04M
       || ( line_string_segment[ line_string_segment_index ] == '=' ) )
1724
28.1k
      {
1725
28.1k
        break;
1726
28.1k
      }
1727
9.01M
      value_identifier_length++;
1728
1729
9.01M
      line_string_segment_index++;
1730
9.01M
    }
1731
    /* Skip a line not containing a value
1732
     */
1733
41.8k
    if( ( line_string_segment_index >= line_string_segment_size )
1734
41.8k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
1735
13.6k
    {
1736
13.6k
      *line_index += 1;
1737
1738
13.6k
      continue;
1739
13.6k
    }
1740
    /* Make sure the value identifier is terminated by an end of string
1741
     */
1742
28.1k
    line_string_segment[ line_string_segment_index ] = 0;
1743
1744
28.1k
    line_string_segment_index++;
1745
1746
    /* Ignore whitespace
1747
     */
1748
108k
    while( line_string_segment_index < line_string_segment_size )
1749
103k
    {
1750
103k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
1751
103k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
1752
103k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
1753
103k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
1754
103k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
1755
103k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
1756
23.2k
      {
1757
23.2k
        break;
1758
23.2k
      }
1759
80.6k
      line_string_segment_index++;
1760
80.6k
    }
1761
28.1k
    if( line_string_segment[ line_string_segment_index ] == '=' )
1762
5.24k
    {
1763
5.24k
      line_string_segment_index++;
1764
1765
11.3k
      while( line_string_segment_index < line_string_segment_size )
1766
10.0k
      {
1767
10.0k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
1768
10.0k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
1769
10.0k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
1770
10.0k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
1771
10.0k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
1772
10.0k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
1773
3.92k
        {
1774
3.92k
          break;
1775
3.92k
        }
1776
6.07k
        line_string_segment_index++;
1777
6.07k
      }
1778
5.24k
    }
1779
    /* Skip a line not containing a value
1780
     */
1781
28.1k
    if( ( line_string_segment_index >= line_string_segment_size )
1782
28.1k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
1783
9.76k
    {
1784
9.76k
      *line_index += 1;
1785
1786
9.76k
      continue;
1787
9.76k
    }
1788
    /* Determine the value
1789
     */
1790
18.4k
    value        = &( line_string_segment[ line_string_segment_index ] );
1791
18.4k
    value_length = line_string_segment_size - 1;
1792
1793
    /* Ingore quotes at the beginning of the value data
1794
     */
1795
18.4k
    if( ( line_string_segment[ line_string_segment_index ] == '"' )
1796
18.4k
     || ( line_string_segment[ line_string_segment_index ] == '\'' ) )
1797
3.05k
    {
1798
3.05k
      line_string_segment_index++;
1799
3.05k
      value++;
1800
3.05k
      value_length--;
1801
3.05k
    }
1802
    /* Ingore quotes at the end of the value data
1803
     */
1804
18.4k
    if( ( line_string_segment[ value_length - 1 ] == '"' )
1805
18.4k
     || ( line_string_segment[ value_length - 1 ] == '\'' ) )
1806
1.64k
    {
1807
1.64k
      value_length--;
1808
1.64k
    }
1809
    /* Make sure the value is terminated by an end of string
1810
     */
1811
18.4k
    line_string_segment[ value_length ] = 0;
1812
1813
18.4k
    value_length -= line_string_segment_index;
1814
1815
18.4k
    if( value_identifier_length == 2 )
1816
3.62k
    {
1817
3.62k
      if( narrow_string_compare(
1818
3.62k
           value_identifier,
1819
3.62k
           "id",
1820
3.62k
           2 ) == 0 )
1821
228
      {
1822
228
        if( libvslvm_physical_volume_set_identifier(
1823
228
             physical_volume,
1824
228
             value,
1825
228
             value_length + 1,
1826
228
             error ) != 1 )
1827
18
        {
1828
18
          libcerror_error_set(
1829
18
           error,
1830
18
           LIBCERROR_ERROR_DOMAIN_RUNTIME,
1831
18
           LIBCERROR_RUNTIME_ERROR_SET_FAILED,
1832
18
           "%s: unable to set physical volume identifier.",
1833
18
           function );
1834
1835
18
          goto on_error;
1836
18
        }
1837
#if defined( HAVE_DEBUG_OUTPUT )
1838
        if( libcnotify_verbose != 0 )
1839
        {
1840
          libcnotify_printf(
1841
           "%s: identifier\t\t\t: %s\n",
1842
           function,
1843
           ( (libvslvm_internal_physical_volume_t *) physical_volume )->identifier );
1844
        }
1845
#endif
1846
228
      }
1847
3.62k
    }
1848
14.7k
    else if( value_identifier_length == 5 )
1849
918
    {
1850
918
      if( narrow_string_compare(
1851
918
           value_identifier,
1852
918
           "flags",
1853
918
           5 ) == 0 )
1854
319
      {
1855
#if defined( HAVE_DEBUG_OUTPUT )
1856
        if( libcnotify_verbose != 0 )
1857
        {
1858
          libcnotify_printf(
1859
           "%s: flags\t\t\t\t: %s\n",
1860
           function,
1861
           value );
1862
        }
1863
#endif
1864
/* TODO */
1865
319
      }
1866
918
    }
1867
13.8k
    else if( value_identifier_length == 6 )
1868
1.28k
    {
1869
1.28k
      if( narrow_string_compare(
1870
1.28k
           value_identifier,
1871
1.28k
           "device",
1872
1.28k
           6 ) == 0 )
1873
671
      {
1874
671
        if( libvslvm_physical_volume_set_device_path(
1875
671
             physical_volume,
1876
671
             value,
1877
671
             value_length + 1,
1878
671
             error ) != 1 )
1879
1
        {
1880
1
          libcerror_error_set(
1881
1
           error,
1882
1
           LIBCERROR_ERROR_DOMAIN_RUNTIME,
1883
1
           LIBCERROR_RUNTIME_ERROR_SET_FAILED,
1884
1
           "%s: unable to set physical volume device path.",
1885
1
           function );
1886
1887
1
          goto on_error;
1888
1
        }
1889
#if defined( HAVE_DEBUG_OUTPUT )
1890
        if( libcnotify_verbose != 0 )
1891
        {
1892
          libcnotify_printf(
1893
           "%s: device path\t\t\t: %s\n",
1894
           function,
1895
           ( (libvslvm_internal_physical_volume_t *) physical_volume )->device_path );
1896
        }
1897
#endif
1898
671
      }
1899
611
      else if( narrow_string_compare(
1900
611
                value_identifier,
1901
611
                "status",
1902
611
                6 ) == 0 )
1903
46
      {
1904
#if defined( HAVE_DEBUG_OUTPUT )
1905
        if( libcnotify_verbose != 0 )
1906
        {
1907
          libcnotify_printf(
1908
           "%s: status flags\t\t\t: %s\n",
1909
           function,
1910
           value );
1911
        }
1912
#endif
1913
/* TODO */
1914
46
      }
1915
1916
1.28k
    }
1917
12.5k
    else if( value_identifier_length == 8 )
1918
2.03k
    {
1919
2.03k
      if( narrow_string_compare(
1920
2.03k
           value_identifier,
1921
2.03k
           "dev_size",
1922
2.03k
           8 ) == 0 )
1923
340
      {
1924
#if defined( HAVE_DEBUG_OUTPUT )
1925
        if( libcnotify_verbose != 0 )
1926
        {
1927
          libcnotify_printf(
1928
           "%s: volume size\t\t\t: %s\n",
1929
           function,
1930
           value );
1931
        }
1932
#endif
1933
340
        if( libfvalue_utf8_string_copy_to_integer(
1934
340
             (uint8_t *) value,
1935
340
             value_length + 1,
1936
340
             &value_64bit,
1937
340
             64,
1938
340
             LIBFVALUE_INTEGER_FORMAT_TYPE_DECIMAL_UNSIGNED,
1939
340
             error ) != 1 )
1940
14
        {
1941
14
          libcerror_error_set(
1942
14
           error,
1943
14
           LIBCERROR_ERROR_DOMAIN_MEMORY,
1944
14
           LIBCERROR_MEMORY_ERROR_SET_FAILED,
1945
14
           "%s: unable to set volume size.",
1946
14
           function );
1947
1948
14
          goto on_error;
1949
14
        }
1950
326
        if( value_64bit > (uint64_t) ( UINT64_MAX / 512 ) )
1951
18
        {
1952
18
          libcerror_error_set(
1953
18
           error,
1954
18
           LIBCERROR_ERROR_DOMAIN_RUNTIME,
1955
18
           LIBCERROR_RUNTIME_ERROR_VALUE_EXCEEDS_MAXIMUM,
1956
18
           "%s: invalid volume size value exceeds maximum.",
1957
18
           function );
1958
1959
18
          goto on_error;
1960
18
        }
1961
308
        value_64bit *= 512;
1962
1963
308
        ( (libvslvm_internal_physical_volume_t *) physical_volume )->size = value_64bit;
1964
308
      }
1965
1.69k
      else if( narrow_string_compare(
1966
1.69k
                value_identifier,
1967
1.69k
                "pe_count",
1968
1.69k
                8 ) == 0 )
1969
12
      {
1970
#if defined( HAVE_DEBUG_OUTPUT )
1971
        if( libcnotify_verbose != 0 )
1972
        {
1973
          libcnotify_printf(
1974
           "%s: pe_count\t\t\t: %s\n",
1975
           function,
1976
           value );
1977
        }
1978
#endif
1979
/* TODO */
1980
12
      }
1981
1.68k
      else if( narrow_string_compare(
1982
1.68k
                value_identifier,
1983
1.68k
                "pe_start",
1984
1.68k
                8 ) == 0 )
1985
36
      {
1986
#if defined( HAVE_DEBUG_OUTPUT )
1987
        if( libcnotify_verbose != 0 )
1988
        {
1989
          libcnotify_printf(
1990
           "%s: pe_start\t\t\t: %s\n",
1991
           function,
1992
           value );
1993
        }
1994
#endif
1995
/* TODO */
1996
36
      }
1997
2.03k
    }
1998
#if defined( HAVE_DEBUG_OUTPUT )
1999
    else if( libcnotify_verbose != 0 )
2000
    {
2001
      libcnotify_printf(
2002
       "%s: value: %d\t\t\t: %s = %s\n",
2003
       function,
2004
       *line_index,
2005
       value_identifier,
2006
       value );
2007
    }
2008
#endif
2009
18.3k
    *line_index += 1;
2010
18.3k
  }
2011
5.21k
  if( libvslvm_volume_group_append_physical_volume(
2012
5.21k
       volume_group,
2013
5.21k
       physical_volume,
2014
5.21k
       error ) != 1 )
2015
0
  {
2016
0
    libcerror_error_set(
2017
0
     error,
2018
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2019
0
     LIBCERROR_RUNTIME_ERROR_APPEND_FAILED,
2020
0
     "%s: unable to append physical volume to volume group.",
2021
0
     function );
2022
2023
0
    goto on_error;
2024
0
  }
2025
5.21k
  physical_volume = NULL;
2026
2027
5.21k
  return( 1 );
2028
2029
53
on_error:
2030
53
  if( physical_volume != NULL )
2031
53
  {
2032
53
    libvslvm_internal_physical_volume_free(
2033
53
     (libvslvm_internal_physical_volume_t **) &physical_volume,
2034
53
     NULL );
2035
53
  }
2036
53
  return( -1 );
2037
5.21k
}
2038
2039
/* Reads the logical volumes
2040
 * Returns the 1 if succesful or -1 on error
2041
 */
2042
int libvslvm_metadata_read_logical_volumes(
2043
     libvslvm_metadata_t *metadata,
2044
     libvslvm_volume_group_t *volume_group,
2045
     libcsplit_narrow_split_string_t *lines,
2046
     int number_of_lines,
2047
     int *line_index,
2048
     libcerror_error_t **error )
2049
1.83k
{
2050
1.83k
  char *line_string_segment        = NULL;
2051
1.83k
  static char *function            = "libvslvm_metadata_read_logical_volumes";
2052
1.83k
  size_t line_string_segment_index = 0;
2053
1.83k
  size_t line_string_segment_size  = 0;
2054
2055
1.83k
  if( metadata == NULL )
2056
0
  {
2057
0
    libcerror_error_set(
2058
0
     error,
2059
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2060
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
2061
0
     "%s: invalid metadata.",
2062
0
     function );
2063
2064
0
    return( -1 );
2065
0
  }
2066
1.83k
  if( line_index == NULL )
2067
0
  {
2068
0
    libcerror_error_set(
2069
0
     error,
2070
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2071
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
2072
0
     "%s: invalid line index.",
2073
0
     function );
2074
2075
0
    return( -1 );
2076
0
  }
2077
1.83k
  if( number_of_lines <= 0 )
2078
0
  {
2079
0
    libcerror_error_set(
2080
0
     error,
2081
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2082
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
2083
0
     "%s: invalid number of lines value out of bounds.",
2084
0
     function );
2085
2086
0
    return( -1 );
2087
0
  }
2088
1.83k
  if( ( *line_index < 0 )
2089
1.83k
   || ( *line_index >= number_of_lines ) )
2090
0
  {
2091
0
    libcerror_error_set(
2092
0
     error,
2093
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2094
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
2095
0
     "%s: invalid line index value out of bounds.",
2096
0
     function );
2097
2098
0
    return( -1 );
2099
0
  }
2100
1.83k
  if( libcsplit_narrow_split_string_get_segment_by_index(
2101
1.83k
       lines,
2102
1.83k
       *line_index,
2103
1.83k
       &line_string_segment,
2104
1.83k
       &line_string_segment_size,
2105
1.83k
       error ) != 1 )
2106
0
  {
2107
0
    libcerror_error_set(
2108
0
     error,
2109
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2110
0
     LIBCERROR_RUNTIME_ERROR_GET_FAILED,
2111
0
     "%s: unable to retrieve line: %d.",
2112
0
     function,
2113
0
     *line_index );
2114
2115
0
    return( -1 );
2116
0
  }
2117
1.83k
  if( line_string_segment == NULL )
2118
0
  {
2119
0
    libcerror_error_set(
2120
0
     error,
2121
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2122
0
     LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
2123
0
     "%s: missing line string segment: %d.",
2124
0
     function,
2125
0
     *line_index );
2126
2127
0
    return( -1 );
2128
0
  }
2129
  /* Ignore trailing white space
2130
   */
2131
1.83k
  if( line_string_segment_size >= 2 )
2132
1.83k
  {
2133
1.83k
    line_string_segment_index = line_string_segment_size - 2;
2134
2135
37.7k
    while( line_string_segment_index > 0 )
2136
37.7k
    {
2137
37.7k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
2138
37.7k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
2139
37.7k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
2140
37.7k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
2141
37.7k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
2142
37.7k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
2143
1.83k
      {
2144
1.83k
        break;
2145
1.83k
      }
2146
35.8k
      line_string_segment_index--;
2147
35.8k
      line_string_segment_size--;
2148
35.8k
    }
2149
1.83k
  }
2150
  /* Ignore leading white space
2151
   */
2152
1.83k
  line_string_segment_index = 0;
2153
2154
1.16M
  while( line_string_segment_index < line_string_segment_size )
2155
1.16M
  {
2156
1.16M
    if( ( line_string_segment[ line_string_segment_index ] != '\t' )
2157
1.16M
     && ( line_string_segment[ line_string_segment_index ] != '\n' )
2158
1.16M
     && ( line_string_segment[ line_string_segment_index ] != '\f' )
2159
1.16M
     && ( line_string_segment[ line_string_segment_index ] != '\v' )
2160
1.16M
     && ( line_string_segment[ line_string_segment_index ] != '\r' )
2161
1.16M
     && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
2162
1.83k
    {
2163
1.83k
      break;
2164
1.83k
    }
2165
1.16M
    line_string_segment_index++;
2166
1.16M
  }
2167
1.83k
  if( ( ( line_string_segment_size - line_string_segment_index ) != 18 )
2168
1.83k
   || ( narrow_string_compare(
2169
1.83k
         &( line_string_segment[ line_string_segment_index ] ),
2170
1.83k
         "logical_volumes {",
2171
1.83k
         17 ) != 0 ) )
2172
0
  {
2173
0
    libcerror_error_set(
2174
0
     error,
2175
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2176
0
     LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE,
2177
0
     "%s: unsupported logical volumes signature.",
2178
0
     function );
2179
2180
0
    return( -1 );
2181
0
  }
2182
1.83k
  *line_index += 1;
2183
2184
905k
  while( *line_index < number_of_lines )
2185
904k
  {
2186
904k
    if( libcsplit_narrow_split_string_get_segment_by_index(
2187
904k
         lines,
2188
904k
         *line_index,
2189
904k
         &line_string_segment,
2190
904k
         &line_string_segment_size,
2191
904k
         error ) != 1 )
2192
0
    {
2193
0
      libcerror_error_set(
2194
0
       error,
2195
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
2196
0
       LIBCERROR_RUNTIME_ERROR_GET_FAILED,
2197
0
       "%s: unable to retrieve line: %d.",
2198
0
       function,
2199
0
       *line_index );
2200
2201
0
      return( -1 );
2202
0
    }
2203
904k
    if( line_string_segment == NULL )
2204
0
    {
2205
0
      libcerror_error_set(
2206
0
       error,
2207
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
2208
0
       LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
2209
0
       "%s: missing line string segment: %d.",
2210
0
       function,
2211
0
       *line_index );
2212
2213
0
      return( -1 );
2214
0
    }
2215
    /* Ignore trailing white space
2216
     */
2217
904k
    if( line_string_segment_size >= 2 )
2218
26.0k
    {
2219
26.0k
      line_string_segment_index = line_string_segment_size - 2;
2220
2221
93.5k
      while( line_string_segment_index > 0 )
2222
84.1k
      {
2223
84.1k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
2224
84.1k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
2225
84.1k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
2226
84.1k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
2227
84.1k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
2228
84.1k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
2229
16.5k
        {
2230
16.5k
          break;
2231
16.5k
        }
2232
67.5k
        line_string_segment_index--;
2233
67.5k
        line_string_segment_size--;
2234
67.5k
      }
2235
26.0k
    }
2236
    /* Ignore leading white space
2237
     */
2238
904k
    line_string_segment_index = 0;
2239
2240
1.39M
    while( line_string_segment_index < line_string_segment_size )
2241
1.39M
    {
2242
1.39M
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
2243
1.39M
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
2244
1.39M
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
2245
1.39M
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
2246
1.39M
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
2247
1.39M
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
2248
903k
      {
2249
903k
        break;
2250
903k
      }
2251
494k
      line_string_segment_index++;
2252
494k
    }
2253
    /* Skip an empty line
2254
     */
2255
904k
    if( ( line_string_segment_index >= line_string_segment_size )
2256
904k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
2257
881k
    {
2258
881k
      *line_index += 1;
2259
2260
881k
      continue;
2261
881k
    }
2262
    /* Check for the end of section
2263
     */
2264
23.2k
    if( ( ( line_string_segment_size - line_string_segment_index ) == 2 )
2265
23.2k
     && ( line_string_segment[ line_string_segment_index ] == '}' ) )
2266
481
    {
2267
481
      *line_index += 1;
2268
2269
481
      break;
2270
481
    }
2271
    /* Check for the start of a sub section
2272
     */
2273
22.7k
    if( ( line_string_segment_size >= 3 )
2274
22.7k
     && ( line_string_segment[ line_string_segment_size - 3 ] == ' ' )
2275
22.7k
     && ( line_string_segment[ line_string_segment_size - 2 ] == '{' ) )
2276
4.40k
    {
2277
4.40k
      if( libvslvm_metadata_read_logical_volume(
2278
4.40k
           metadata,
2279
4.40k
           volume_group,
2280
4.40k
           lines,
2281
4.40k
           number_of_lines,
2282
4.40k
           line_index,
2283
4.40k
           error ) != 1 )
2284
309
      {
2285
309
        libcerror_error_set(
2286
309
         error,
2287
309
         LIBCERROR_ERROR_DOMAIN_IO,
2288
309
         LIBCERROR_IO_ERROR_READ_FAILED,
2289
309
         "%s: unable to read logical volume.",
2290
309
         function );
2291
2292
309
        return( -1 );
2293
309
      }
2294
4.40k
    }
2295
18.3k
    else
2296
18.3k
    {
2297
/* TODO debug print other lines ? */
2298
18.3k
      *line_index += 1;
2299
18.3k
    }
2300
22.7k
  }
2301
1.52k
  return( 1 );
2302
1.83k
}
2303
2304
/* Reads the logical volume
2305
 * Returns the 1 if succesful or -1 on error
2306
 */
2307
int libvslvm_metadata_read_logical_volume(
2308
     libvslvm_metadata_t *metadata,
2309
     libvslvm_volume_group_t *volume_group,
2310
     libcsplit_narrow_split_string_t *lines,
2311
     int number_of_lines,
2312
     int *line_index,
2313
     libcerror_error_t **error )
2314
4.40k
{
2315
4.40k
  libvslvm_logical_volume_values_t *logical_volume_values = NULL;
2316
4.40k
  char *line_string_segment                               = NULL;
2317
4.40k
  char *value                                             = NULL;
2318
4.40k
  char *value_identifier                                  = NULL;
2319
4.40k
  static char *function                                   = "libvslvm_metadata_read_logical_volume";
2320
4.40k
  size_t line_string_segment_index                        = 0;
2321
4.40k
  size_t line_string_segment_size                         = 0;
2322
4.40k
  size_t value_identifier_length                          = 0;
2323
4.40k
  size_t value_length                                     = 0;
2324
2325
4.40k
  if( metadata == NULL )
2326
0
  {
2327
0
    libcerror_error_set(
2328
0
     error,
2329
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2330
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
2331
0
     "%s: invalid metadata.",
2332
0
     function );
2333
2334
0
    return( -1 );
2335
0
  }
2336
4.40k
  if( volume_group == NULL )
2337
0
  {
2338
0
    libcerror_error_set(
2339
0
     error,
2340
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2341
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
2342
0
     "%s: invalid volume group.",
2343
0
     function );
2344
2345
0
    return( -1 );
2346
0
  }
2347
4.40k
  if( line_index == NULL )
2348
0
  {
2349
0
    libcerror_error_set(
2350
0
     error,
2351
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2352
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
2353
0
     "%s: invalid line index.",
2354
0
     function );
2355
2356
0
    return( -1 );
2357
0
  }
2358
4.40k
  if( number_of_lines <= 0 )
2359
0
  {
2360
0
    libcerror_error_set(
2361
0
     error,
2362
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2363
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
2364
0
     "%s: invalid number of lines value out of bounds.",
2365
0
     function );
2366
2367
0
    return( -1 );
2368
0
  }
2369
4.40k
  if( ( *line_index < 0 )
2370
4.40k
   || ( *line_index >= number_of_lines ) )
2371
0
  {
2372
0
    libcerror_error_set(
2373
0
     error,
2374
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2375
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
2376
0
     "%s: invalid line index value out of bounds.",
2377
0
     function );
2378
2379
0
    return( -1 );
2380
0
  }
2381
4.40k
  if( libcsplit_narrow_split_string_get_segment_by_index(
2382
4.40k
       lines,
2383
4.40k
       *line_index,
2384
4.40k
       &line_string_segment,
2385
4.40k
       &line_string_segment_size,
2386
4.40k
       error ) != 1 )
2387
0
  {
2388
0
    libcerror_error_set(
2389
0
     error,
2390
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2391
0
     LIBCERROR_RUNTIME_ERROR_GET_FAILED,
2392
0
     "%s: unable to retrieve line: %d.",
2393
0
     function,
2394
0
     *line_index );
2395
2396
0
    goto on_error;
2397
0
  }
2398
4.40k
  if( line_string_segment == NULL )
2399
0
  {
2400
0
    libcerror_error_set(
2401
0
     error,
2402
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2403
0
     LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
2404
0
     "%s: missing line string segment: %d.",
2405
0
     function,
2406
0
     *line_index );
2407
2408
0
    goto on_error;
2409
0
  }
2410
  /* Ignore trailing white space
2411
   */
2412
4.40k
  if( line_string_segment_size >= 2 )
2413
4.40k
  {
2414
4.40k
    line_string_segment_index = line_string_segment_size - 2;
2415
2416
44.9k
    while( line_string_segment_index > 0 )
2417
44.9k
    {
2418
44.9k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
2419
44.9k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
2420
44.9k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
2421
44.9k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
2422
44.9k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
2423
44.9k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
2424
4.40k
      {
2425
4.40k
        break;
2426
4.40k
      }
2427
40.4k
      line_string_segment_index--;
2428
40.4k
      line_string_segment_size--;
2429
40.4k
    }
2430
4.40k
  }
2431
  /* Ignore leading white space
2432
   */
2433
4.40k
  line_string_segment_index = 0;
2434
2435
86.4k
  while( line_string_segment_index < line_string_segment_size )
2436
86.4k
  {
2437
86.4k
    if( ( line_string_segment[ line_string_segment_index ] != '\t' )
2438
86.4k
     && ( line_string_segment[ line_string_segment_index ] != '\n' )
2439
86.4k
     && ( line_string_segment[ line_string_segment_index ] != '\f' )
2440
86.4k
     && ( line_string_segment[ line_string_segment_index ] != '\v' )
2441
86.4k
     && ( line_string_segment[ line_string_segment_index ] != '\r' )
2442
86.4k
     && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
2443
4.40k
    {
2444
4.40k
      break;
2445
4.40k
    }
2446
82.0k
    line_string_segment_index++;
2447
82.0k
  }
2448
4.40k
  if( ( line_string_segment_size < 3 )
2449
4.40k
   || ( line_string_segment[ line_string_segment_size - 3 ] != ' ' )
2450
4.40k
   || ( line_string_segment[ line_string_segment_size - 2 ] != '{' ) )
2451
0
  {
2452
0
    libcerror_error_set(
2453
0
     error,
2454
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2455
0
     LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE,
2456
0
     "%s: unsupported logical volume signature.",
2457
0
     function );
2458
2459
0
    goto on_error;
2460
0
  }
2461
4.40k
  if( libvslvm_logical_volume_values_initialize(
2462
4.40k
       &logical_volume_values,
2463
4.40k
       error ) != 1 )
2464
0
  {
2465
0
    libcerror_error_set(
2466
0
     error,
2467
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2468
0
     LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED,
2469
0
     "%s: unable to create logical volume values.",
2470
0
     function );
2471
2472
0
    goto on_error;
2473
0
  }
2474
4.40k
  if( ( line_string_segment_size < 2 )
2475
4.40k
   || ( line_string_segment_index >= ( line_string_segment_size - 2 ) ) )
2476
1
  {
2477
1
    libcerror_error_set(
2478
1
     error,
2479
1
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2480
1
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
2481
1
     "%s: invalid line string segment size value out of bounds.",
2482
1
     function );
2483
2484
1
    goto on_error;
2485
1
  }
2486
4.40k
  if( libvslvm_logical_volume_values_set_name(
2487
4.40k
       logical_volume_values,
2488
4.40k
       &( line_string_segment[ line_string_segment_index ] ),
2489
4.40k
       line_string_segment_size - ( line_string_segment_index + 2 ),
2490
4.40k
       error ) != 1 )
2491
0
  {
2492
0
    libcerror_error_set(
2493
0
     error,
2494
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2495
0
     LIBCERROR_RUNTIME_ERROR_SET_FAILED,
2496
0
     "%s: unable to set logical volume name.",
2497
0
     function );
2498
2499
0
    goto on_error;
2500
0
  }
2501
#if defined( HAVE_DEBUG_OUTPUT )
2502
  if( libcnotify_verbose != 0 )
2503
  {
2504
    libcnotify_printf(
2505
     "\n" );
2506
2507
    libcnotify_printf(
2508
     "%s: name\t\t\t\t: %s\n",
2509
     function,
2510
     logical_volume_values->name );
2511
  }
2512
#endif
2513
4.40k
  *line_index += 1;
2514
2515
1.78M
  while( *line_index < number_of_lines )
2516
1.78M
  {
2517
1.78M
    if( libcsplit_narrow_split_string_get_segment_by_index(
2518
1.78M
         lines,
2519
1.78M
         *line_index,
2520
1.78M
         &line_string_segment,
2521
1.78M
         &line_string_segment_size,
2522
1.78M
         error ) != 1 )
2523
0
    {
2524
0
      libcerror_error_set(
2525
0
       error,
2526
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
2527
0
       LIBCERROR_RUNTIME_ERROR_GET_FAILED,
2528
0
       "%s: unable to retrieve line: %d.",
2529
0
       function,
2530
0
       *line_index );
2531
2532
0
      goto on_error;
2533
0
    }
2534
1.78M
    if( line_string_segment == NULL )
2535
0
    {
2536
0
      libcerror_error_set(
2537
0
       error,
2538
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
2539
0
       LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
2540
0
       "%s: missing line string segment: %d.",
2541
0
       function,
2542
0
       *line_index );
2543
2544
0
      goto on_error;
2545
0
    }
2546
    /* Ignore trailing white space
2547
     */
2548
1.78M
    if( line_string_segment_size >= 2 )
2549
49.3k
    {
2550
49.3k
      line_string_segment_index = line_string_segment_size - 2;
2551
2552
170k
      while( line_string_segment_index > 0 )
2553
151k
      {
2554
151k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
2555
151k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
2556
151k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
2557
151k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
2558
151k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
2559
151k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
2560
30.5k
        {
2561
30.5k
          break;
2562
30.5k
        }
2563
121k
        line_string_segment_index--;
2564
121k
        line_string_segment_size--;
2565
121k
      }
2566
49.3k
    }
2567
    /* Ignore leading white space
2568
     */
2569
1.78M
    line_string_segment_index = 0;
2570
2571
2.40M
    while( line_string_segment_index < line_string_segment_size )
2572
2.40M
    {
2573
2.40M
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
2574
2.40M
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
2575
2.40M
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
2576
2.40M
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
2577
2.40M
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
2578
2.40M
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
2579
1.78M
      {
2580
1.78M
        break;
2581
1.78M
      }
2582
624k
      line_string_segment_index++;
2583
624k
    }
2584
    /* Skip an empty line
2585
     */
2586
1.78M
    if( ( line_string_segment_index >= line_string_segment_size )
2587
1.78M
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
2588
1.73M
    {
2589
1.73M
      *line_index += 1;
2590
2591
1.73M
      continue;
2592
1.73M
    }
2593
    /* Check for the end of section
2594
     */
2595
46.5k
    if( ( ( line_string_segment_size - line_string_segment_index ) == 2 )
2596
46.5k
     && ( line_string_segment[ line_string_segment_index ] == '}' ) )
2597
3.18k
    {
2598
3.18k
      *line_index += 1;
2599
2600
3.18k
      break;
2601
3.18k
    }
2602
    /* Check for the start of a sub section
2603
     */
2604
43.3k
    if( ( line_string_segment_size >= 3 )
2605
43.3k
     && ( line_string_segment[ line_string_segment_size - 3 ] == ' ' )
2606
43.3k
     && ( line_string_segment[ line_string_segment_size - 2 ] == '{' )
2607
43.3k
     && ( ( line_string_segment_size - line_string_segment_index ) >= 7 )
2608
43.3k
     && ( narrow_string_compare(
2609
3.53k
           &( line_string_segment[ line_string_segment_index ] ),
2610
3.53k
           "segment",
2611
3.53k
           7 ) == 0 ) )
2612
1.47k
    {
2613
1.47k
      if( libvslvm_metadata_read_segment(
2614
1.47k
           metadata,
2615
1.47k
           logical_volume_values,
2616
1.47k
           lines,
2617
1.47k
           number_of_lines,
2618
1.47k
           line_index,
2619
1.47k
           error ) != 1 )
2620
302
      {
2621
302
        libcerror_error_set(
2622
302
         error,
2623
302
         LIBCERROR_ERROR_DOMAIN_IO,
2624
302
         LIBCERROR_IO_ERROR_READ_FAILED,
2625
302
         "%s: unable to read segment.",
2626
302
         function );
2627
2628
302
        goto on_error;
2629
302
      }
2630
1.17k
      continue;
2631
1.47k
    }
2632
    /* Determine the value identifier
2633
     */
2634
41.8k
    value_identifier        = &( line_string_segment[ line_string_segment_index ] );
2635
41.8k
    value_identifier_length = 0;
2636
2637
6.10M
    while( line_string_segment_index < line_string_segment_size )
2638
6.09M
    {
2639
6.09M
      if( ( line_string_segment[ line_string_segment_index ] == '\t' )
2640
6.09M
       || ( line_string_segment[ line_string_segment_index ] == '\n' )
2641
6.09M
       || ( line_string_segment[ line_string_segment_index ] == '\f' )
2642
6.09M
       || ( line_string_segment[ line_string_segment_index ] == '\v' )
2643
6.09M
       || ( line_string_segment[ line_string_segment_index ] == '\r' )
2644
6.09M
       || ( line_string_segment[ line_string_segment_index ] == ' ' )
2645
6.09M
       || ( line_string_segment[ line_string_segment_index ] == '=' ) )
2646
29.2k
      {
2647
29.2k
        break;
2648
29.2k
      }
2649
6.06M
      value_identifier_length++;
2650
2651
6.06M
      line_string_segment_index++;
2652
6.06M
    }
2653
    /* Skip a line not containing a value
2654
     */
2655
41.8k
    if( ( line_string_segment_index >= line_string_segment_size )
2656
41.8k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
2657
12.5k
    {
2658
12.5k
      *line_index += 1;
2659
2660
12.5k
      continue;
2661
12.5k
    }
2662
    /* Make sure the value identifier is terminated by an end of string
2663
     */
2664
29.2k
    line_string_segment[ line_string_segment_index ] = 0;
2665
2666
29.2k
    line_string_segment_index++;
2667
2668
    /* Ignore whitespace
2669
     */
2670
130k
    while( line_string_segment_index < line_string_segment_size )
2671
124k
    {
2672
124k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
2673
124k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
2674
124k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
2675
124k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
2676
124k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
2677
124k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
2678
23.5k
      {
2679
23.5k
        break;
2680
23.5k
      }
2681
101k
      line_string_segment_index++;
2682
101k
    }
2683
29.2k
    if( line_string_segment[ line_string_segment_index ] == '=' )
2684
4.19k
    {
2685
4.19k
      line_string_segment_index++;
2686
2687
13.2k
      while( line_string_segment_index < line_string_segment_size )
2688
12.1k
      {
2689
12.1k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
2690
12.1k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
2691
12.1k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
2692
12.1k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
2693
12.1k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
2694
12.1k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
2695
3.09k
        {
2696
3.09k
          break;
2697
3.09k
        }
2698
9.04k
        line_string_segment_index++;
2699
9.04k
      }
2700
4.19k
    }
2701
    /* Skip a line not containing a value
2702
     */
2703
29.2k
    if( ( line_string_segment_index >= line_string_segment_size )
2704
29.2k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
2705
9.89k
    {
2706
9.89k
      *line_index += 1;
2707
2708
9.89k
      continue;
2709
9.89k
    }
2710
    /* Determine the value
2711
     */
2712
19.3k
    value        = &( line_string_segment[ line_string_segment_index ] );
2713
19.3k
    value_length = line_string_segment_size - 1;
2714
2715
    /* Ingore quotes at the beginning of the value data
2716
     */
2717
19.3k
    if( ( line_string_segment[ line_string_segment_index ] == '"' )
2718
19.3k
     || ( line_string_segment[ line_string_segment_index ] == '\'' ) )
2719
2.31k
    {
2720
2.31k
      line_string_segment_index++;
2721
2.31k
      value++;
2722
2.31k
      value_length--;
2723
2.31k
    }
2724
    /* Ingore quotes at the end of the value data
2725
     */
2726
19.3k
    if( ( line_string_segment[ value_length - 1 ] == '"' )
2727
19.3k
     || ( line_string_segment[ value_length - 1 ] == '\'' ) )
2728
979
    {
2729
979
      value_length--;
2730
979
    }
2731
    /* Make sure the value is terminated by an end of string
2732
     */
2733
19.3k
    line_string_segment[ value_length ] = 0;
2734
2735
19.3k
    value_length -= line_string_segment_index;
2736
2737
19.3k
    if( value_identifier_length == 2 )
2738
6.48k
    {
2739
6.48k
      if( narrow_string_compare(
2740
6.48k
           value_identifier,
2741
6.48k
           "id",
2742
6.48k
           2 ) == 0 )
2743
215
      {
2744
215
        if( libvslvm_logical_volume_values_set_identifier(
2745
215
             logical_volume_values,
2746
215
             value,
2747
215
             value_length + 1,
2748
215
             error ) != 1 )
2749
6
        {
2750
6
          libcerror_error_set(
2751
6
           error,
2752
6
           LIBCERROR_ERROR_DOMAIN_RUNTIME,
2753
6
           LIBCERROR_RUNTIME_ERROR_SET_FAILED,
2754
6
           "%s: unable to set logical volume identifier.",
2755
6
           function );
2756
2757
6
          goto on_error;
2758
6
        }
2759
#if defined( HAVE_DEBUG_OUTPUT )
2760
        if( libcnotify_verbose != 0 )
2761
        {
2762
          libcnotify_printf(
2763
           "%s: identifier\t\t\t: %s\n",
2764
           function,
2765
           logical_volume_values->identifier );
2766
        }
2767
#endif
2768
215
      }
2769
6.48k
    }
2770
12.9k
    else if( value_identifier_length == 5 )
2771
599
    {
2772
599
      if( narrow_string_compare(
2773
599
           value_identifier,
2774
599
           "flags",
2775
599
           5 ) == 0 )
2776
232
      {
2777
#if defined( HAVE_DEBUG_OUTPUT )
2778
        if( libcnotify_verbose != 0 )
2779
        {
2780
          libcnotify_printf(
2781
           "%s: flags\t\t\t\t: %s\n",
2782
           function,
2783
           value );
2784
        }
2785
#endif
2786
/* TODO */
2787
232
      }
2788
599
    }
2789
12.3k
    else if( value_identifier_length == 6 )
2790
688
    {
2791
688
      if( narrow_string_compare(
2792
688
           value_identifier,
2793
688
           "status",
2794
688
           6 ) == 0 )
2795
40
      {
2796
#if defined( HAVE_DEBUG_OUTPUT )
2797
        if( libcnotify_verbose != 0 )
2798
        {
2799
          libcnotify_printf(
2800
           "%s: status flags\t\t\t: %s\n",
2801
           function,
2802
           value );
2803
        }
2804
#endif
2805
/* TODO */
2806
40
      }
2807
2808
688
    }
2809
11.6k
    else if( value_identifier_length == 13 )
2810
140
    {
2811
140
      if( narrow_string_compare(
2812
140
           value_identifier,
2813
140
           "segment_count",
2814
140
           13 ) == 0 )
2815
1
      {
2816
#if defined( HAVE_DEBUG_OUTPUT )
2817
        if( libcnotify_verbose != 0 )
2818
        {
2819
          libcnotify_printf(
2820
           "%s: number of segments\t\t: %s\n",
2821
           function,
2822
           value );
2823
        }
2824
#endif
2825
/* TODO */
2826
1
      }
2827
2828
140
    }
2829
#if defined( HAVE_DEBUG_OUTPUT )
2830
    else if( libcnotify_verbose != 0 )
2831
    {
2832
      libcnotify_printf(
2833
       "%s: value: %d\t\t\t: %s = %s\n",
2834
       function,
2835
       *line_index,
2836
       value_identifier,
2837
       value );
2838
    }
2839
#endif
2840
19.3k
    *line_index += 1;
2841
19.3k
  }
2842
4.09k
  if( libvslvm_volume_group_append_logical_volume(
2843
4.09k
       volume_group,
2844
4.09k
       logical_volume_values,
2845
4.09k
       error ) != 1 )
2846
0
  {
2847
0
    libcerror_error_set(
2848
0
     error,
2849
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2850
0
     LIBCERROR_RUNTIME_ERROR_APPEND_FAILED,
2851
0
     "%s: unable to append logical volume to volume group.",
2852
0
     function );
2853
2854
0
    goto on_error;
2855
0
  }
2856
4.09k
  logical_volume_values = NULL;
2857
2858
4.09k
  return( 1 );
2859
2860
309
on_error:
2861
309
  if( logical_volume_values != NULL )
2862
309
  {
2863
309
    libvslvm_logical_volume_values_free(
2864
309
     &logical_volume_values,
2865
309
     NULL );
2866
309
  }
2867
309
  return( -1 );
2868
4.09k
}
2869
2870
/* Reads the segment
2871
 * Returns the 1 if succesful or -1 on error
2872
 */
2873
int libvslvm_metadata_read_segment(
2874
     libvslvm_metadata_t *metadata,
2875
     libvslvm_logical_volume_values_t *logical_volume_values,
2876
     libcsplit_narrow_split_string_t *lines,
2877
     int number_of_lines,
2878
     int *line_index,
2879
     libcerror_error_t **error )
2880
1.47k
{
2881
1.47k
  libvslvm_internal_volume_group_t *internal_volume_group = NULL;
2882
1.47k
  libvslvm_segment_t *segment                             = NULL;
2883
1.47k
  char *line_string_segment                               = NULL;
2884
1.47k
  char *value                                             = NULL;
2885
1.47k
  char *value_identifier                                  = NULL;
2886
1.47k
  static char *function                                   = "libvslvm_metadata_read_segment";
2887
1.47k
  size_t line_string_segment_index                        = 0;
2888
1.47k
  size_t line_string_segment_size                         = 0;
2889
1.47k
  size_t value_identifier_length                          = 0;
2890
1.47k
  size_t value_length                                     = 0;
2891
1.47k
  uint64_t value_64bit                                    = 0;
2892
2893
1.47k
  if( metadata == NULL )
2894
0
  {
2895
0
    libcerror_error_set(
2896
0
     error,
2897
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2898
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
2899
0
     "%s: invalid metadata.",
2900
0
     function );
2901
2902
0
    return( -1 );
2903
0
  }
2904
1.47k
  if( metadata->volume_group == NULL )
2905
0
  {
2906
0
    libcerror_error_set(
2907
0
     error,
2908
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2909
0
     LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
2910
0
     "%s: invalid metadata - missing volume group.",
2911
0
     function );
2912
2913
0
    return( -1 );
2914
0
  }
2915
1.47k
  internal_volume_group = (libvslvm_internal_volume_group_t *) metadata->volume_group;
2916
2917
1.47k
  if( internal_volume_group->extent_size == 0 )
2918
4
  {
2919
4
    libcerror_error_set(
2920
4
     error,
2921
4
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2922
4
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
2923
4
     "%s: invalid volume group - extent size value out of bounds.",
2924
4
     function );
2925
2926
4
    return( -1 );
2927
4
  }
2928
1.47k
  if( logical_volume_values == NULL )
2929
0
  {
2930
0
    libcerror_error_set(
2931
0
     error,
2932
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2933
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
2934
0
     "%s: invalid logical volume values.",
2935
0
     function );
2936
2937
0
    return( -1 );
2938
0
  }
2939
1.47k
  if( line_index == NULL )
2940
0
  {
2941
0
    libcerror_error_set(
2942
0
     error,
2943
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2944
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
2945
0
     "%s: invalid line index.",
2946
0
     function );
2947
2948
0
    return( -1 );
2949
0
  }
2950
1.47k
  if( number_of_lines <= 0 )
2951
0
  {
2952
0
    libcerror_error_set(
2953
0
     error,
2954
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2955
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
2956
0
     "%s: invalid number of lines value out of bounds.",
2957
0
     function );
2958
2959
0
    return( -1 );
2960
0
  }
2961
1.47k
  if( ( *line_index < 0 )
2962
1.47k
   || ( *line_index >= number_of_lines ) )
2963
0
  {
2964
0
    libcerror_error_set(
2965
0
     error,
2966
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
2967
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
2968
0
     "%s: invalid line index value out of bounds.",
2969
0
     function );
2970
2971
0
    return( -1 );
2972
0
  }
2973
1.47k
  if( libcsplit_narrow_split_string_get_segment_by_index(
2974
1.47k
       lines,
2975
1.47k
       *line_index,
2976
1.47k
       &line_string_segment,
2977
1.47k
       &line_string_segment_size,
2978
1.47k
       error ) != 1 )
2979
0
  {
2980
0
    libcerror_error_set(
2981
0
     error,
2982
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2983
0
     LIBCERROR_RUNTIME_ERROR_GET_FAILED,
2984
0
     "%s: unable to retrieve line: %d.",
2985
0
     function,
2986
0
     *line_index );
2987
2988
0
    goto on_error;
2989
0
  }
2990
1.47k
  if( line_string_segment == NULL )
2991
0
  {
2992
0
    libcerror_error_set(
2993
0
     error,
2994
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
2995
0
     LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
2996
0
     "%s: missing line string segment: %d.",
2997
0
     function,
2998
0
     *line_index );
2999
3000
0
    goto on_error;
3001
0
  }
3002
  /* Ignore trailing white space
3003
   */
3004
1.47k
  if( line_string_segment_size >= 2 )
3005
1.47k
  {
3006
1.47k
    line_string_segment_index = line_string_segment_size - 2;
3007
3008
28.1k
    while( line_string_segment_index > 0 )
3009
28.1k
    {
3010
28.1k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
3011
28.1k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
3012
28.1k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
3013
28.1k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
3014
28.1k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
3015
28.1k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
3016
1.47k
      {
3017
1.47k
        break;
3018
1.47k
      }
3019
26.6k
      line_string_segment_index--;
3020
26.6k
      line_string_segment_size--;
3021
26.6k
    }
3022
1.47k
  }
3023
  /* Ignore leading white space
3024
   */
3025
1.47k
  line_string_segment_index = 0;
3026
3027
193k
  while( line_string_segment_index < line_string_segment_size )
3028
193k
  {
3029
193k
    if( ( line_string_segment[ line_string_segment_index ] != '\t' )
3030
193k
     && ( line_string_segment[ line_string_segment_index ] != '\n' )
3031
193k
     && ( line_string_segment[ line_string_segment_index ] != '\f' )
3032
193k
     && ( line_string_segment[ line_string_segment_index ] != '\v' )
3033
193k
     && ( line_string_segment[ line_string_segment_index ] != '\r' )
3034
193k
     && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
3035
1.47k
    {
3036
1.47k
      break;
3037
1.47k
    }
3038
191k
    line_string_segment_index++;
3039
191k
  }
3040
1.47k
  if( ( line_string_segment_size < ( 7 + 3 ) )
3041
1.47k
   || ( line_string_segment[ line_string_segment_size - 3 ] != ' ' )
3042
1.47k
   || ( line_string_segment[ line_string_segment_size - 2 ] != '{' )
3043
1.47k
   || ( narrow_string_compare(
3044
1.47k
         &( line_string_segment[ line_string_segment_index ] ),
3045
1.47k
         "segment",
3046
1.47k
         7 ) != 0 ) )
3047
0
  {
3048
0
    libcerror_error_set(
3049
0
     error,
3050
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
3051
0
     LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE,
3052
0
     "%s: unsupported segment signature.",
3053
0
     function );
3054
3055
0
    goto on_error;
3056
0
  }
3057
1.47k
  if( libvslvm_segment_initialize(
3058
1.47k
       &segment,
3059
1.47k
       error ) != 1 )
3060
0
  {
3061
0
    libcerror_error_set(
3062
0
     error,
3063
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
3064
0
     LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED,
3065
0
     "%s: unable to create segment.",
3066
0
     function );
3067
3068
0
    goto on_error;
3069
0
  }
3070
1.47k
  if( ( line_string_segment_size < 2 )
3071
1.47k
   || ( line_string_segment_index >= ( line_string_segment_size - 2 ) ) )
3072
0
  {
3073
0
    libcerror_error_set(
3074
0
     error,
3075
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
3076
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
3077
0
     "%s: invalid line string segment size value out of bounds.",
3078
0
     function );
3079
3080
0
    goto on_error;
3081
0
  }
3082
1.47k
  if( libvslvm_internal_segment_set_name(
3083
1.47k
       (libvslvm_internal_segment_t *) segment,
3084
1.47k
       &( line_string_segment[ line_string_segment_index ] ),
3085
1.47k
       line_string_segment_size - ( line_string_segment_index + 2 ),
3086
1.47k
       error ) != 1 )
3087
0
  {
3088
0
    libcerror_error_set(
3089
0
     error,
3090
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
3091
0
     LIBCERROR_RUNTIME_ERROR_SET_FAILED,
3092
0
     "%s: unable to set segment name.",
3093
0
     function );
3094
3095
0
    goto on_error;
3096
0
  }
3097
#if defined( HAVE_DEBUG_OUTPUT )
3098
  if( libcnotify_verbose != 0 )
3099
  {
3100
    libcnotify_printf(
3101
     "\n" );
3102
3103
    libcnotify_printf(
3104
     "%s: name\t\t\t\t\t: %s\n",
3105
     function,
3106
     ( (libvslvm_internal_segment_t *) segment )->name );
3107
  }
3108
#endif
3109
1.47k
  *line_index += 1;
3110
3111
5.93M
  while( *line_index < number_of_lines )
3112
5.93M
  {
3113
5.93M
    if( libcsplit_narrow_split_string_get_segment_by_index(
3114
5.93M
         lines,
3115
5.93M
         *line_index,
3116
5.93M
         &line_string_segment,
3117
5.93M
         &line_string_segment_size,
3118
5.93M
         error ) != 1 )
3119
0
    {
3120
0
      libcerror_error_set(
3121
0
       error,
3122
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
3123
0
       LIBCERROR_RUNTIME_ERROR_GET_FAILED,
3124
0
       "%s: unable to retrieve line: %d.",
3125
0
       function,
3126
0
       *line_index );
3127
3128
0
      goto on_error;
3129
0
    }
3130
5.93M
    if( line_string_segment == NULL )
3131
0
    {
3132
0
      libcerror_error_set(
3133
0
       error,
3134
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
3135
0
       LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
3136
0
       "%s: missing line string segment: %d.",
3137
0
       function,
3138
0
       *line_index );
3139
3140
0
      goto on_error;
3141
0
    }
3142
    /* Ignore trailing white space
3143
     */
3144
5.93M
    if( line_string_segment_size >= 2 )
3145
61.8k
    {
3146
61.8k
      line_string_segment_index = line_string_segment_size - 2;
3147
3148
191k
      while( line_string_segment_index > 0 )
3149
168k
      {
3150
168k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
3151
168k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
3152
168k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
3153
168k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
3154
168k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
3155
168k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
3156
38.3k
        {
3157
38.3k
          break;
3158
38.3k
        }
3159
129k
        line_string_segment_index--;
3160
129k
        line_string_segment_size--;
3161
129k
      }
3162
61.8k
    }
3163
    /* Ignore leading white space
3164
     */
3165
5.93M
    line_string_segment_index = 0;
3166
3167
6.57M
    while( line_string_segment_index < line_string_segment_size )
3168
6.57M
    {
3169
6.57M
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
3170
6.57M
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
3171
6.57M
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
3172
6.57M
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
3173
6.57M
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
3174
6.57M
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
3175
5.93M
      {
3176
5.93M
        break;
3177
5.93M
      }
3178
642k
      line_string_segment_index++;
3179
642k
    }
3180
    /* Skip an empty line
3181
     */
3182
5.93M
    if( ( line_string_segment_index >= line_string_segment_size )
3183
5.93M
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
3184
5.87M
    {
3185
5.87M
      *line_index += 1;
3186
3187
5.87M
      continue;
3188
5.87M
    }
3189
    /* Check for the end of section
3190
     */
3191
57.4k
    if( ( ( line_string_segment_size - line_string_segment_index ) == 2 )
3192
57.4k
     && ( line_string_segment[ line_string_segment_index ] == '}' ) )
3193
657
    {
3194
657
      *line_index += 1;
3195
3196
657
      break;
3197
657
    }
3198
    /* Determine the value identifier
3199
     */
3200
56.8k
    value_identifier        = &( line_string_segment[ line_string_segment_index ] );
3201
56.8k
    value_identifier_length = 0;
3202
3203
8.46M
    while( line_string_segment_index < line_string_segment_size )
3204
8.44M
    {
3205
8.44M
      if( ( line_string_segment[ line_string_segment_index ] == '\t' )
3206
8.44M
       || ( line_string_segment[ line_string_segment_index ] == '\n' )
3207
8.44M
       || ( line_string_segment[ line_string_segment_index ] == '\f' )
3208
8.44M
       || ( line_string_segment[ line_string_segment_index ] == '\v' )
3209
8.44M
       || ( line_string_segment[ line_string_segment_index ] == '\r' )
3210
8.44M
       || ( line_string_segment[ line_string_segment_index ] == ' ' )
3211
8.44M
       || ( line_string_segment[ line_string_segment_index ] == '=' ) )
3212
38.7k
      {
3213
38.7k
        break;
3214
38.7k
      }
3215
8.41M
      value_identifier_length++;
3216
3217
8.41M
      line_string_segment_index++;
3218
8.41M
    }
3219
    /* Skip a line not containing a value
3220
     */
3221
56.8k
    if( ( line_string_segment_index >= line_string_segment_size )
3222
56.8k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
3223
18.1k
    {
3224
18.1k
      *line_index += 1;
3225
3226
18.1k
      continue;
3227
18.1k
    }
3228
    /* Make sure the value identifier is terminated by an end of string
3229
     */
3230
38.7k
    line_string_segment[ line_string_segment_index ] = 0;
3231
3232
38.7k
    line_string_segment_index++;
3233
3234
    /* Ignore whitespace
3235
     */
3236
108k
    while( line_string_segment_index < line_string_segment_size )
3237
101k
    {
3238
101k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
3239
101k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
3240
101k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
3241
101k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
3242
101k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
3243
101k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
3244
31.5k
      {
3245
31.5k
        break;
3246
31.5k
      }
3247
69.4k
      line_string_segment_index++;
3248
69.4k
    }
3249
38.7k
    if( line_string_segment[ line_string_segment_index ] == '=' )
3250
5.11k
    {
3251
5.11k
      line_string_segment_index++;
3252
3253
11.5k
      while( line_string_segment_index < line_string_segment_size )
3254
9.79k
      {
3255
9.79k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
3256
9.79k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
3257
9.79k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
3258
9.79k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
3259
9.79k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
3260
9.79k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
3261
3.38k
        {
3262
3.38k
          break;
3263
3.38k
        }
3264
6.40k
        line_string_segment_index++;
3265
6.40k
      }
3266
5.11k
    }
3267
    /* Skip a line not containing a value
3268
     */
3269
38.7k
    if( ( line_string_segment_index >= line_string_segment_size )
3270
38.7k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
3271
13.9k
    {
3272
13.9k
      *line_index += 1;
3273
3274
13.9k
      continue;
3275
13.9k
    }
3276
    /* Ingore quotes at the beginning of the value data
3277
     */
3278
24.7k
    if( ( line_string_segment[ line_string_segment_index ] == '"' )
3279
24.7k
     || ( line_string_segment[ line_string_segment_index ] == '\'' ) )
3280
2.44k
    {
3281
2.44k
      line_string_segment_index++;
3282
2.44k
    }
3283
    /* Determine the value
3284
     */
3285
24.7k
    value        = &( line_string_segment[ line_string_segment_index ] );
3286
24.7k
    value_length = 0;
3287
3288
196k
    while( line_string_segment_index < line_string_segment_size )
3289
195k
    {
3290
195k
      if( ( line_string_segment[ line_string_segment_index ] == 0 )
3291
195k
       || ( line_string_segment[ line_string_segment_index ] == '\t' )
3292
195k
       || ( line_string_segment[ line_string_segment_index ] == '\n' )
3293
195k
       || ( line_string_segment[ line_string_segment_index ] == '\f' )
3294
195k
       || ( line_string_segment[ line_string_segment_index ] == '\v' )
3295
195k
       || ( line_string_segment[ line_string_segment_index ] == '\r' )
3296
195k
       || ( line_string_segment[ line_string_segment_index ] == '#' ) )
3297
24.0k
      {
3298
24.0k
        break;
3299
24.0k
      }
3300
171k
      line_string_segment_index++;
3301
171k
      value_length++;
3302
171k
    }
3303
    /* Ingore quotes at the end of the value data
3304
     */
3305
24.7k
    if( ( line_string_segment[ line_string_segment_index - 1 ] == '"' )
3306
24.7k
     || ( line_string_segment[ line_string_segment_index - 1 ] == '\'' ) )
3307
1.89k
    {
3308
1.89k
      line_string_segment_index--;
3309
1.89k
      value_length--;
3310
1.89k
    }
3311
    /* Make sure the value is terminated by an end of string
3312
     */
3313
24.7k
    line_string_segment[ line_string_segment_index ] = 0;
3314
3315
24.7k
    if( value_identifier_length == 4 )
3316
2.44k
    {
3317
2.44k
      if( narrow_string_compare(
3318
2.44k
           value_identifier,
3319
2.44k
           "type",
3320
2.44k
           4 ) == 0 )
3321
236
      {
3322
#if defined( HAVE_DEBUG_OUTPUT )
3323
        if( libcnotify_verbose != 0 )
3324
        {
3325
          libcnotify_printf(
3326
           "%s: type\t\t\t\t\t: %s\n",
3327
           function,
3328
           value );
3329
        }
3330
#endif
3331
/* TODO */
3332
236
      }
3333
2.44k
    }
3334
22.2k
    else if( value_identifier_length == 7 )
3335
2.65k
    {
3336
2.65k
      if( narrow_string_compare(
3337
2.65k
           value_identifier,
3338
2.65k
           "stripes",
3339
2.65k
           7 ) == 0 )
3340
2.19k
      {
3341
#if defined( HAVE_DEBUG_OUTPUT )
3342
        if( libcnotify_verbose != 0 )
3343
        {
3344
          libcnotify_printf(
3345
           "%s: stripes list:\n",
3346
           function );
3347
        }
3348
#endif
3349
2.19k
        if( ( value_length != 1 )
3350
2.19k
         || ( value[ 0 ] != '[' )
3351
2.19k
         || ( libvslvm_metadata_read_stripes_list(
3352
2.18k
               metadata,
3353
2.18k
               segment,
3354
2.18k
               lines,
3355
2.18k
               number_of_lines,
3356
2.18k
               line_index,
3357
2.18k
               error ) != 1 ) )
3358
291
        {
3359
291
          libcerror_error_set(
3360
291
           error,
3361
291
           LIBCERROR_ERROR_DOMAIN_IO,
3362
291
           LIBCERROR_IO_ERROR_READ_FAILED,
3363
291
           "%s: unable to read stripes list.",
3364
291
           function );
3365
3366
291
          goto on_error;
3367
291
        }
3368
/* TODO validate number of stripes */
3369
2.19k
      }
3370
2.65k
    }
3371
19.6k
    else if( value_identifier_length == 12 )
3372
1.19k
    {
3373
1.19k
      if( narrow_string_compare(
3374
1.19k
           value_identifier,
3375
1.19k
           "extent_count",
3376
1.19k
           12 ) == 0 )
3377
341
      {
3378
#if defined( HAVE_DEBUG_OUTPUT )
3379
        if( libcnotify_verbose != 0 )
3380
        {
3381
          libcnotify_printf(
3382
           "%s: number of extents\t\t\t: %s\n",
3383
           function,
3384
           value );
3385
        }
3386
#endif
3387
341
        if( libfvalue_utf8_string_copy_to_integer(
3388
341
             (uint8_t *) value,
3389
341
             value_length + 1,
3390
341
             &value_64bit,
3391
341
             64,
3392
341
             LIBFVALUE_INTEGER_FORMAT_TYPE_DECIMAL_UNSIGNED,
3393
341
             error ) != 1 )
3394
2
        {
3395
2
          libcerror_error_set(
3396
2
           error,
3397
2
           LIBCERROR_ERROR_DOMAIN_MEMORY,
3398
2
           LIBCERROR_MEMORY_ERROR_SET_FAILED,
3399
2
           "%s: unable to set number of extents.",
3400
2
           function );
3401
3402
2
          goto on_error;
3403
2
        }
3404
339
        if( value_64bit > (uint64_t) ( UINT64_MAX / internal_volume_group->extent_size ) )
3405
1
        {
3406
1
          libcerror_error_set(
3407
1
           error,
3408
1
           LIBCERROR_ERROR_DOMAIN_RUNTIME,
3409
1
           LIBCERROR_RUNTIME_ERROR_VALUE_EXCEEDS_MAXIMUM,
3410
1
           "%s: invalid number of extents value exceeds maximum.",
3411
1
           function );
3412
3413
1
          goto on_error;
3414
1
        }
3415
338
        value_64bit *= internal_volume_group->extent_size;
3416
3417
338
        ( (libvslvm_internal_segment_t *) segment )->size = value_64bit;
3418
338
      }
3419
850
      else if( narrow_string_compare(
3420
850
                value_identifier,
3421
850
                "start_extent",
3422
850
                12 ) == 0 )
3423
315
      {
3424
#if defined( HAVE_DEBUG_OUTPUT )
3425
        if( libcnotify_verbose != 0 )
3426
        {
3427
          libcnotify_printf(
3428
           "%s: start extent\t\t\t\t: %s\n",
3429
           function,
3430
           value );
3431
        }
3432
#endif
3433
315
        if( libfvalue_utf8_string_copy_to_integer(
3434
315
             (uint8_t *) value,
3435
315
             value_length + 1,
3436
315
             &value_64bit,
3437
315
             64,
3438
315
             LIBFVALUE_INTEGER_FORMAT_TYPE_DECIMAL_UNSIGNED,
3439
315
             error ) != 1 )
3440
1
        {
3441
1
          libcerror_error_set(
3442
1
           error,
3443
1
           LIBCERROR_ERROR_DOMAIN_MEMORY,
3444
1
           LIBCERROR_MEMORY_ERROR_SET_FAILED,
3445
1
           "%s: unable to set start extent.",
3446
1
           function );
3447
3448
1
          goto on_error;
3449
1
        }
3450
314
        if( value_64bit > (uint64_t) ( UINT64_MAX / internal_volume_group->extent_size ) )
3451
3
        {
3452
3
          libcerror_error_set(
3453
3
           error,
3454
3
           LIBCERROR_ERROR_DOMAIN_RUNTIME,
3455
3
           LIBCERROR_RUNTIME_ERROR_VALUE_EXCEEDS_MAXIMUM,
3456
3
           "%s: invalid start extent value exceeds maximum.",
3457
3
           function );
3458
3459
3
          goto on_error;
3460
3
        }
3461
311
        value_64bit *= internal_volume_group->extent_size;
3462
3463
311
        ( (libvslvm_internal_segment_t *) segment )->offset = value_64bit;
3464
311
      }
3465
535
      else if( narrow_string_compare(
3466
535
                value_identifier,
3467
535
                "stripe_count",
3468
535
                12 ) == 0 )
3469
0
      {
3470
#if defined( HAVE_DEBUG_OUTPUT )
3471
        if( libcnotify_verbose != 0 )
3472
        {
3473
          libcnotify_printf(
3474
           "%s: number of stripes\t\t\t: %s\n",
3475
           function,
3476
           value );
3477
        }
3478
#endif
3479
/* TODO */
3480
0
      }
3481
1.19k
    }
3482
#if defined( HAVE_DEBUG_OUTPUT )
3483
    else if( libcnotify_verbose != 0 )
3484
    {
3485
      libcnotify_printf(
3486
       "%s: value: %d\t\t\t\t: %s = %s\n",
3487
       function,
3488
       *line_index,
3489
       value_identifier,
3490
       value );
3491
    }
3492
#endif
3493
24.4k
    *line_index += 1;
3494
24.4k
  }
3495
1.17k
  if( libvslvm_logical_volume_values_append_segment(
3496
1.17k
       logical_volume_values,
3497
1.17k
       segment,
3498
1.17k
       error ) != 1 )
3499
0
  {
3500
0
    libcerror_error_set(
3501
0
     error,
3502
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
3503
0
     LIBCERROR_RUNTIME_ERROR_APPEND_FAILED,
3504
0
     "%s: unable to append segment to logical volume values.",
3505
0
     function );
3506
3507
0
    goto on_error;
3508
0
  }
3509
1.17k
  segment = NULL;
3510
3511
1.17k
  return( 1 );
3512
3513
298
on_error:
3514
298
  if( segment != NULL )
3515
298
  {
3516
298
    libvslvm_internal_segment_free(
3517
298
     (libvslvm_internal_segment_t **) &segment,
3518
298
     NULL );
3519
298
  }
3520
298
  return( -1 );
3521
1.17k
}
3522
3523
/* Reads the stripes list
3524
 * Returns the 1 if succesful or -1 on error
3525
 */
3526
int libvslvm_metadata_read_stripes_list(
3527
     libvslvm_metadata_t *metadata,
3528
     libvslvm_segment_t *segment,
3529
     libcsplit_narrow_split_string_t *lines,
3530
     int number_of_lines,
3531
     int *line_index,
3532
     libcerror_error_t **error )
3533
2.18k
{
3534
2.18k
  libvslvm_internal_volume_group_t *internal_volume_group = NULL;
3535
2.18k
  libvslvm_stripe_t *stripe                               = NULL;
3536
2.18k
  char *line_string_segment                               = NULL;
3537
2.18k
  char *value                                             = NULL;
3538
2.18k
  char *value_identifier                                  = NULL;
3539
2.18k
  static char *function                                   = "libvslvm_metadata_read_stripes_list";
3540
2.18k
  size_t line_string_segment_index                        = 0;
3541
2.18k
  size_t line_string_segment_size                         = 0;
3542
2.18k
  size_t value_identifier_length                          = 0;
3543
2.18k
  size_t value_length                                     = 0;
3544
2.18k
  uint64_t value_64bit                                    = 0;
3545
3546
2.18k
  if( metadata == NULL )
3547
0
  {
3548
0
    libcerror_error_set(
3549
0
     error,
3550
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
3551
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
3552
0
     "%s: invalid metadata.",
3553
0
     function );
3554
3555
0
    return( -1 );
3556
0
  }
3557
2.18k
  if( metadata->volume_group == NULL )
3558
0
  {
3559
0
    libcerror_error_set(
3560
0
     error,
3561
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
3562
0
     LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
3563
0
     "%s: invalid metadata - missing volume group.",
3564
0
     function );
3565
3566
0
    return( -1 );
3567
0
  }
3568
2.18k
  internal_volume_group = (libvslvm_internal_volume_group_t *) metadata->volume_group;
3569
3570
2.18k
  if( internal_volume_group->extent_size == 0 )
3571
0
  {
3572
0
    libcerror_error_set(
3573
0
     error,
3574
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
3575
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
3576
0
     "%s: invalid volume group - extent size value out of bounds.",
3577
0
     function );
3578
3579
0
    return( -1 );
3580
0
  }
3581
2.18k
  if( line_index == NULL )
3582
0
  {
3583
0
    libcerror_error_set(
3584
0
     error,
3585
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
3586
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
3587
0
     "%s: invalid line index.",
3588
0
     function );
3589
3590
0
    return( -1 );
3591
0
  }
3592
2.18k
  if( number_of_lines <= 0 )
3593
0
  {
3594
0
    libcerror_error_set(
3595
0
     error,
3596
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
3597
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
3598
0
     "%s: invalid number of lines value out of bounds.",
3599
0
     function );
3600
3601
0
    return( -1 );
3602
0
  }
3603
2.18k
  if( ( *line_index < 0 )
3604
2.18k
   || ( *line_index >= number_of_lines ) )
3605
0
  {
3606
0
    libcerror_error_set(
3607
0
     error,
3608
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
3609
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
3610
0
     "%s: invalid line index value out of bounds.",
3611
0
     function );
3612
3613
0
    return( -1 );
3614
0
  }
3615
2.18k
  *line_index += 1;
3616
3617
389k
  while( *line_index < number_of_lines )
3618
389k
  {
3619
389k
    if( libcsplit_narrow_split_string_get_segment_by_index(
3620
389k
         lines,
3621
389k
         *line_index,
3622
389k
         &line_string_segment,
3623
389k
         &line_string_segment_size,
3624
389k
         error ) != 1 )
3625
0
    {
3626
0
      libcerror_error_set(
3627
0
       error,
3628
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
3629
0
       LIBCERROR_RUNTIME_ERROR_GET_FAILED,
3630
0
       "%s: unable to retrieve line: %d.",
3631
0
       function,
3632
0
       *line_index );
3633
3634
0
      goto on_error;
3635
0
    }
3636
389k
    if( line_string_segment == NULL )
3637
0
    {
3638
0
      libcerror_error_set(
3639
0
       error,
3640
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
3641
0
       LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
3642
0
       "%s: missing line string segment: %d.",
3643
0
       function,
3644
0
       *line_index );
3645
3646
0
      goto on_error;
3647
0
    }
3648
    /* Ignore trailing white space
3649
     */
3650
389k
    if( line_string_segment_size >= 2 )
3651
145k
    {
3652
145k
      line_string_segment_index = line_string_segment_size - 2;
3653
3654
267k
      while( line_string_segment_index > 0 )
3655
242k
      {
3656
242k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
3657
242k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
3658
242k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
3659
242k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
3660
242k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
3661
242k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
3662
120k
        {
3663
120k
          break;
3664
120k
        }
3665
122k
        line_string_segment_index--;
3666
122k
        line_string_segment_size--;
3667
122k
      }
3668
145k
    }
3669
    /* Ignore leading white space
3670
     */
3671
389k
    line_string_segment_index = 0;
3672
3673
654k
    while( line_string_segment_index < line_string_segment_size )
3674
652k
    {
3675
652k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
3676
652k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
3677
652k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
3678
652k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
3679
652k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
3680
652k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
3681
386k
      {
3682
386k
        break;
3683
386k
      }
3684
265k
      line_string_segment_index++;
3685
265k
    }
3686
    /* Skip an empty line
3687
     */
3688
389k
    if( ( line_string_segment_index >= line_string_segment_size )
3689
389k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
3690
248k
    {
3691
248k
      *line_index += 1;
3692
3693
248k
      continue;
3694
248k
    }
3695
    /* Check for the end of section
3696
     */
3697
140k
    if( ( ( line_string_segment_size - line_string_segment_index ) == 2 )
3698
140k
     && ( line_string_segment[ line_string_segment_index ] == ']' ) )
3699
1.81k
    {
3700
1.81k
      break;
3701
1.81k
    }
3702
    /* Ingore quotes at the beginning of the value data
3703
     */
3704
138k
    if( ( line_string_segment[ line_string_segment_index ] == '"' )
3705
138k
     || ( line_string_segment[ line_string_segment_index ] == '\'' ) )
3706
8.28k
    {
3707
8.28k
      line_string_segment_index++;
3708
8.28k
    }
3709
    /* Determine the value identifier
3710
     */
3711
138k
    value_identifier        = &( line_string_segment[ line_string_segment_index ] );
3712
138k
    value_identifier_length = 0;
3713
3714
4.52M
    while( line_string_segment_index < line_string_segment_size )
3715
4.49M
    {
3716
4.49M
      if( ( line_string_segment[ line_string_segment_index ] == '\t' )
3717
4.49M
       || ( line_string_segment[ line_string_segment_index ] == '\n' )
3718
4.49M
       || ( line_string_segment[ line_string_segment_index ] == '\f' )
3719
4.49M
       || ( line_string_segment[ line_string_segment_index ] == '\v' )
3720
4.49M
       || ( line_string_segment[ line_string_segment_index ] == '\r' )
3721
4.49M
       || ( line_string_segment[ line_string_segment_index ] == ' ' )
3722
4.49M
       || ( line_string_segment[ line_string_segment_index ] == ',' ) )
3723
113k
      {
3724
113k
        break;
3725
113k
      }
3726
4.38M
      value_identifier_length++;
3727
3728
4.38M
      line_string_segment_index++;
3729
4.38M
    }
3730
    /* Skip a line not containing a value
3731
     */
3732
138k
    if( ( line_string_segment_index >= line_string_segment_size )
3733
138k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
3734
25.6k
    {
3735
25.6k
      *line_index += 1;
3736
3737
25.6k
      continue;
3738
25.6k
    }
3739
    /* Ingore quotes at the end of the value identifier
3740
     */
3741
113k
    if( ( line_string_segment[ line_string_segment_index - 1 ] == '"' )
3742
113k
     || ( line_string_segment[ line_string_segment_index - 1 ] == '\'' ) )
3743
10.3k
    {
3744
10.3k
      value_identifier_length--;
3745
3746
      /* Make sure the value identifier is terminated by an end of string
3747
       */
3748
10.3k
      line_string_segment[ line_string_segment_index - 1 ] = 0;
3749
10.3k
    }
3750
102k
    else
3751
102k
    {
3752
      /* Make sure the value identifier is terminated by an end of string
3753
       */
3754
102k
      line_string_segment[ line_string_segment_index ] = 0;
3755
102k
    }
3756
113k
    line_string_segment_index++;
3757
3758
    /* Ignore whitespace
3759
     */
3760
227k
    while( line_string_segment_index < line_string_segment_size )
3761
209k
    {
3762
209k
      if( ( line_string_segment[ line_string_segment_index ] != '\t' )
3763
209k
       && ( line_string_segment[ line_string_segment_index ] != '\n' )
3764
209k
       && ( line_string_segment[ line_string_segment_index ] != '\f' )
3765
209k
       && ( line_string_segment[ line_string_segment_index ] != '\v' )
3766
209k
       && ( line_string_segment[ line_string_segment_index ] != '\r' )
3767
209k
       && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
3768
95.4k
      {
3769
95.4k
        break;
3770
95.4k
      }
3771
114k
      line_string_segment_index++;
3772
114k
    }
3773
113k
    if( line_string_segment[ line_string_segment_index ] == ',' )
3774
9.98k
    {
3775
9.98k
      line_string_segment_index++;
3776
3777
19.9k
      while( line_string_segment_index < line_string_segment_size )
3778
19.4k
      {
3779
19.4k
        if( ( line_string_segment[ line_string_segment_index ] != '\t' )
3780
19.4k
         && ( line_string_segment[ line_string_segment_index ] != '\n' )
3781
19.4k
         && ( line_string_segment[ line_string_segment_index ] != '\f' )
3782
19.4k
         && ( line_string_segment[ line_string_segment_index ] != '\v' )
3783
19.4k
         && ( line_string_segment[ line_string_segment_index ] != '\r' )
3784
19.4k
         && ( line_string_segment[ line_string_segment_index ] != ' ' ) )
3785
9.48k
        {
3786
9.48k
          break;
3787
9.48k
        }
3788
9.95k
        line_string_segment_index++;
3789
9.95k
      }
3790
9.98k
    }
3791
    /* Skip a line not containing a value
3792
     */
3793
113k
    if( ( line_string_segment_index >= line_string_segment_size )
3794
113k
     || ( line_string_segment[ line_string_segment_index ] == 0 ) )
3795
23.9k
    {
3796
23.9k
      *line_index += 1;
3797
3798
23.9k
      continue;
3799
23.9k
    }
3800
    /* Determine the value
3801
     */
3802
89.3k
    value        = &( line_string_segment[ line_string_segment_index ] );
3803
89.3k
    value_length = line_string_segment_size - 1;
3804
3805
    /* Make sure the value is terminated by an end of string
3806
     */
3807
89.3k
    line_string_segment[ value_length ] = 0;
3808
3809
89.3k
    value_length -= line_string_segment_index;
3810
3811
#if defined( HAVE_DEBUG_OUTPUT )
3812
    if( libcnotify_verbose != 0 )
3813
    {
3814
      libcnotify_printf(
3815
       "%s: value: %d\t\t\t\t: %s, %s\n",
3816
       function,
3817
       *line_index,
3818
       value_identifier,
3819
       value );
3820
    }
3821
#endif
3822
89.3k
    *line_index += 1;
3823
3824
89.3k
    if( libfvalue_utf8_string_copy_to_integer(
3825
89.3k
         (uint8_t *) value,
3826
89.3k
         value_length + 1,
3827
89.3k
         &value_64bit,
3828
89.3k
         64,
3829
89.3k
         LIBFVALUE_INTEGER_FORMAT_TYPE_DECIMAL_UNSIGNED,
3830
89.3k
         error ) != 1 )
3831
266
    {
3832
266
      libcerror_error_set(
3833
266
       error,
3834
266
       LIBCERROR_ERROR_DOMAIN_MEMORY,
3835
266
       LIBCERROR_MEMORY_ERROR_SET_FAILED,
3836
266
       "%s: unable to set data area offset.",
3837
266
       function );
3838
3839
266
      goto on_error;
3840
266
    }
3841
89.0k
    if( value_64bit > (uint64_t) ( UINT64_MAX / internal_volume_group->extent_size ) )
3842
11
    {
3843
11
      libcerror_error_set(
3844
11
       error,
3845
11
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
3846
11
       LIBCERROR_RUNTIME_ERROR_VALUE_EXCEEDS_MAXIMUM,
3847
11
       "%s: invalid data area offset value exceeds maximum.",
3848
11
       function );
3849
3850
11
      goto on_error;
3851
11
    }
3852
89.0k
    value_64bit *= internal_volume_group->extent_size;
3853
3854
89.0k
    if( libvslvm_stripe_initialize(
3855
89.0k
         &stripe,
3856
89.0k
         error ) != 1 )
3857
0
    {
3858
0
      libcerror_error_set(
3859
0
       error,
3860
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
3861
0
       LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED,
3862
0
       "%s: unable to create stripe.",
3863
0
       function );
3864
3865
0
      goto on_error;
3866
0
    }
3867
89.0k
    if( libvslvm_internal_stripe_set_physical_volume_name(
3868
89.0k
         (libvslvm_internal_stripe_t *) stripe,
3869
89.0k
         value_identifier,
3870
89.0k
         value_identifier_length + 1,
3871
89.0k
         error ) != 1 )
3872
1
    {
3873
1
      libcerror_error_set(
3874
1
       error,
3875
1
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
3876
1
       LIBCERROR_RUNTIME_ERROR_SET_FAILED,
3877
1
       "%s: unable to set physical volume name.",
3878
1
       function );
3879
3880
1
      goto on_error;
3881
1
    }
3882
89.0k
    if( libvslvm_stripe_set_data_area_offset(
3883
89.0k
         stripe,
3884
89.0k
         value_64bit,
3885
89.0k
         error ) != 1 )
3886
0
    {
3887
0
      libcerror_error_set(
3888
0
       error,
3889
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
3890
0
       LIBCERROR_RUNTIME_ERROR_SET_FAILED,
3891
0
       "%s: unable to set data area offset.",
3892
0
       function );
3893
3894
0
      goto on_error;
3895
0
    }
3896
89.0k
    if( libvslvm_segment_append_stripe(
3897
89.0k
         segment,
3898
89.0k
         stripe,
3899
89.0k
         error ) != 1 )
3900
0
    {
3901
0
      libcerror_error_set(
3902
0
       error,
3903
0
       LIBCERROR_ERROR_DOMAIN_RUNTIME,
3904
0
       LIBCERROR_RUNTIME_ERROR_APPEND_FAILED,
3905
0
       "%s: unable to append stripe to segment.",
3906
0
       function );
3907
3908
0
      goto on_error;
3909
0
    }
3910
89.0k
    stripe = NULL;
3911
89.0k
  }
3912
1.90k
  return( 1 );
3913
3914
278
on_error:
3915
278
  if( stripe != NULL )
3916
1
  {
3917
1
    libvslvm_internal_stripe_free(
3918
1
     (libvslvm_internal_stripe_t **) &stripe,
3919
1
     NULL );
3920
1
  }
3921
278
  return( -1 );
3922
2.18k
}
3923
3924
/* Retrieves the volume group
3925
 * Returns 1 if successful, 0 if not available or -1 on error
3926
 */
3927
int libvslvm_metadata_get_volume_group(
3928
     libvslvm_metadata_t *metadata,
3929
     libvslvm_volume_group_t **volume_group,
3930
     libcerror_error_t **error )
3931
2.41k
{
3932
2.41k
  static char *function = "libvslvm_metadata_get_volume_group";
3933
3934
2.41k
  if( metadata == NULL )
3935
0
  {
3936
0
    libcerror_error_set(
3937
0
     error,
3938
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
3939
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
3940
0
     "%s: invalid metadata.",
3941
0
     function );
3942
3943
0
    return( -1 );
3944
0
  }
3945
2.41k
  if( volume_group == NULL )
3946
0
  {
3947
0
    libcerror_error_set(
3948
0
     error,
3949
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
3950
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
3951
0
     "%s: invalid volume group.",
3952
0
     function );
3953
3954
0
    return( -1 );
3955
0
  }
3956
2.41k
  if( *volume_group != NULL )
3957
0
  {
3958
0
    libcerror_error_set(
3959
0
     error,
3960
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
3961
0
     LIBCERROR_RUNTIME_ERROR_VALUE_ALREADY_SET,
3962
0
     "%s: invalid volume group value already set.",
3963
0
     function );
3964
3965
0
    return( -1 );
3966
0
  }
3967
2.41k
  if( metadata->volume_group == NULL )
3968
0
  {
3969
0
    return( 0 );
3970
0
  }
3971
2.41k
  *volume_group = metadata->volume_group;
3972
3973
2.41k
  return( 1 );
3974
2.41k
}
3975