patterncMinor
Standard way of reading file contents to a buffer
Viewed 0 times
readingfilecontentswaystandardbuffer
Problem
I have been trying to write a sample code block to read file contents into a buffer.
I am assuming that:
Do you think the return of
I am assuming that:
- Code must be platform independent
- Should work in all cases(or report proper error)
- It should be readable and maintainable
- It shouldn't be over-complex and shouldn't have errors
Do you think the return of
fseek should be tested as well?void
die( int error_code, char* message )
{
fprintf( stderr, message );
exit( error_code );
}
char *
read_certificate_file ( char *file_location )
{
FILE *file_descriptor = NULL;
size_t file_size = 0;
size_t bytes_read = 0;
char *certificate_content = NULL;
file_descriptor = fopen ( file_location, "r" );
if ( file_descriptor == NULL ) {
perror ( "Opening certificate file" );
die ( EXIT_FAILURE, "Error opening certificate file." );
}
fseek (file_descriptor, 0, SEEK_END);
file_size = ftell ( file_descriptor );
if ( file_size == 0 ) {
fclose ( file_descriptor );
die ( EXIT_FAILURE, "Certificate file is empty." );
}
certificate_content = (char *) malloc ( file_size+1 );
if ( certificate_content == NULL ) {
fclose( file_descriptor );
die( EXIT_FAILURE, "Error allocating memory for " \
" certificate." );
}
certificate_content[ file_size ] = '\0';
fseek ( file_descriptor, 0, SEEK_SET );
bytes_read = fread ( certificate_content, 1, file_size,
file_descriptor );
if ( bytes_read != file_size ) {
perror ( "Reading Certificate file" );
fclose( file_descriptor );
die ( EXIT_FAILURE, "Error reading "
"certificate file." );
}
fclose ( file_descriptor );
return certificate_content;
}
int main()
{
printf( "%s", read_certificate_file ( "./certificate.pem" ));
return EXIT_SUCCESS;
}Solution
A few things stand out...
Function declarations
I'm not a huge fan of specify return type on previous line style:
However, if you're going to use it, be consistent (your main is defined differently).
should work in all cases
You're assuming that the file you're reading does't contain any nulls. This may be OK, as you're not opening the file in binary mode, however if you decide to reuse the code for binary files, returning a null terminated buffer without a size field is going to cause issues.
Main is leaking
I know your main is just a test harness to demonstrate the code, however it's best to always use appropriate memory management. Your function is allocating a buffer using
Function declarations
I'm not a huge fan of specify return type on previous line style:
void
die( int error_code, char* message )However, if you're going to use it, be consistent (your main is defined differently).
should work in all cases
You're assuming that the file you're reading does't contain any nulls. This may be OK, as you're not opening the file in binary mode, however if you decide to reuse the code for binary files, returning a null terminated buffer without a size field is going to cause issues.
Main is leaking
I know your main is just a test harness to demonstrate the code, however it's best to always use appropriate memory management. Your function is allocating a buffer using
malloc, you should be freeing it in your main. By including this in your example it demonstrates that you recognise responsibility for the returned buffer is sitting with the caller.Code Snippets
void
die( int error_code, char* message )Context
StackExchange Code Review Q#137818, answer score: 6
Revisions (0)
No revisions yet.