Coverage Report

Created: 2026-01-20 07:11

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/libsmraw/libsmraw/libsmraw_filename.c
Line
Count
Source
1
/*
2
 * Filename functions
3
 *
4
 * Copyright (C) 2010-2025, 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 <file_stream.h>
24
#include <memory.h>
25
#include <narrow_string.h>
26
#include <system_string.h>
27
#include <types.h>
28
#include <wide_string.h>
29
30
#include "libsmraw_definitions.h"
31
#include "libsmraw_handle.h"
32
#include "libsmraw_information_file.h"
33
#include "libsmraw_libbfio.h"
34
#include "libsmraw_libcerror.h"
35
#include "libsmraw_libcnotify.h"
36
#include "libsmraw_handle.h"
37
#include "libsmraw_types.h"
38
39
/* Creates a (split) RAW filename
40
 * Returns 1 if successful or -1 on error
41
 */
42
int libsmraw_filename_create(
43
     system_character_t **filename,
44
     size_t *filename_size,
45
     system_character_t *basename,
46
     size_t basename_size,
47
     int number_of_segments,
48
     int segment_index,
49
     libcerror_error_t **error )
50
0
{
51
0
  static char *function    = "libsmraw_filename_create";
52
0
  size_t additional_length = 0;
53
0
  size_t filename_index    = 0;
54
55
0
  if( filename == NULL )
56
0
  {
57
0
    libcerror_error_set(
58
0
     error,
59
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
60
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
61
0
     "%s: invalid segment filename.",
62
0
     function );
63
64
0
    return( -1 );
65
0
  }
66
0
  if( *filename != NULL )
67
0
  {
68
0
    libcerror_error_set(
69
0
     error,
70
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
71
0
     LIBCERROR_RUNTIME_ERROR_VALUE_ALREADY_SET,
72
0
     "%s: invalid segment filename already set.",
73
0
     function );
74
75
0
    return( -1 );
76
0
  }
77
0
  if( filename_size == NULL )
78
0
  {
79
0
    libcerror_error_set(
80
0
     error,
81
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
82
0
     LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
83
0
     "%s: invalid segment filename size.",
84
0
     function );
85
86
0
    return( -1 );
87
0
  }
88
0
  if( basename == NULL )
89
0
  {
90
0
    libcerror_error_set(
91
0
     error,
92
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
93
0
     LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
94
0
     "%s: invalid basename.",
95
0
     function );
96
97
0
    return( -1 );
98
0
  }
99
0
  if( basename_size > (size_t) SSIZE_MAX )
100
0
  {
101
0
    libcerror_error_set(
102
0
     error,
103
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
104
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_EXCEEDS_MAXIMUM,
105
0
     "%s: invalid basename size value exceeds maximum.",
106
0
     function );
107
108
0
    return( -1 );
109
0
  }
110
0
  if( ( number_of_segments < 0 )
111
0
   || ( number_of_segments >= 1000 ) )
112
0
  {
113
0
    libcerror_error_set(
114
0
     error,
115
0
     LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
116
0
     LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
117
0
     "%s: invalid number of segments value out of bounds.",
118
0
     function );
119
120
0
    return( -1 );
121
0
  }
122
0
  if( number_of_segments > 0 )
123
0
  {
124
0
    if( ( segment_index < 0 )
125
0
     || ( segment_index > number_of_segments ) )
126
0
    {
127
0
      libcerror_error_set(
128
0
       error,
129
0
       LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
130
0
       LIBCERROR_ARGUMENT_ERROR_VALUE_OUT_OF_BOUNDS,
131
0
       "%s: invalid segment index value out of bounds.",
132
0
       function );
133
134
0
      return( -1 );
135
0
    }
136
0
  }
137
0
  if( number_of_segments == 1 )
138
0
  {
139
0
    additional_length = 4;
140
0
  }
141
0
  else
142
0
  {
143
0
    additional_length = 8;
144
0
  }
145
0
  *filename_size = basename_size + additional_length;
146
147
0
  *filename = system_string_allocate(
148
0
               *filename_size );
149
150
0
  if( *filename == NULL )
151
0
  {
152
0
    libcerror_error_set(
153
0
     error,
154
0
     LIBCERROR_ERROR_DOMAIN_MEMORY,
155
0
     LIBCERROR_MEMORY_ERROR_INSUFFICIENT,
156
0
     "%s: unable to create segment filename.",
157
0
     function );
158
159
0
    goto on_error;
160
0
  }
161
0
  if( system_string_copy(
162
0
       *filename,
163
0
       basename,
164
0
       basename_size - 1 ) == NULL )
165
0
  {
166
0
    libcerror_error_set(
167
0
     error,
168
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
169
0
     LIBCERROR_RUNTIME_ERROR_COPY_FAILED,
170
0
     "%s: unable to copy basename to segment filename.",
171
0
     function );
172
173
0
    goto on_error;
174
0
  }
175
0
  filename_index = basename_size - 1;
176
177
0
  if( system_string_copy(
178
0
       &( ( *filename )[ filename_index ] ),
179
0
       _SYSTEM_STRING( ".raw" ),
180
0
       4 ) == NULL )
181
0
  {
182
0
    libcerror_error_set(
183
0
     error,
184
0
     LIBCERROR_ERROR_DOMAIN_RUNTIME,
185
0
     LIBCERROR_RUNTIME_ERROR_COPY_FAILED,
186
0
     "%s: unable to copy extension to segment filename.",
187
0
     function );
188
189
0
    goto on_error;
190
0
  }
191
0
  filename_index += 4;
192
193
0
  if( number_of_segments != 1 )
194
0
  {
195
0
    ( *filename )[ filename_index++ ] = (system_character_t) '.';
196
197
0
    ( *filename )[ filename_index++ ] = (system_character_t) '0'
198
0
                                      + (system_character_t) ( segment_index / 100 );
199
200
0
    segment_index %= 100;
201
202
0
    ( *filename )[ filename_index++ ] = (system_character_t) '0'
203
0
                                      + (system_character_t) ( segment_index / 10 );
204
205
0
    segment_index %= 10;
206
207
0
    ( *filename )[ filename_index++ ] = (system_character_t) '0'
208
0
                                      + (system_character_t) segment_index;
209
0
  }
210
0
  ( *filename )[ filename_index ] = 0;
211
212
0
  return( 1 );
213
214
0
on_error:
215
0
  if( *filename != NULL )
216
0
  {
217
0
    memory_free(
218
0
     *filename );
219
220
0
    *filename = NULL;
221
0
  }
222
0
  *filename_size = 0;
223
224
0
  return( -1 );
225
0
}
226