/* Creates a new string object from a GUID * Returns a Python object if successful or NULL on error */ PyObject *pylnk_string_new_from_guid( const uint8_t *guid_buffer, size_t guid_buffer_size ) { char guid_string[ 48 ]; libcerror_error_t *error = NULL; libfguid_identifier_t *guid = NULL; PyObject *string_object = NULL; const char *errors = NULL; static char *function = "pylnk_string_new_from_guid"; if( libfguid_identifier_initialize( &guid, &error ) != 1 ) { pylnk_error_raise( error, PyExc_IOError, "%s: unable to create GUID.", function ); libcerror_error_free( &error ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, guid_buffer, guid_buffer_size, LIBFGUID_ENDIAN_LITTLE, &error ) != 1 ) { pylnk_error_raise( error, PyExc_IOError, "%s: unable to copy byte stream to GUID.", function ); libcerror_error_free( &error ); goto on_error; } if( libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, &error ) != 1 ) { pylnk_error_raise( error, PyExc_IOError, "%s: unable to copy GUID to string.", function ); libcerror_error_free( &error ); goto on_error; } if( libfguid_identifier_free( &guid, &error ) != 1 ) { pylnk_error_raise( error, PyExc_IOError, "%s: unable to free GUID.", function ); libcerror_error_free( &error ); goto on_error; } /* Pass the string length to PyUnicode_DecodeUTF8 * otherwise it makes the end of string character is part * of the string */ string_object = PyUnicode_DecodeUTF8( guid_string, (Py_ssize_t) 36, errors ); return( string_object ); on_error: if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } return( NULL ); }
/* Reads the property set from the property set stream * Returns 1 if successful or -1 on error */ int libolecf_property_set_read( libolecf_property_set_t *property_set, libolecf_io_handle_t *io_handle, libolecf_item_t *property_set_stream, libcerror_error_t **error ) { olecf_property_set_header_t property_set_header; libolecf_internal_property_set_t *internal_property_set = NULL; libolecf_property_section_t *property_section = NULL; static char *function = "libolecf_property_set_read"; off64_t section_list_entry_offset = 0; ssize_t read_count = 0; uint32_t section_header_offset = 0; uint16_t number_of_sections = 0; uint16_t section_index = 0; int sections_entry = 0; #if defined( HAVE_DEBUG_OUTPUT ) libcstring_system_character_t guid_string[ 48 ]; libfguid_identifier_t *guid = NULL; int result = 0; #endif if( property_set == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid property set.", function ); return( -1 ); } internal_property_set = (libolecf_internal_property_set_t *) property_set; if( libolecf_stream_seek_offset( property_set_stream, 0, SEEK_SET, error ) == -1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_SEEK_FAILED, "%s: unable to seek property set header offset: 0.", function ); goto on_error; } read_count = libolecf_stream_read_buffer( property_set_stream, (uint8_t *) &property_set_header, sizeof( olecf_property_set_header_t ), error ); if( read_count != (ssize_t) sizeof( olecf_property_set_header_t ) ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read property set header.", function ); goto on_error; } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: property set header:\n", function ); libcnotify_print_data( (uint8_t *) &property_set_header, sizeof( olecf_property_set_header_t ), 0 ); } #endif if( ( property_set_header.byte_order[ 0 ] == 0xfe ) && ( property_set_header.byte_order[ 1 ] == 0xff ) ) { internal_property_set->byte_order = LIBOLECF_ENDIAN_LITTLE; } else if( ( property_set_header.byte_order[ 0 ] == 0xff ) && ( property_set_header.byte_order[ 1 ] == 0xfe ) ) { internal_property_set->byte_order = LIBOLECF_ENDIAN_BIG; } else { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE, "%s: unsupported byte order: 0x%02" PRIx8 " 0x%02" PRIx8 ".", function, property_set_header.byte_order[ 0 ], property_set_header.byte_order[ 1 ] ); goto on_error; } if( internal_property_set->byte_order == LIBOLECF_ENDIAN_LITTLE ) { byte_stream_copy_to_uint16_little_endian( property_set_header.format, internal_property_set->format ); byte_stream_copy_to_uint32_little_endian( property_set_header.system_version, internal_property_set->system_version ); byte_stream_copy_to_uint16_little_endian( property_set_header.number_of_sections, number_of_sections ); } else if( internal_property_set->byte_order == LIBOLECF_ENDIAN_BIG ) { byte_stream_copy_to_uint16_big_endian( property_set_header.format, internal_property_set->format ); byte_stream_copy_to_uint32_big_endian( property_set_header.system_version, internal_property_set->system_version ); byte_stream_copy_to_uint16_big_endian( property_set_header.number_of_sections, number_of_sections ); } if( memory_copy( internal_property_set->class_identifier, property_set_header.class_identifier, 16 ) == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_COPY_FAILED, "%s: unable to copy class identifier.", function ); goto on_error; } /* TODO make sure the class identifier is set in little endian */ #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: property set header byte order\t\t: 0x%02" PRIx8 " 0x%02" PRIx8 "\n", function, property_set_header.byte_order[ 0 ], property_set_header.byte_order[ 1 ] ); libcnotify_printf( "%s: property set header format\t\t\t: %" PRIu16 "\n", function, internal_property_set->format ); libcnotify_printf( "%s: property set header system version\t\t: 0x%08" PRIx32 "\n", function, internal_property_set->system_version ); if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, internal_property_set->class_identifier, 16, internal_property_set->byte_order, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: property set header class identifier\t: %" PRIs_LIBCSTRING_SYSTEM " (%s : %s)\n", function, guid_string, libfwps_format_class_identifier_get_identifier( internal_property_set->class_identifier ), libfwps_format_class_identifier_get_description( internal_property_set->class_identifier ) ); if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } libcnotify_printf( "%s: property set header number of sections\t: %" PRIu16 "\n", function, number_of_sections ); libcnotify_printf( "\n" ); } #endif section_list_entry_offset = sizeof( olecf_property_set_header_t ); for( section_index = 0; section_index < (int) number_of_sections; section_index++ ) { if( libolecf_property_section_initialize( &property_section, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create property section: %d.", function, section_index ); goto on_error; } if( libolecf_stream_seek_offset( property_set_stream, section_list_entry_offset, SEEK_SET, error ) == -1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_SEEK_FAILED, "%s: unable to seek property section list entry: %d offset: %" PRIi64 ".", function, section_index, section_list_entry_offset ); goto on_error; } if( libolecf_property_section_read_list_entry( (libolecf_internal_property_section_t *) property_section, property_set_stream, internal_property_set->byte_order, §ion_header_offset, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read property section list entry: %d.", function, section_index ); goto on_error; } if( libolecf_stream_get_offset( property_set_stream, §ion_list_entry_offset, error ) == -1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_SEEK_FAILED, "%s: unable to retrieve property section list entry offset.", function ); goto on_error; } if( libolecf_property_section_read( (libolecf_internal_property_section_t *) property_section, io_handle, property_set_stream, section_header_offset, internal_property_set->byte_order, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read property section: %d at offset: %" PRIu32 ".", function, section_index, section_header_offset ); goto on_error; } if( libcdata_array_append_entry( internal_property_set->sections, §ions_entry, (intptr_t *) property_section, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_APPEND_FAILED, "%s: unable to append property section: %d to sections array.", function, section_index ); goto on_error; } property_section = NULL; } return( 1 ); on_error: #if defined( HAVE_DEBUG_OUTPUT ) if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } #endif if( property_section != NULL ) { libolecf_property_section_free( &property_section, NULL ); } return( -1 ); }
/* Reads the known folder location * Returns the number of bytes read if successful or -1 on error */ int liblnk_known_folder_location_read( liblnk_known_folder_location_t *known_folder_location, liblnk_data_block_t *data_block, libcerror_error_t **error ) { lnk_data_block_known_folder_location_t *known_folder_location_data = NULL; static char *function = "liblnk_data_block_strings_read"; #if defined( HAVE_DEBUG_OUTPUT ) libcstring_system_character_t guid_string[ 48 ]; libfguid_identifier_t *guid = NULL; int result = 0; #endif if( known_folder_location == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid known folder location.", function ); return( -1 ); } if( data_block == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid data block.", function ); return( -1 ); } if( data_block->data == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_VALUE_MISSING, "%s: invalid data block - missing data.", function ); return( -1 ); } if( data_block->data_size < sizeof( lnk_data_block_known_folder_location_t ) ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_VALUE_OUT_OF_BOUNDS, "%s: invalid data block - data size too small.", function ); return( -1 ); } known_folder_location_data = (lnk_data_block_known_folder_location_t *) data_block->data; if( memory_copy( known_folder_location->folder_identifier, known_folder_location_data->folder_identifier, 16 ) == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_COPY_FAILED, "%s: unable to copy folder identifier.", function ); goto on_error; } byte_stream_copy_to_uint32_little_endian( known_folder_location_data->first_child_segment_offset, known_folder_location->first_child_segment_offset ); #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, known_folder_location->folder_identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: known folder identifier\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); libcnotify_printf( "%s: known folder name\t\t\t: %s\n", function, libfwsi_known_folder_identifier_get_name( known_folder_location->folder_identifier ) ); libcnotify_printf( "%s: first child segment offset\t\t: %" PRIu32 "\n", function, known_folder_location->first_child_segment_offset ); libcnotify_printf( "\n" ); if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } } #endif #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( data_block->data_size > sizeof( lnk_data_block_known_folder_location_t ) ) { libcnotify_printf( "%s: trailing data:\n", function ); libcnotify_print_data( &( data_block->data[ sizeof( lnk_data_block_known_folder_location_t ) ] ), data_block->data_size - sizeof( lnk_data_block_known_folder_location_t ), 0 ); } } #endif return( 1 ); on_error: #if defined( HAVE_DEBUG_OUTPUT ) if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } #endif return( -1 ); }
/* Reads a external key from the metadata entry * Returns 1 if successful or -1 on error */ int libbde_external_key_read( libbde_external_key_t *external_key, libbde_metadata_entry_t *metadata_entry, libcerror_error_t **error ) { libbde_key_t *key = NULL; libbde_metadata_entry_t *property_metadata_entry = NULL; uint8_t *value_data = NULL; static char *function = "libbde_external_key_read"; size_t value_data_size = 0; ssize_t read_count = 0; int property_metadata_entry_index = 0; #if defined( HAVE_DEBUG_OUTPUT ) libcstring_system_character_t filetime_string[ 32 ]; libcstring_system_character_t guid_string[ 48 ]; libfdatetime_filetime_t *filetime = NULL; libfguid_identifier_t *guid = NULL; int result = 0; #endif if( external_key == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid external key.", function ); return( -1 ); } if( metadata_entry == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid metadata entry.", function ); return( -1 ); } if( metadata_entry->value_type != LIBBDE_VALUE_TYPE_EXTERNAL_KEY ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE, "%s: invalid metadata entry - unsupported value type: 0x%04" PRIx16 ".", function, metadata_entry->value_type ); return( -1 ); } value_data = metadata_entry->value_data; value_data_size = metadata_entry->value_data_size; if( value_data_size < sizeof( bde_metadata_entry_external_key_header_t ) ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_VALUE_OUT_OF_BOUNDS, "%s: value data size value out of bounds.", function ); return( -1 ); } if( memory_copy( external_key->identifier, ( (bde_metadata_entry_external_key_header_t *) value_data )->identifier, 16 ) == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_COPY_FAILED, "%s: unable to copy volume identifier.", function ); goto on_error; } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, ( (bde_metadata_entry_external_key_header_t *) value_data )->identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: identifier\t\t\t\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } if( libfdatetime_filetime_initialize( &filetime, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create filetime.", function ); goto on_error; } if( libfdatetime_filetime_copy_from_byte_stream( filetime, ( (bde_metadata_entry_external_key_header_t *) value_data )->modification_time, 8, LIBFDATETIME_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_SET_FAILED, "%s: unable to copy filetime from byte stream.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfdatetime_filetime_copy_to_utf16_string( filetime, (uint16_t *) filetime_string, 32, LIBFDATETIME_STRING_FORMAT_TYPE_CTIME | LIBFDATETIME_STRING_FORMAT_FLAG_DATE_TIME_NANO_SECONDS, error ); #else result = libfdatetime_filetime_copy_to_utf8_string( filetime, (uint8_t *) filetime_string, 32, LIBFDATETIME_STRING_FORMAT_TYPE_CTIME | LIBFDATETIME_STRING_FORMAT_FLAG_DATE_TIME_NANO_SECONDS, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_SET_FAILED, "%s: unable to copy filetime to string.", function ); goto on_error; } libcnotify_printf( "%s: modification time\t\t\t\t: %" PRIs_LIBCSTRING_SYSTEM " UTC\n", function, filetime_string ); if( libfdatetime_filetime_free( &filetime, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free filetime.", function ); goto on_error; } libcnotify_printf( "\n" ); } #endif value_data += sizeof( bde_metadata_entry_external_key_header_t ); value_data_size -= sizeof( bde_metadata_entry_external_key_header_t ); while( value_data_size >= sizeof( bde_metadata_entry_v1_t ) ) { if( memory_compare( value_data, libbde_metadata_entry_empty, sizeof( bde_metadata_entry_v1_t ) ) == 0 ) { break; } if( libbde_metadata_entry_initialize( &property_metadata_entry, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create property metadata entry.", function ); goto on_error; } read_count = libbde_metadata_entry_read( property_metadata_entry, value_data, value_data_size, error ); if( read_count == -1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read property metadata entry.", function ); goto on_error; } value_data += read_count; value_data_size -= read_count; if( property_metadata_entry->value_type == LIBBDE_VALUE_TYPE_KEY ) { if( libbde_key_initialize( &key, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create key.", function ); goto on_error; } if( libbde_key_read( key, property_metadata_entry, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read key metadata entry.", function ); goto on_error; } if( external_key->key == NULL ) { external_key->key = key; key = NULL; } if( key != NULL ) { if( libbde_key_free( &key, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free key.", function ); goto on_error; } } } else if( property_metadata_entry->value_type == LIBBDE_VALUE_TYPE_UNICODE_STRING ) { #if defined( HAVE_DEBUG_OUTPUT ) if( libbde_metadata_entry_read_string( property_metadata_entry, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read string from property metadata entry.", function ); goto on_error; } #endif if( external_key->string_entry == NULL ) { external_key->string_entry = property_metadata_entry; } } if( libcdata_array_append_entry( external_key->entries_array, &property_metadata_entry_index, (intptr_t *) property_metadata_entry, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to append property metadata entry to entries array.", function ); goto on_error; } property_metadata_entry = NULL; } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( value_data_size > 0 ) { libcnotify_printf( "%s: trailing data:\n", function ); libcnotify_print_data( value_data, value_data_size, LIBCNOTIFY_PRINT_DATA_FLAG_GROUP_DATA ); } } #endif return( 1 ); on_error: #if defined( HAVE_DEBUG_OUTPUT ) if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } if( filetime != NULL ) { libfdatetime_filetime_free( &filetime, NULL ); } #endif if( key != NULL ) { libbde_key_free( &key, NULL ); } if( property_metadata_entry != NULL ) { libbde_metadata_entry_free( &property_metadata_entry, NULL ); } return( -1 ); }
/* Reads the manifest * Returns 1 if successful or -1 on error */ int libfwevt_manifest_read( libfwevt_manifest_t *manifest, const uint8_t *data, size_t data_size, libcerror_error_t **error ) { libfwevt_internal_manifest_t *internal_manifest = NULL; libfwevt_provider_t *provider = NULL; fwevt_template_manifest_t *wevt_manifest = NULL; fwevt_template_provider_entry_t *provider_entry = NULL; static char *function = "libfwevt_manifest_read"; size_t data_offset = 0; uint32_t number_of_providers = 0; uint32_t provider_data_offset = 0; uint32_t provider_index = 0; #if defined( HAVE_DEBUG_OUTPUT ) system_character_t guid_string[ 48 ]; libfguid_identifier_t *guid = NULL; uint32_t value_32bit = 0; int result = 0; #endif if( manifest == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid manifest.", function ); return( -1 ); } internal_manifest = (libfwevt_internal_manifest_t *) manifest; if( data == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid data.", function ); return( -1 ); } if( data_size > (size_t) SSIZE_MAX ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_VALUE_EXCEEDS_MAXIMUM, "%s: invalid data size value exceeds maximum.", function ); return( -1 ); } if( data_size < sizeof( fwevt_template_manifest_t ) ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_VALUE_TOO_SMALL, "%s: invalid data value too small.", function ); return( -1 ); } wevt_manifest = (fwevt_template_manifest_t *) data; #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: manifest data:\n", function ); libcnotify_print_data( (uint8_t *) wevt_manifest, sizeof( fwevt_template_manifest_t ), 0 ); } #endif byte_stream_copy_to_uint16_little_endian( wevt_manifest->major_version, internal_manifest->major_version ); byte_stream_copy_to_uint16_little_endian( wevt_manifest->minor_version, internal_manifest->minor_version ); byte_stream_copy_to_uint32_little_endian( wevt_manifest->number_of_providers, number_of_providers ); #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: signature\t\t\t\t\t: %c%c%c%c\n", function, wevt_manifest->signature[ 0 ], wevt_manifest->signature[ 1 ], wevt_manifest->signature[ 2 ], wevt_manifest->signature[ 3 ] ); byte_stream_copy_to_uint32_little_endian( wevt_manifest->size, value_32bit ); libcnotify_printf( "%s: size\t\t\t\t\t\t: %" PRIu32 "\n", function, value_32bit ); libcnotify_printf( "%s: major version\t\t\t\t\t: %" PRIu16 "\n", function, internal_manifest->major_version ); libcnotify_printf( "%s: minor version\t\t\t\t\t: %" PRIu16 "\n", function, internal_manifest->minor_version ); libcnotify_printf( "%s: number of providers\t\t\t\t: %" PRIu32 "\n", function, number_of_providers ); libcnotify_printf( "\n" ); } #endif if( memory_compare( wevt_manifest->signature, "CRIM", 4 ) != 0 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE, "%s: unsupported manifest signature.", function ); goto on_error; } data_offset = sizeof( fwevt_template_manifest_t ); if( libcdata_array_initialize( &( internal_manifest->providers_array ), number_of_providers, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create providers array.", function ); goto on_error; } for( provider_index = 0; provider_index < number_of_providers; provider_index++ ) { if( data_offset >= data_size ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_VALUE_OUT_OF_BOUNDS, "%s: invalid data offset value out of bounds.", function ); goto on_error; } provider_entry = (fwevt_template_provider_entry_t *) &( data[ data_offset ] ); if( ( data_offset + sizeof( fwevt_template_provider_entry_t ) ) >= data_size ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_VALUE_OUT_OF_BOUNDS, "%s: invalid data value too small.", function ); goto on_error; } byte_stream_copy_to_uint32_little_endian( provider_entry->data_offset, provider_data_offset ); #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, provider_entry->identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: provider entry: %02" PRIu32 " identifier\t\t\t: %" PRIs_SYSTEM "\n", function, provider_index, guid_string ); if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } libcnotify_printf( "%s: provider entry: %02" PRIu32 " data offset\t\t\t: 0x%08" PRIx32 "\n", function, provider_index, provider_data_offset ); } #endif data_offset += sizeof( fwevt_template_provider_entry_t ); if( libfwevt_provider_initialize( &provider, provider_entry->identifier, 16, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create provider: %" PRIu32 ".", function, provider_index ); goto on_error; } if( libfwevt_provider_read( provider, data, data_size, (size_t) provider_data_offset, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read provider: %d.", function, provider_index ); goto on_error; } if( libcdata_array_set_entry_by_index( internal_manifest->providers_array, (int) provider_index, (intptr_t *) provider, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_SET_FAILED, "%s: unable to set provider: %" PRIu32 ".", function, provider_index ); goto on_error; } provider = NULL; } /* TODO refactor to read on demand ? */ for( provider_index = 0; provider_index < number_of_providers; provider_index++ ) { if( libcdata_array_get_entry_by_index( internal_manifest->providers_array, provider_index, (intptr_t **) &provider, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve provider: %d.", function, provider_index ); provider = NULL; goto on_error; } if( libfwevt_provider_read_channels( provider, data, data_size, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read channels.", function ); provider = NULL; goto on_error; } if( libfwevt_provider_read_events( provider, data, data_size, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read events.", function ); provider = NULL; goto on_error; } if( libfwevt_provider_read_keywords( provider, data, data_size, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read keywords.", function ); provider = NULL; goto on_error; } if( libfwevt_provider_read_levels( provider, data, data_size, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read levels.", function ); provider = NULL; goto on_error; } if( libfwevt_provider_read_maps( provider, data, data_size, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read maps.", function ); provider = NULL; goto on_error; } if( libfwevt_provider_read_opcodes( provider, data, data_size, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read opcodes.", function ); provider = NULL; goto on_error; } if( libfwevt_provider_read_tasks( provider, data, data_size, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read tasks.", function ); provider = NULL; goto on_error; } if( libfwevt_provider_read_templates( provider, data, data_size, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read templates.", function ); provider = NULL; goto on_error; } } /* TODO end refactor */ #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( number_of_providers > 0 ) { libcnotify_printf( "\n" ); } } #endif return( 1 ); on_error: #if defined( HAVE_DEBUG_OUTPUT ) if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } #endif if( provider != NULL ) { libfwevt_provider_free( &provider, NULL ); } if( internal_manifest->providers_array != NULL ) { libcdata_array_free( &( internal_manifest->providers_array ), (int (*)(intptr_t **, libcerror_error_t **)) &libfwevt_provider_free, NULL ); } return( -1 ); }
/* Reads the record * Returns 1 if successful or -1 on error */ int libftxf_record_read( libftxf_record_t *record, const uint8_t *record_data, size_t record_data_size, libcerror_error_t **error ) { libftxf_internal_record_t *internal_record = NULL; static char *function = "libftxf_record_read"; size_t record_data_offset = 0; uint16_t record_type = 0; uint16_t name_offset = 0; uint16_t name_size = 0; #if defined( HAVE_DEBUG_OUTPUT ) libcstring_system_character_t date_time_string[ 32 ]; libcstring_system_character_t guid_string[ 48 ]; libcstring_system_character_t *value_string = NULL; libfdatetime_filetime_t *filetime = NULL; libfguid_identifier_t *guid = NULL; size_t value_string_size = 0; uint64_t value_64bit = 0; uint32_t value_32bit = 0; uint16_t value_16bit = 0; int result = 0; #endif if( record == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid record.", function ); return( -1 ); } internal_record = (libftxf_internal_record_t *) record; if( record_data == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid record data.", function ); return( -1 ); } if( record_data_size > (size_t) SSIZE_MAX ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_VALUE_EXCEEDS_MAXIMUM, "%s: invalid record data size value exceeds maximum.", function ); return( -1 ); } if( record_data_size < sizeof( ftxf_record_header_t ) ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_VALUE_TOO_SMALL, "%s: invalid record data value too small.", function ); return( -1 ); } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: record header data:\n", function ); libcnotify_print_data( record_data, sizeof( ftxf_record_header_t ), 0 ); } #endif byte_stream_copy_to_uint16_little_endian( ( (ftxf_record_header_t *) record_data )->record_type, record_type ); byte_stream_copy_to_uint32_little_endian( ( (ftxf_record_header_t *) record_data )->record_size, internal_record->size ); #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { byte_stream_copy_to_uint32_little_endian( ( (ftxf_record_header_t *) record_data )->unknown1, value_32bit ); libcnotify_printf( "%s: unknown1\t\t\t\t\t\t: 0x%08" PRIx32 "\n", function, value_32bit ); libcnotify_printf( "%s: record type\t\t\t\t\t: 0x%04" PRIx16 "\n", function, record_type ); byte_stream_copy_to_uint16_little_endian( ( (ftxf_record_header_t *) record_data )->unknown2, value_16bit ); libcnotify_printf( "%s: unknown2\t\t\t\t\t\t: 0x%04" PRIx16 "\n", function, value_16bit ); byte_stream_copy_to_uint64_little_endian( ( (ftxf_record_header_t *) record_data )->file_identifier, value_64bit ); libcnotify_printf( "%s: file identifier\t\t\t\t\t: 0x%08" PRIx64 "\n", function, value_64bit ); byte_stream_copy_to_uint64_little_endian( ( (ftxf_record_header_t *) record_data )->file_reference, value_64bit ); libcnotify_printf( "%s: file reference\t\t\t\t\t: MFT entry: %" PRIu64 ", sequence: %" PRIu64 "\n", function, value_64bit & 0xffffffffffffUL, value_64bit >> 48 ); byte_stream_copy_to_uint32_little_endian( ( (ftxf_record_header_t *) record_data )->unknown4, value_32bit ); libcnotify_printf( "%s: unknown4\t\t\t\t\t\t: 0x%08" PRIx32 "\n", function, value_32bit ); byte_stream_copy_to_uint32_little_endian( ( (ftxf_record_header_t *) record_data )->unknown5, value_32bit ); libcnotify_printf( "%s: unknown5\t\t\t\t\t\t: 0x%08" PRIx32 "\n", function, value_32bit ); if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, ( (ftxf_record_header_t *) record_data )->unknown6, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } libcnotify_printf( "%s: unknown6 guid\t\t\t\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); byte_stream_copy_to_uint64_little_endian( ( (ftxf_record_header_t *) record_data )->unknown7, value_64bit ); libcnotify_printf( "%s: unknown7\t\t\t\t\t\t: 0x%08" PRIx64 "\n", function, value_64bit ); if( libfdatetime_filetime_initialize( &filetime, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create filetime.", function ); goto on_error; } if( libfdatetime_filetime_copy_from_byte_stream( filetime, ( (ftxf_record_header_t *) record_data )->unknown8, 8, LIBFDATETIME_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_SET_FAILED, "%s: unable to copy filetime from byte stream.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfdatetime_filetime_copy_to_utf16_string( filetime, (uint16_t *) date_time_string, 32, LIBFDATETIME_STRING_FORMAT_TYPE_CTIME | LIBFDATETIME_STRING_FORMAT_FLAG_DATE_TIME_NANO_SECONDS, error ); #else result = libfdatetime_filetime_copy_to_utf8_string( filetime, (uint8_t *) date_time_string, 32, LIBFDATETIME_STRING_FORMAT_TYPE_CTIME | LIBFDATETIME_STRING_FORMAT_FLAG_DATE_TIME_NANO_SECONDS, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_SET_FAILED, "%s: unable to copy filetime to date time string.", function ); goto on_error; } libcnotify_printf( "%s: unknown8 filetime\t\t\t\t\t: %" PRIs_LIBCSTRING_SYSTEM " UTC\n", function, date_time_string ); if( libfdatetime_filetime_free( &filetime, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free filetime.", function ); goto on_error; } libcnotify_printf( "%s: record size\t\t\t\t\t: %" PRIu32 "\n", function, internal_record->size ); byte_stream_copy_to_uint32_little_endian( ( (ftxf_record_header_t *) record_data )->unknown9, value_32bit ); libcnotify_printf( "%s: unknown9\t\t\t\t\t\t: 0x%08" PRIx32 "\n", function, value_32bit ); byte_stream_copy_to_uint64_little_endian( ( (ftxf_record_header_t *) record_data )->unknown10, value_64bit ); libcnotify_printf( "%s: unknown10\t\t\t\t\t\t: 0x%08" PRIx64 "\n", function, value_64bit ); libcnotify_printf( "\n" ); }
/* Reads the volume values * Returns the number of bytes read, 0 if not able to read or -1 on error */ ssize_t libfwsi_volume_values_read( libfwsi_volume_values_t *volume_values, const uint8_t *shell_item_data, size_t shell_item_data_size, int ascii_codepage, libcerror_error_t **error ) { static char *function = "libfwsi_volume_values_read"; size_t shell_item_data_offset = 0; size_t string_size = 0; uint8_t class_type_indicator = 0; #if defined( HAVE_DEBUG_OUTPUT ) libcstring_system_character_t guid_string[ 48 ]; libcstring_system_character_t *value_string = NULL; libfguid_identifier_t *guid = NULL; size_t value_string_size = 0; uint16_t value_16bit = 0; int result = 0; #endif if( volume_values == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid volume values.", function ); return( -1 ); } if( shell_item_data == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid shell item data.", function ); return( -1 ); } if( shell_item_data_size > (size_t) SSIZE_MAX ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_VALUE_EXCEEDS_MAXIMUM, "%s: shell item data size exceeds maximum.", function ); return( -1 ); } /* Do not try to parse unsupported shell item data sizes */ if( shell_item_data_size < 20 ) { return( 0 ); } /* Do not try to parse unknown class type indicators */ if( ( shell_item_data[ 2 ] != 0x23 ) && ( shell_item_data[ 2 ] != 0x25 ) && ( shell_item_data[ 2 ] != 0x29 ) && ( shell_item_data[ 2 ] != 0x2a ) && ( shell_item_data[ 2 ] != 0x2e ) && ( shell_item_data[ 2 ] != 0x2f ) ) { return( 0 ); } class_type_indicator = shell_item_data[ 2 ]; volume_values->ascii_codepage = ascii_codepage; #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } } #endif if( class_type_indicator == 0x2e ) { #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: unknown1\t\t\t\t\t: 0x%02" PRIx8 "\n", function, shell_item_data[ 3 ] ); } #endif volume_values->has_name = 0; if( memory_copy( volume_values->identifier, &( shell_item_data[ 4 ] ), 16 ) == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_COPY_FAILED, "%s: unable to copy volume identifier.", function ); goto on_error; } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( libfguid_identifier_copy_from_byte_stream( guid, volume_values->identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_UPPER_CASE | LIBFGUID_STRING_FORMAT_FLAG_USE_SURROUNDING_BRACES, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_UPPER_CASE | LIBFGUID_STRING_FORMAT_FLAG_USE_SURROUNDING_BRACES, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: shell folder identifier\t\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); libcnotify_printf( "%s: shell folder name\t\t\t\t: %s\n", function, libfwsi_shell_folder_identifier_get_name( volume_values->identifier ) ); } #endif shell_item_data_offset = 20; } else { /* Do not try to parse unsupported shell item data sizes */ if( shell_item_data_size < 25 ) { return( 0 ); } volume_values->has_name = 1; if( memory_copy( volume_values->name, &( shell_item_data[ 3 ] ), 20 ) == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_COPY_FAILED, "%s: unable to copy volume name.", function ); goto on_error; } for( string_size = 0; string_size < 20; string_size++ ) { if( volume_values->name[ string_size ] == 0 ) { break; } } volume_values->name_size = string_size; #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libuna_utf16_string_size_from_byte_stream( volume_values->name, volume_values->name_size, volume_values->ascii_codepage, &value_string_size, error ); #else result = libuna_utf8_string_size_from_byte_stream( volume_values->name, volume_values->name_size, volume_values->ascii_codepage, &value_string_size, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to determine size of volume name string.", function ); goto on_error; } if( value_string_size > (size_t) ( SSIZE_MAX / sizeof( libcstring_system_character_t ) ) ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_VALUE_EXCEEDS_MAXIMUM, "%s: invalid volume name string size value exceeds maximum.", function ); goto on_error; } value_string = libcstring_system_string_allocate( value_string_size ); if( value_string == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_INSUFFICIENT, "%s: unable to create volume name string.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libuna_utf16_string_copy_from_byte_stream( (libuna_utf16_character_t *) value_string, value_string_size, volume_values->name, volume_values->name_size, volume_values->ascii_codepage, error ); #else result = libuna_utf8_string_copy_from_byte_stream( (libuna_utf8_character_t *) value_string, value_string_size, volume_values->name, volume_values->name_size, volume_values->ascii_codepage, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_SET_FAILED, "%s: unable to set volume name string.", function ); goto on_error; } libcnotify_printf( "%s: volume name\t\t\t\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, value_string ); memory_free( value_string ); value_string = NULL; } #endif #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { byte_stream_copy_to_uint16_little_endian( &( shell_item_data[ 23 ] ), value_16bit ); libcnotify_printf( "%s: unknown2\t\t\t\t\t: 0x%04" PRIx16 "\n", function, value_16bit ); } #endif shell_item_data_offset = 25; if( shell_item_data_offset <= ( shell_item_data_size - 16 ) ) { if( memory_copy( volume_values->shell_folder_identifier, &( shell_item_data[ shell_item_data_offset ] ), 16 ) == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_COPY_FAILED, "%s: unable to copy shell folder identifier.", function ); goto on_error; } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( libfguid_identifier_copy_from_byte_stream( guid, volume_values->shell_folder_identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_UPPER_CASE | LIBFGUID_STRING_FORMAT_FLAG_USE_SURROUNDING_BRACES, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_UPPER_CASE | LIBFGUID_STRING_FORMAT_FLAG_USE_SURROUNDING_BRACES, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: shell folder identifier\t\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); libcnotify_printf( "%s: shell folder name\t\t\t\t: %s\n", function, libfwsi_shell_folder_identifier_get_name( &( shell_item_data[ shell_item_data_offset ] ) ) ); } #endif shell_item_data_offset += 16; } } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } libcnotify_printf( "\n" ); } #endif return( (ssize_t) shell_item_data_offset ); on_error: #if defined( HAVE_DEBUG_OUTPUT ) if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } if( value_string != NULL ) { memory_free( value_string ); } #endif return( -1 ); }
/* Prints the store information to a stream * Returns 1 if successful or -1 on error */ int info_handle_store_fprint( info_handle_t *info_handle, int store_index, libvshadow_store_t *store, libcerror_error_t **error ) { uint8_t guid_buffer[ 16 ]; libcstring_system_character_t filetime_string[ 32 ]; libcstring_system_character_t guid_string[ 48 ]; libfdatetime_filetime_t *filetime = NULL; libfguid_identifier_t *guid = NULL; libvshadow_block_t *block = NULL; static char *function = "info_handle_store_fprint"; size64_t volume_size = 0; uint64_t value_64bit = 0; uint32_t attribute_flags = 0; int block_index = 0; int number_of_blocks = 0; int result = 0; if( info_handle == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid info handle.", function ); return( -1 ); } fprintf( info_handle->notify_stream, "Store: %d\n", store_index + 1 ); if( libfdatetime_filetime_initialize( &filetime, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create filetime.", function ); goto on_error; } if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libvshadow_store_get_identifier( store, guid_buffer, 16, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve store: %d identifier.", function, store_index ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, guid_buffer, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tIdentifier\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", guid_string ); if( libvshadow_store_get_copy_set_identifier( store, guid_buffer, 16, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve store: %d shadow copy set identifier.", function, store_index ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, guid_buffer, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tShadow copy set ID\t: %" PRIs_LIBCSTRING_SYSTEM "\n", guid_string ); if( libvshadow_store_get_creation_time( store, &value_64bit, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve store: %d creation time.", function, store_index ); goto on_error; } if( libfdatetime_filetime_copy_from_64bit( filetime, value_64bit, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_CONVERSION, LIBCERROR_CONVERSION_ERROR_GENERIC, "%s: unable to create filetime.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfdatetime_filetime_copy_to_utf16_string( filetime, (uint16_t *) filetime_string, 32, LIBFDATETIME_STRING_FORMAT_TYPE_CTIME | LIBFDATETIME_STRING_FORMAT_FLAG_DATE_TIME_NANO_SECONDS, error ); #else result = libfdatetime_filetime_copy_to_utf8_string( filetime, (uint8_t *) filetime_string, 32, LIBFDATETIME_STRING_FORMAT_TYPE_CTIME | LIBFDATETIME_STRING_FORMAT_FLAG_DATE_TIME_NANO_SECONDS, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy filetime to string.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tCreation time\t\t: %" PRIs_LIBCSTRING_SYSTEM " UTC\n", filetime_string ); if( libvshadow_store_get_copy_identifier( store, guid_buffer, 16, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve store: %d shadow copy identifier.", function, store_index ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, guid_buffer, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tShadow copy ID\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", guid_string ); if( libvshadow_store_get_volume_size( store, &volume_size, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve store: %d volume size.", function, store_index ); goto on_error; } fprintf( info_handle->notify_stream, "\tVolume size\t\t: %" PRIu64 " bytes\n", volume_size ); if( libvshadow_store_get_attribute_flags( store, &attribute_flags, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve store: %d attribute flags.", function, store_index ); goto on_error; } /* TODO print a description of the flags */ fprintf( info_handle->notify_stream, "\tAttribute flags\t\t: 0x%08" PRIx32 "\n", attribute_flags ); if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } if( libfdatetime_filetime_free( &filetime, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free filetime.", function ); goto on_error; } if( info_handle->show_allocation_information != 0 ) { if( libvshadow_store_get_number_of_blocks( store, &number_of_blocks, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve store: %d number of blocks.", function, store_index ); goto on_error; } fprintf( info_handle->notify_stream, "\tNumber of blocks\t: %d\n", number_of_blocks ); for( block_index = 0; block_index < number_of_blocks; block_index++ ) { if( libvshadow_store_get_block_by_index( store, block_index, &block, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve block: %d.", function, block_index ); goto on_error; } if( info_handle_block_fprint( info_handle, block_index, block, error ) != 1 ) { goto on_error; } if( libvshadow_block_free( &block, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free block: %d.", function, block_index ); goto on_error; } } } fprintf( info_handle->notify_stream, "\n" ); return( 1 ); on_error: if( block != NULL ) { libvshadow_block_free( &block, NULL ); } if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } if( filetime != NULL ) { libfdatetime_filetime_free( &filetime, NULL ); } return( -1 ); }
/* Reads the volume header * Returns 1 if successful or -1 on error */ int libbde_io_handle_read_volume_header( libbde_io_handle_t *io_handle, libbfio_handle_t *file_io_handle, off64_t file_offset, libcerror_error_t **error ) { uint8_t *volume_header_data = NULL; static char *function = "libbde_io_handle_read_volume_header"; size_t read_size = 512; ssize_t read_count = 0; uint64_t total_number_of_sectors = 0; #if defined( HAVE_DEBUG_OUTPUT ) libcstring_system_character_t guid_string[ 48 ]; libfguid_identifier_t *guid = NULL; uint64_t value_64bit = 0; uint32_t value_32bit = 0; uint16_t value_16bit = 0; int result = 0; #endif if( io_handle == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid IO handle.", function ); goto on_error; } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: reading volume header at offset: %" PRIi64 " (0x%08" PRIx64 ")\n", function, file_offset, file_offset ); } #endif if( libbfio_handle_seek_offset( file_io_handle, file_offset, SEEK_SET, error ) == -1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_SEEK_FAILED, "%s: unable to seek volume header offset: %" PRIi64 ".", function, file_offset ); goto on_error; } volume_header_data = (uint8_t *) memory_allocate( sizeof( uint8_t ) * read_size ); if( volume_header_data == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_INSUFFICIENT, "%s: unable to create volume header data.", function ); goto on_error; } read_count = libbfio_handle_read_buffer( file_io_handle, volume_header_data, read_size, error ); if( read_count != (ssize_t) read_size ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read volume header data.", function ); goto on_error; } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: volume header data:\n", function ); libcnotify_print_data( volume_header_data, read_size, 0 ); } #endif if( memory_compare( volume_header_data, bde_boot_entry_point_vista, 3 ) == 0 ) { io_handle->version = LIBBDE_VERSION_WINDOWS_VISTA; } else if( memory_compare( volume_header_data, bde_boot_entry_point_win7, 3 ) == 0 ) { if( memory_compare( ( (bde_volume_header_windows_7_t *) volume_header_data )->identifier, bde_identifier, 16 ) == 0 ) { io_handle->version = LIBBDE_VERSION_WINDOWS_7; } else if( memory_compare( ( (bde_volume_header_to_go_t *) volume_header_data )->identifier, bde_identifier, 16 ) == 0 ) { io_handle->version = LIBBDE_VERSION_TO_GO; } else { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE, "%s: unsupported identifier.", function ); goto on_error; } } else { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE, "%s: unsupported volume boot entry point.", function ); goto on_error; } if( ( io_handle->version == LIBBDE_VERSION_WINDOWS_VISTA ) || ( io_handle->version == LIBBDE_VERSION_WINDOWS_7 ) ) { if( memory_compare( &( volume_header_data[ 3 ] ), bde_signature, 8 ) != 0 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE, "%s: invalid volume signature.", function ); goto on_error; } } byte_stream_copy_to_uint16_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->bytes_per_sector, io_handle->bytes_per_sector ); io_handle->sectors_per_cluster_block = ( (bde_volume_header_windows_vista_t *) volume_header_data )->sectors_per_cluster_block; byte_stream_copy_to_uint16_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->total_number_of_sectors_16bit, total_number_of_sectors ); if( total_number_of_sectors == 0 ) { byte_stream_copy_to_uint32_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->total_number_of_sectors_32bit, total_number_of_sectors ); } if( io_handle->version == LIBBDE_VERSION_WINDOWS_VISTA ) { byte_stream_copy_to_uint64_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->first_metadata_cluster_block_number, io_handle->first_metadata_offset ); if( total_number_of_sectors == 0 ) { byte_stream_copy_to_uint64_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->total_number_of_sectors_64bit, total_number_of_sectors ); } } else if( io_handle->version == LIBBDE_VERSION_WINDOWS_7 ) { byte_stream_copy_to_uint64_little_endian( ( (bde_volume_header_windows_7_t *) volume_header_data )->first_metadata_offset, io_handle->first_metadata_offset ); byte_stream_copy_to_uint64_little_endian( ( (bde_volume_header_windows_7_t *) volume_header_data )->second_metadata_offset, io_handle->second_metadata_offset ); byte_stream_copy_to_uint64_little_endian( ( (bde_volume_header_windows_7_t *) volume_header_data )->third_metadata_offset, io_handle->third_metadata_offset ); } else if( io_handle->version == LIBBDE_VERSION_TO_GO ) { byte_stream_copy_to_uint64_little_endian( ( (bde_volume_header_to_go_t *) volume_header_data )->first_metadata_offset, io_handle->first_metadata_offset ); byte_stream_copy_to_uint64_little_endian( ( (bde_volume_header_to_go_t *) volume_header_data )->second_metadata_offset, io_handle->second_metadata_offset ); byte_stream_copy_to_uint64_little_endian( ( (bde_volume_header_to_go_t *) volume_header_data )->third_metadata_offset, io_handle->third_metadata_offset ); } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: boot entry point:\n", function ); libcnotify_print_data( volume_header_data, 3, 0 ); libcnotify_printf( "%s: signature\t\t\t\t: %c%c%c%c%c%c%c%c\n", function, volume_header_data[ 3 ], volume_header_data[ 4 ], volume_header_data[ 5 ], volume_header_data[ 6 ], volume_header_data[ 7 ], volume_header_data[ 8 ], volume_header_data[ 9 ], volume_header_data[ 10 ] ); libcnotify_printf( "%s: bytes per sector\t\t\t: %" PRIu16 "\n", function, io_handle->bytes_per_sector ); libcnotify_printf( "%s: sectors per cluster block\t\t: %" PRIu8 "\n", function, io_handle->sectors_per_cluster_block ); libcnotify_printf( "%s: unknown1\n", function ); libcnotify_print_data( ( (bde_volume_header_windows_vista_t *) volume_header_data )->unknown1, 5, 0 ); byte_stream_copy_to_uint16_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->total_number_of_sectors_16bit, value_16bit ); libcnotify_printf( "%s: total number of sectors (16-bit)\t: %" PRIu16 "\n", function, value_16bit ); libcnotify_printf( "%s: media descriptor\t\t\t: 0x%02" PRIx8 "\n", function, ( (bde_volume_header_windows_vista_t *) volume_header_data )->media_descriptor ); byte_stream_copy_to_uint16_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->unknown2, value_16bit ); libcnotify_printf( "%s: unknown2\t\t\t\t: %" PRIu16 "\n", function, value_16bit ); byte_stream_copy_to_uint16_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->sectors_per_track, value_16bit ); libcnotify_printf( "%s: sectors per track\t\t\t: %" PRIu16 "\n", function, value_16bit ); byte_stream_copy_to_uint16_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->number_of_heads, value_16bit ); libcnotify_printf( "%s: number of heads\t\t\t: %" PRIu16 "\n", function, value_16bit ); byte_stream_copy_to_uint32_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->number_of_hidden_sectors, value_32bit ); libcnotify_printf( "%s: number of hidden sectors\t\t: %" PRIu32 "\n", function, value_32bit ); byte_stream_copy_to_uint32_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->total_number_of_sectors_32bit, value_32bit ); libcnotify_printf( "%s: total number of sectors (32-bit)\t: %" PRIu32 "\n", function, value_32bit ); if( io_handle->version == LIBBDE_VERSION_WINDOWS_VISTA ) { byte_stream_copy_to_uint32_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->unknown4, value_32bit ); libcnotify_printf( "%s: unknown4\t\t\t\t: 0x%08" PRIx32 " (%" PRIu32 ")\n", function, value_32bit, value_32bit ); byte_stream_copy_to_uint32_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->total_number_of_sectors_64bit, value_64bit ); libcnotify_printf( "%s: total number of sectors (64-bit)\t: %" PRIu64 "\n", function, value_64bit ); byte_stream_copy_to_uint64_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->mft_cluster_block_number, value_64bit ); libcnotify_printf( "%s: MFT cluster block number\t\t: %" PRIu64 "\n", function, value_64bit ); libcnotify_printf( "%s: first metadata cluster block\t: 0x%08" PRIx64 "\n", function, io_handle->first_metadata_offset ); byte_stream_copy_to_uint32_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->mft_entry_size, value_32bit ); libcnotify_printf( "%s: MFT entry size\t\t\t: %" PRIu32 "\n", function, value_32bit ); byte_stream_copy_to_uint32_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->index_entry_size, value_32bit ); libcnotify_printf( "%s: index entry size\t\t: %" PRIu32 "\n", function, value_32bit ); byte_stream_copy_to_uint64_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->volume_serial_number, value_64bit ); libcnotify_printf( "%s: volume serial number\t\t: 0x%08" PRIx64 "\n", function, value_64bit ); byte_stream_copy_to_uint32_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->checksum, value_32bit ); libcnotify_printf( "%s: checksum\t\t\t: 0x%08" PRIx32 "\n", function, value_32bit ); libcnotify_printf( "%s: bootcode\n", function ); libcnotify_print_data( ( (bde_volume_header_windows_vista_t *) volume_header_data )->bootcode, 426, 0 ); } else if( ( io_handle->version == LIBBDE_VERSION_WINDOWS_7 ) || ( io_handle->version == LIBBDE_VERSION_TO_GO ) ) { libcnotify_printf( "%s: unknown4:\n", function ); libcnotify_print_data( ( (bde_volume_header_windows_7_t *) volume_header_data )->unknown4, 31, 0 ); byte_stream_copy_to_uint32_little_endian( ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_serial_number, value_64bit ); libcnotify_printf( "%s: volume serial number\t\t: 0x%08" PRIx32 "\n", function, value_32bit ); libcnotify_printf( "%s: volume label\t\t\t: %c%c%c%c%c%c%c%c%c%c%c\n", function, ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_label[ 0 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_label[ 1 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_label[ 2 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_label[ 3 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_label[ 4 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_label[ 5 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_label[ 6 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_label[ 7 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_label[ 8 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_label[ 9 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->volume_label[ 10 ] ); libcnotify_printf( "%s: file system signature\t\t: %c%c%c%c%c%c%c%c\n", function, ( (bde_volume_header_windows_7_t *) volume_header_data )->file_system_signature[ 0 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->file_system_signature[ 1 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->file_system_signature[ 2 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->file_system_signature[ 3 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->file_system_signature[ 4 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->file_system_signature[ 5 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->file_system_signature[ 6 ], ( (bde_volume_header_windows_7_t *) volume_header_data )->file_system_signature[ 7 ] ); } if( io_handle->version == LIBBDE_VERSION_WINDOWS_7 ) { libcnotify_printf( "%s: bootcode\n", function ); libcnotify_print_data( ( (bde_volume_header_windows_7_t *) volume_header_data )->bootcode, 47, 0 ); if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, ( (bde_volume_header_windows_7_t *) volume_header_data )->identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: identifier\t\t\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } } else if( io_handle->version == LIBBDE_VERSION_TO_GO ) { libcnotify_printf( "%s: bootcode\n", function ); libcnotify_print_data( ( (bde_volume_header_to_go_t *) volume_header_data )->bootcode, 335, 0 ); if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, ( (bde_volume_header_to_go_t *) volume_header_data )->identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: identifier\t\t\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } } if( ( io_handle->version == LIBBDE_VERSION_WINDOWS_7 ) || ( io_handle->version == LIBBDE_VERSION_TO_GO ) ) { libcnotify_printf( "%s: first metadata offset\t\t: 0x%08" PRIx64 "\n", function, io_handle->first_metadata_offset ); libcnotify_printf( "%s: second metadata offset\t\t: 0x%08" PRIx64 "\n", function, io_handle->second_metadata_offset ); libcnotify_printf( "%s: third metadata offset\t\t: 0x%08" PRIx64 "\n", function, io_handle->third_metadata_offset ); } if( io_handle->version == LIBBDE_VERSION_WINDOWS_7 ) { libcnotify_printf( "%s: unknown5:\n", function ); libcnotify_print_data( ( (bde_volume_header_windows_7_t *) volume_header_data )->unknown5, 310, 0 ); } else if( io_handle->version == LIBBDE_VERSION_TO_GO ) { libcnotify_printf( "%s: unknown5:\n", function ); libcnotify_print_data( ( (bde_volume_header_to_go_t *) volume_header_data )->unknown5, 46, 0 ); } byte_stream_copy_to_uint16_little_endian( ( (bde_volume_header_windows_vista_t *) volume_header_data )->sector_signature, value_16bit ); libcnotify_printf( "%s: sector signature\t\t\t: 0x%04" PRIx16 "\n", function, value_16bit ); libcnotify_printf( "\n" ); } #endif if( total_number_of_sectors != 0 ) { io_handle->volume_size = total_number_of_sectors; io_handle->volume_size *= io_handle->bytes_per_sector; } if( io_handle->version == LIBBDE_VERSION_WINDOWS_VISTA ) { io_handle->first_metadata_offset *= io_handle->sectors_per_cluster_block; io_handle->first_metadata_offset *= io_handle->bytes_per_sector; io_handle->metadata_size = 16384; } else if( ( io_handle->version == LIBBDE_VERSION_WINDOWS_7 ) || ( io_handle->version == LIBBDE_VERSION_TO_GO ) ) { io_handle->metadata_size = 65536; } memory_free( volume_header_data ); volume_header_data = NULL; return( 1 ); on_error: #if defined( HAVE_DEBUG_OUTPUT ) if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } #endif if( volume_header_data != NULL ) { memory_free( volume_header_data ); } return( -1 ); }
/* Prints the file information to a stream * Returns 1 if successful or -1 on error */ int info_handle_file_fprint( info_handle_t *info_handle, libcerror_error_t **error ) { uint8_t guid_data[ 16 ]; libcstring_system_character_t guid_string[ 48 ]; libfguid_identifier_t *guid = NULL; libcstring_system_character_t *value_string = NULL; static char *function = "info_handle_file_fprint"; size_t value_string_size = 0; size64_t media_size = 0; uint32_t disk_type = 0; uint16_t major_version = 0; uint16_t minor_version = 0; int result = 0; if( info_handle == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid info handle.", function ); return( -1 ); } fprintf( info_handle->notify_stream, "Virtual Hard Disk (VHD) image information:\n" ); if( libvhdi_file_get_format_version( info_handle->input_file, &major_version, &minor_version, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve format version.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tFormat:\t\t\t%" PRIu16 ".%" PRIu16 "\n", major_version, minor_version ); if( libvhdi_file_get_disk_type( info_handle->input_file, &disk_type, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve disk type.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tDisk type:\t\t" ); switch( disk_type ) { case LIBVHDI_DISK_TYPE_FIXED: fprintf( info_handle->notify_stream, "Fixed" ); break; case LIBVHDI_DISK_TYPE_DYNAMIC: fprintf( info_handle->notify_stream, "Dynamic" ); break; case LIBVHDI_DISK_TYPE_DIFFERENTIAL: fprintf( info_handle->notify_stream, "Differential" ); break; default: fprintf( info_handle->notify_stream, "Unknown" ); break; } fprintf( info_handle->notify_stream, "\n" ); if( libvhdi_file_get_media_size( info_handle->input_file, &media_size, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve media size.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tMedia size:\t\t%" PRIu64 " bytes\n", media_size ); if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libvhdi_file_get_identifier( info_handle->input_file, guid_data, 16, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve identifier.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, guid_data, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tIdentifier:\t\t%" PRIs_LIBCSTRING_SYSTEM "\n", guid_string ); result = libvhdi_file_get_parent_identifier( info_handle->input_file, guid_data, 16, error ); if( result == -1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve parent identifier.", function ); goto on_error; } else if( result != 0 ) { if( libfguid_identifier_copy_from_byte_stream( guid, guid_data, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tParent identifier:\t%" PRIs_LIBCSTRING_SYSTEM "\n", guid_string ); } if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libvhdi_file_get_utf16_parent_filename_size( info_handle->input_file, &value_string_size, error ); #else result = libvhdi_file_get_utf8_parent_filename_size( info_handle->input_file, &value_string_size, error ); #endif if( result == -1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve parent filename string size.", function ); goto on_error; } else if( result != 0 ) { if( ( value_string_size > (size_t) SSIZE_MAX ) || ( ( sizeof( libcstring_system_character_t ) * value_string_size ) > (size_t) SSIZE_MAX ) ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_VALUE_EXCEEDS_MAXIMUM, "%s: invalid parent filename size value exceeds maximum.", function ); goto on_error; } value_string = libcstring_system_string_allocate( value_string_size ); if( value_string == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_INSUFFICIENT, "%s: unable to create parent filename string.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libvhdi_file_get_utf16_parent_filename( info_handle->input_file, (uint16_t *) value_string, value_string_size, error ); #else result = libvhdi_file_get_utf8_parent_filename( info_handle->input_file, (uint8_t *) value_string, value_string_size, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve parent filename.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tParent filename:\t%s\n", value_string ); memory_free( value_string ); value_string = NULL; } /* TODO add more info */ fprintf( info_handle->notify_stream, "\n" ); return( 1 ); on_error: if( value_string != NULL ) { memory_free( value_string ); } if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } return( -1 ); }
/* Reads distributed link tracker properties * Returns the number of bytes read if successful or -1 on error */ int liblnk_distributed_link_tracker_properties_read( liblnk_distributed_link_tracker_properties_t *distributed_link_tracker_properties, liblnk_data_block_t *data_block, liblnk_io_handle_t *io_handle, libcerror_error_t **error ) { lnk_data_block_distributed_link_tracker_properties_t *distributed_link_tracker_properties_data = NULL; static char *function = "liblnk_distributed_link_tracker_properties_read"; uint32_t data_size = 0; uint32_t data_version = 0; #if defined( HAVE_DEBUG_OUTPUT ) libcstring_system_character_t guid_string[ 48 ]; libcstring_system_character_t *value_string = NULL; libfguid_identifier_t *guid = NULL; size_t value_string_size = 0; int result = 0; #endif if( distributed_link_tracker_properties == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid distributed link tracker properties.", function ); return( -1 ); } if( data_block == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid data block.", function ); return( -1 ); } if( data_block->data == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_VALUE_MISSING, "%s: invalid data block - missing data.", function ); return( -1 ); } if( data_block->data_size < sizeof( lnk_data_block_distributed_link_tracker_properties_t ) ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_VALUE_OUT_OF_BOUNDS, "%s: invalid data block - data size too small.", function ); return( -1 ); } distributed_link_tracker_properties_data = (lnk_data_block_distributed_link_tracker_properties_t *) data_block->data; if( io_handle == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid IO handle.", function ); return( -1 ); } byte_stream_copy_to_uint32_little_endian( distributed_link_tracker_properties_data->data_size, data_size ); byte_stream_copy_to_uint32_little_endian( distributed_link_tracker_properties_data->data_version, data_version ); if( data_version != 0 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE, "%s: unsupported data version: %" PRIu32 ".", function, data_version ); goto on_error; } /* TODO check if data size matches data block size */ if( data_size < 88 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE, "%s: unsupported data size: %" PRIu32 ".", function, data_size ); goto on_error; } if( memory_copy( distributed_link_tracker_properties->machine_identifier_string, distributed_link_tracker_properties_data->machine_identifier_string, 16 ) == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_COPY_FAILED, "%s: unable to copy machine identifier string.", function ); goto on_error; } if( memory_copy( distributed_link_tracker_properties->droid_volume_identifier, distributed_link_tracker_properties_data->droid_volume_identifier, 16 ) == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_COPY_FAILED, "%s: unable to copy droid volume identifier.", function ); goto on_error; } if( memory_copy( distributed_link_tracker_properties->droid_file_identifier, distributed_link_tracker_properties_data->droid_file_identifier, 16 ) == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_COPY_FAILED, "%s: unable to copy droid file identifier.", function ); goto on_error; } if( memory_copy( distributed_link_tracker_properties->birth_droid_volume_identifier, distributed_link_tracker_properties_data->birth_droid_volume_identifier, 16 ) == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_COPY_FAILED, "%s: unable to copy birth droid volume identifier.", function ); goto on_error; } if( memory_copy( distributed_link_tracker_properties->birth_droid_file_identifier, distributed_link_tracker_properties_data->birth_droid_file_identifier, 16 ) == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_COPY_FAILED, "%s: unable to copy birth droid file identifier.", function ); goto on_error; } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: data size\t\t\t: %" PRIu32 "\n", function, data_size ); libcnotify_printf( "%s: data version\t\t\t: %" PRIu32 "\n", function, data_version ); libcnotify_printf( "%s: machine identifier string data:\n", function ); libcnotify_print_data( distributed_link_tracker_properties_data->machine_identifier_string, 16, 0 ); #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libuna_utf16_string_size_from_byte_stream( distributed_link_tracker_properties_data->machine_identifier_string, 16, io_handle->ascii_codepage, &value_string_size, error ); #else result = libuna_utf8_string_size_from_byte_stream( distributed_link_tracker_properties_data->machine_identifier_string, 16, io_handle->ascii_codepage, &value_string_size, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to determine size of machine identifier string.", function ); goto on_error; } if( ( value_string_size > (size_t) SSIZE_MAX ) || ( ( sizeof( libcstring_system_character_t ) * value_string_size ) > (size_t) SSIZE_MAX ) ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_VALUE_EXCEEDS_MAXIMUM, "%s: invalid machine identifier string size value exceeds maximum.", function ); goto on_error; } value_string = libcstring_system_string_allocate( value_string_size ); if( value_string == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_MEMORY, LIBCERROR_MEMORY_ERROR_INSUFFICIENT, "%s: unable to create machine identifier string.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libuna_utf16_string_copy_from_byte_stream( (libuna_utf16_character_t *) value_string, value_string_size, distributed_link_tracker_properties_data->machine_identifier_string, 16, io_handle->ascii_codepage, error ); #else result = libuna_utf8_string_copy_from_byte_stream( (libuna_utf8_character_t *) value_string, value_string_size, distributed_link_tracker_properties_data->machine_identifier_string, 16, io_handle->ascii_codepage, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_SET_FAILED, "%s: unable to set machine identifier string.", function ); goto on_error; } libcnotify_printf( "%s: machine identifier string\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, value_string ); memory_free( value_string ); value_string = NULL; if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, distributed_link_tracker_properties->droid_volume_identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: droid volume identifier\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); if( libfguid_identifier_copy_from_byte_stream( guid, distributed_link_tracker_properties->droid_file_identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: droid file identifier\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); if( libfguid_identifier_copy_from_byte_stream( guid, distributed_link_tracker_properties->birth_droid_volume_identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: birth droid volume identifier\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); if( libfguid_identifier_copy_from_byte_stream( guid, distributed_link_tracker_properties->birth_droid_file_identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: birth droid file identifier\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); libcnotify_printf( "\n" ); if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } } #endif #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( data_block->data_size > sizeof( lnk_data_block_distributed_link_tracker_properties_t ) ) { libcnotify_printf( "%s: trailing data:\n", function ); libcnotify_print_data( &( data_block->data[ sizeof( lnk_data_block_distributed_link_tracker_properties_t ) ] ), data_block->data_size - sizeof( lnk_data_block_distributed_link_tracker_properties_t ), 0 ); } } #endif return( 1 ); on_error: #if defined( HAVE_DEBUG_OUTPUT ) if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } if( value_string != NULL ) { memory_free( value_string ); } #endif return( -1 ); }
/* Reads the store block * Returns 1 if successful or -1 on error */ int libvshadow_store_block_read( libvshadow_store_block_t *store_block, libbfio_handle_t *file_io_handle, off64_t file_offset, libcerror_error_t **error ) { static char *function = "libvshadow_store_block_read"; ssize_t read_count = 0; #if defined( HAVE_DEBUG_OUTPUT ) libcstring_system_character_t guid_string[ 48 ]; libfguid_identifier_t *guid = NULL; uint64_t value_64bit = 0; int result = 0; #endif if( store_block == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid store block.", function ); return( -1 ); } if( store_block->data == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_VALUE_MISSING, "%s: invalid store block - missing data.", function ); return( -1 ); } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: reading store block at offset: %" PRIi64 " (0x%08" PRIx64 ")\n", function, file_offset, file_offset ); } #endif if( libbfio_handle_seek_offset( file_io_handle, file_offset, SEEK_SET, error ) == -1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_SEEK_FAILED, "%s: unable to seek store block offset: %" PRIi64 ".", function, file_offset ); return( -1 ); } read_count = libbfio_handle_read_buffer( file_io_handle, store_block->data, store_block->data_size, error ); if( read_count != (ssize_t) store_block->data_size ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_IO, LIBCERROR_IO_ERROR_READ_FAILED, "%s: unable to read block data.", function ); return( -1 ); } #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { libcnotify_printf( "%s: store block header:\n", function ); libcnotify_print_data( store_block->data, sizeof( vshadow_store_block_header_t ), LIBCNOTIFY_PRINT_DATA_FLAG_GROUP_DATA ); } #endif if( memory_compare( ( (vshadow_store_block_header_t *) store_block->data )->identifier, vshadow_vss_identifier, 8 ) != 0 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE, "%s: invalid store block list header identifier.", function ); return( -1 ); } byte_stream_copy_to_uint32_little_endian( ( (vshadow_store_block_header_t *) store_block->data )->version, store_block->version ); byte_stream_copy_to_uint32_little_endian( ( (vshadow_store_block_header_t *) store_block->data )->record_type, store_block->record_type ); byte_stream_copy_to_uint64_little_endian( ( (vshadow_store_block_header_t *) store_block->data )->relative_offset, store_block->relative_offset ); byte_stream_copy_to_uint64_little_endian( ( (vshadow_store_block_header_t *) store_block->data )->offset, store_block->offset ); byte_stream_copy_to_uint64_little_endian( ( (vshadow_store_block_header_t *) store_block->data )->next_offset, store_block->next_offset ); #if defined( HAVE_DEBUG_OUTPUT ) if( libcnotify_verbose != 0 ) { if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); return( -1 ); } if( libfguid_identifier_copy_from_byte_stream( guid, ( (vshadow_store_block_header_t *) store_block->data )->identifier, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); return( -1 ); } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); return( -1 ); } libcnotify_printf( "%s: identifier\t\t\t\t\t: %" PRIs_LIBCSTRING_SYSTEM "\n", function, guid_string ); libcnotify_printf( "%s: version\t\t\t\t\t: %" PRIu32 "\n", function, store_block->version ); libcnotify_printf( "%s: record type\t\t\t\t: %" PRIu32 "\n", function, store_block->record_type ); libcnotify_printf( "%s: relative offset\t\t\t\t: 0x%08" PRIx64 "\n", function, store_block->relative_offset ); libcnotify_printf( "%s: offset\t\t\t\t\t: 0x%08" PRIx64 "\n", function, store_block->offset ); libcnotify_printf( "%s: next offset\t\t\t\t: 0x%08" PRIx64 "\n", function, store_block->next_offset ); byte_stream_copy_to_uint64_little_endian( ( (vshadow_store_block_header_t *) store_block->data )->unknown1, value_64bit ); libcnotify_printf( "%s: unknown1\t\t\t\t\t: %" PRIu64 "\n", function, value_64bit ); libcnotify_printf( "%s: unknown2:\n", function ); libcnotify_print_data( ( (vshadow_store_block_header_t *) store_block->data )->unknown2, 72, LIBCNOTIFY_PRINT_DATA_FLAG_GROUP_DATA ); if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); return( -1 ); } } #endif if( store_block->version != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_UNSUPPORTED_VALUE, "%s: unsupported version: %" PRIu32 ".", function, store_block->version ); return( -1 ); } return( 1 ); }
/* Prints a GUID/UUID value * Returns 1 if successful or -1 on error */ int libfwsi_debug_print_guid_value( const char *function_name, const char *value_name, const uint8_t *byte_stream, size_t byte_stream_size, int byte_order, uint32_t string_format_flags, libcerror_error_t **error ) { system_character_t guid_string[ 48 ]; libfguid_identifier_t *guid = NULL; static char *function = "libfwsi_debug_print_guid_value"; if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, byte_stream, byte_stream_size, byte_order, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } if( libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, string_format_flags, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } libcnotify_printf( "%s: %s: %s\n", function_name, value_name, guid_string ); if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } return( 1 ); on_error: if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } return( -1 ); }
/* Prints the document summary information to a stream * Returns 1 if successful or -1 on error */ int info_handle_document_summary_information_fprint( info_handle_t *info_handle, libcerror_error_t **error ) { uint8_t guid_data[ 16 ]; libcstring_system_character_t guid_string[ 48 ]; libfguid_identifier_t *guid = NULL; libolecf_item_t *property_set_stream = NULL; libolecf_property_set_t *property_set = NULL; libolecf_property_section_t *property_section = NULL; libolecf_property_value_t *property_value = NULL; const char *property_value_identifier_string = NULL; static char *function = "info_handle_document_summary_information_fprint"; uint32_t property_value_identifier = 0; uint32_t property_value_type = 0; int number_of_properties = 0; int number_of_sections = 0; int property_index = 0; int result = 0; int section_index = 0; if( info_handle == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid info handle.", function ); return( -1 ); } if( info_handle->root_item == NULL ) { if( libolecf_file_get_root_item( info_handle->input_file, &( info_handle->root_item ), error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve root item.", function ); return( -1 ); } } /* Using \005 because \x05 also absorbes the D */ result = libolecf_item_get_sub_item_by_utf8_name( info_handle->root_item, (uint8_t *) "\005DocumentSummaryInformation", 27, &property_set_stream, error ); if( result == -1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve sub item.", function ); goto on_error; } else if( result != 0 ) { fprintf( info_handle->notify_stream, "Document summary information:\n" ); if( libolecf_property_set_stream_get_set( property_set_stream, &property_set, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property set stream.", function ); goto on_error; } if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libolecf_property_set_get_class_identifier( property_set, guid_data, 16, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property set class identifier.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, guid_data, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tClass identifier\t: %" PRIs_LIBCSTRING_SYSTEM "\n", guid_string ); if( libolecf_property_set_get_number_of_sections( property_set, &number_of_sections, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve number of sections.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tNumber of sections\t: %d\n", number_of_sections ); fprintf( info_handle->notify_stream, "\n" ); for( section_index = 0; section_index < number_of_sections; section_index++ ) { fprintf( info_handle->notify_stream, "\tSection: %d\n", section_index + 1 ); if( libolecf_property_set_get_section_by_index( property_set, section_index, &property_section, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property set section: %d.", function, section_index ); goto on_error; } if( libolecf_property_section_get_class_identifier( property_section, guid_data, 16, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property section class identifier.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, guid_data, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tClass identifier\t: %" PRIs_LIBCSTRING_SYSTEM "\n", guid_string ); if( libolecf_property_section_get_number_of_properties( property_section, &number_of_properties, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve number of properties.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tNumber of properties\t: %d\n", number_of_properties ); fprintf( info_handle->notify_stream, "\n" ); for( property_index = 0; property_index < number_of_properties; property_index++ ) { fprintf( info_handle->notify_stream, "\tProperty: %d\n", property_index + 1 ); if( libolecf_property_section_get_property_by_index( property_section, property_index, &property_value, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property: %d value.", function, property_index ); goto on_error; } if( libolecf_property_value_get_identifier( property_value, &property_value_identifier, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property: %d value identifier.", function, property_index ); goto on_error; } if( libolecf_property_value_get_value_type( property_value, &property_value_type, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property: %d value type.", function, property_index ); goto on_error; } property_value_identifier_string = NULL; if( memory_compare( guid_data, info_handle_class_identifier_document_summary_information, 16 ) == 0 ) { switch( property_value_type ) { /* TODO */ case LIBOLECF_VALUE_TYPE_INTEGER_16BIT_SIGNED: switch( property_value_identifier ) { case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_CODEPAGE: property_value_identifier_string = "PIDDSI_CODEPAGE"; break; default: break; } break; case LIBOLECF_VALUE_TYPE_INTEGER_32BIT_SIGNED: switch( property_value_identifier ) { case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_BYTE_COUNT: property_value_identifier_string = "PIDDSI_BYTECOUNT"; break; case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_LINE_COUNT: property_value_identifier_string = "PIDDSI_LINECOUNT"; break; case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_PARAGRAPH_COUNT: property_value_identifier_string = "PIDDSI_PARCOUNT"; break; case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_SLIDE_COUNT: property_value_identifier_string = "PIDDSI_SLIDECOUNT"; break; case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_NOTE_COUNT: property_value_identifier_string = "PIDDSI_NOTECOUNT"; break; case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_HIDDEN_SLIDE_COUNT: property_value_identifier_string = "PIDDSI_HIDDENCOUNT"; break; case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_MMCLIP_COUNT: property_value_identifier_string = "PIDDSI_MMCLIPCOUNT"; break; default: break; } break; case LIBOLECF_VALUE_TYPE_BOOLEAN: switch( property_value_identifier ) { case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_SCALE: property_value_identifier_string = "PIDDSI_SCALE"; break; case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_LINKS_DIRTY: property_value_identifier_string = "PIDDSI_LINKSDIRTY"; break; default: break; } break; case LIBOLECF_VALUE_TYPE_STRING_ASCII: case LIBOLECF_VALUE_TYPE_STRING_UNICODE: switch( property_value_identifier ) { case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_CATEGORY : property_value_identifier_string = "PIDDSI_CATEGORY"; break; case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_PRESENTATION_TARGET: property_value_identifier_string = "PIDDSI_PRESFORMAT"; break; case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_MANAGER: property_value_identifier_string = "PIDDSI_MANAGER"; break; case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_COMPANY: property_value_identifier_string = "PIDDSI_COMPANY"; break; default: break; } break; case LIBOLECF_VALUE_TYPE_MULTI_VALUE_VARIANT: switch( property_value_identifier ) { case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_HEADING_PAIRS: property_value_identifier_string = "PIDDSI_HEADINGPAIR"; break; default: break; } break; case LIBOLECF_VALUE_TYPE_MULTI_VALUE_STRING_ASCII: case LIBOLECF_VALUE_TYPE_MULTI_VALUE_STRING_UNICODE: switch( property_value_identifier ) { case LIBOLECF_DOCUMENT_SUMMARY_INFORMATION_PID_DOCUMENT_PARTS: property_value_identifier_string = "PIDDSI_DOCPARTS"; break; default: break; } break; default: break; } } fprintf( info_handle->notify_stream, "\tValue identifier\t: " ); if( property_value_identifier_string != NULL ) { fprintf( info_handle->notify_stream, "%s (", property_value_identifier_string ); } fprintf( info_handle->notify_stream, "0x%08" PRIx32 "", property_value_identifier ); if( property_value_identifier_string != NULL ) { fprintf( info_handle->notify_stream, ")" ); } fprintf( info_handle->notify_stream, "\n" ); fprintf( info_handle->notify_stream, "\tValue type\t\t: %s (0x%08" PRIx32 ")\n", libfole_value_type_get_identifier( property_value_type ), property_value_type ); /* TODO print the properties */ if( libolecf_property_value_free( &property_value, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free property value.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\n" ); } if( libolecf_property_section_free( &property_section, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free property section.", function ); goto on_error; } } if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } if( libolecf_property_set_free( &property_set, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free property set.", function ); goto on_error; } if( libolecf_item_free( &property_set_stream, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free property set stream.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\n" ); } return( 1 ); on_error: if( property_value != NULL ) { libolecf_property_value_free( &property_value, NULL ); } if( property_section != NULL ) { libolecf_property_section_free( &property_section, NULL ); } if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } if( property_set != NULL ) { libolecf_property_set_free( &property_set, NULL ); } if( property_set_stream != NULL ) { libolecf_item_free( &property_set_stream, NULL ); } return( -1 ); }
/* Prints the summary information to a stream * Returns 1 if successful or -1 on error */ int info_handle_summary_information_fprint( info_handle_t *info_handle, libcerror_error_t **error ) { uint8_t guid_data[ 16 ]; libcstring_system_character_t guid_string[ 48 ]; libfguid_identifier_t *guid = NULL; libolecf_item_t *property_set_stream = NULL; libolecf_property_set_t *property_set = NULL; libolecf_property_section_t *property_section = NULL; libolecf_property_value_t *property_value = NULL; const char *property_value_identifier_string = NULL; static char *function = "info_handle_summary_information_fprint"; uint32_t property_value_identifier = 0; uint32_t property_value_type = 0; int number_of_properties = 0; int number_of_sections = 0; int property_index = 0; int result = 0; int section_index = 0; if( info_handle == NULL ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_ARGUMENTS, LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE, "%s: invalid info handle.", function ); return( -1 ); } if( info_handle->root_item == NULL ) { if( libolecf_file_get_root_item( info_handle->input_file, &( info_handle->root_item ), error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve root item.", function ); return( -1 ); } } result = libolecf_item_get_sub_item_by_utf8_name( info_handle->root_item, (uint8_t *) "\005SummaryInformation", 19, &property_set_stream, error ); if( result == -1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve sub item.", function ); goto on_error; } else if( result != 0 ) { fprintf( info_handle->notify_stream, "Summary information:\n" ); if( libolecf_property_set_stream_get_set( property_set_stream, &property_set, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property set stream.", function ); goto on_error; } if( libfguid_identifier_initialize( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED, "%s: unable to create GUID.", function ); goto on_error; } if( libolecf_property_set_get_class_identifier( property_set, guid_data, 16, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property set class identifier.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, guid_data, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tClass identifier\t: %" PRIs_LIBCSTRING_SYSTEM "\n", guid_string ); if( libolecf_property_set_get_number_of_sections( property_set, &number_of_sections, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve number of sections.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tNumber of sections\t: %d\n", number_of_sections ); fprintf( info_handle->notify_stream, "\n" ); for( section_index = 0; section_index < number_of_sections; section_index++ ) { fprintf( info_handle->notify_stream, "\tSection: %d\n", section_index + 1 ); if( libolecf_property_set_get_section_by_index( property_set, section_index, &property_section, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property set section: %d.", function, section_index ); goto on_error; } if( libolecf_property_section_get_class_identifier( property_section, guid_data, 16, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property section class identifier.", function ); goto on_error; } if( libfguid_identifier_copy_from_byte_stream( guid, guid_data, 16, LIBFGUID_ENDIAN_LITTLE, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy byte stream to GUID.", function ); goto on_error; } #if defined( LIBCSTRING_HAVE_WIDE_SYSTEM_CHARACTER ) result = libfguid_identifier_copy_to_utf16_string( guid, (uint16_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #else result = libfguid_identifier_copy_to_utf8_string( guid, (uint8_t *) guid_string, 48, LIBFGUID_STRING_FORMAT_FLAG_USE_LOWER_CASE, error ); #endif if( result != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_COPY_FAILED, "%s: unable to copy GUID to string.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tClass identifier\t: %" PRIs_LIBCSTRING_SYSTEM "\n", guid_string ); if( libolecf_property_section_get_number_of_properties( property_section, &number_of_properties, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve number of properties.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\tNumber of properties\t: %d\n", number_of_properties ); fprintf( info_handle->notify_stream, "\n" ); for( property_index = 0; property_index < number_of_properties; property_index++ ) { fprintf( info_handle->notify_stream, "\tProperty: %d\n", property_index + 1 ); if( libolecf_property_section_get_property_by_index( property_section, property_index, &property_value, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property: %d value.", function, property_index ); goto on_error; } if( libolecf_property_value_get_identifier( property_value, &property_value_identifier, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property: %d value identifier.", function, property_index ); goto on_error; } if( libolecf_property_value_get_value_type( property_value, &property_value_type, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_GET_FAILED, "%s: unable to retrieve property: %d value type.", function, property_index ); goto on_error; } property_value_identifier_string = NULL; if( memory_compare( guid_data, info_handle_class_identifier_summary_information, 16 ) == 0 ) { switch( property_value_type ) { case LIBOLECF_VALUE_TYPE_INTEGER_16BIT_SIGNED: switch( property_value_identifier ) { case LIBOLECF_SUMMARY_INFORMATION_PID_CODEPAGE: property_value_identifier_string = "PIDSI_CODEPAGE"; break; default: break; } break; case LIBOLECF_VALUE_TYPE_INTEGER_32BIT_SIGNED: switch( property_value_identifier ) { case LIBOLECF_SUMMARY_INFORMATION_PID_NUMBER_OF_PAGES: property_value_identifier_string = "PIDSI_PAGECOUNT"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_NUMBER_OF_WORDS: property_value_identifier_string = "PIDSI_WORDCOUNT"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_NUMBER_OF_CHARACTERS: property_value_identifier_string = "PIDSI_CHARCOUNT"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_SECURITY: property_value_identifier_string = "PIDSI_SECURITY"; break; default: break; } break; case LIBOLECF_VALUE_TYPE_STRING_ASCII: case LIBOLECF_VALUE_TYPE_STRING_UNICODE: switch( property_value_identifier ) { case LIBOLECF_SUMMARY_INFORMATION_PID_TITLE: property_value_identifier_string = "PIDSI_TITLE"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_SUBJECT: property_value_identifier_string = "PIDSI_SUBJECT"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_AUTHOR: property_value_identifier_string = "PIDSI_AUTHOR"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_KEYWORDS: property_value_identifier_string = "PIDSI_KEYWORDS"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_COMMENTS: property_value_identifier_string = "PIDSI_COMMENTS"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_TEMPLATE: property_value_identifier_string = "PIDSI_TEMPLATE"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_LAST_SAVED_BY: property_value_identifier_string = "PIDSI_LASTAUTHOR"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_REVISION_NUMBER: property_value_identifier_string = "PIDSI_REVNUMBER"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_APPLICATION_NAME: property_value_identifier_string = "PIDSI_APPNAME"; break; default: break; } break; case LIBOLECF_VALUE_TYPE_FILETIME: switch( property_value_identifier ) { case LIBOLECF_SUMMARY_INFORMATION_PID_EDITING_TIME: property_value_identifier_string = "PIDSI_EDITTIME"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_LAST_PRINTED_TIME: property_value_identifier_string = "PIDSI_LASTPRINTED"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_CREATION_TIME: property_value_identifier_string = "PIDSI_CREATE_DTM"; break; case LIBOLECF_SUMMARY_INFORMATION_PID_LAST_WRITTEN_TIME: property_value_identifier_string = "PIDSI_LASTSAVE_DTM"; break; default: break; } break; case LIBOLECF_VALUE_TYPE_CLIPBOARD_FORMAT: switch( property_value_identifier ) { case LIBOLECF_SUMMARY_INFORMATION_PID_THUMBNAIL: property_value_identifier_string = "PIDSI_THUMBNAIL"; break; default: break; } break; default: break; } } fprintf( info_handle->notify_stream, "\tValue identifier\t: " ); if( property_value_identifier_string != NULL ) { fprintf( info_handle->notify_stream, "%s (", property_value_identifier_string ); } fprintf( info_handle->notify_stream, "0x%08" PRIx32 "", property_value_identifier ); if( property_value_identifier_string != NULL ) { fprintf( info_handle->notify_stream, ")" ); } fprintf( info_handle->notify_stream, "\n" ); fprintf( info_handle->notify_stream, "\tValue type\t\t: %s (0x%08" PRIx32 ")\n", libfole_value_type_get_identifier( property_value_type ), property_value_type ); /* TODO print the properties */ if( libolecf_property_value_free( &property_value, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free property value.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\n" ); } if( libolecf_property_section_free( &property_section, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free property section.", function ); goto on_error; } } if( libfguid_identifier_free( &guid, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free GUID.", function ); goto on_error; } if( libolecf_property_set_free( &property_set, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free property set.", function ); goto on_error; } if( libolecf_item_free( &property_set_stream, error ) != 1 ) { libcerror_error_set( error, LIBCERROR_ERROR_DOMAIN_RUNTIME, LIBCERROR_RUNTIME_ERROR_FINALIZE_FAILED, "%s: unable to free property set stream.", function ); goto on_error; } fprintf( info_handle->notify_stream, "\n" ); } return( 1 ); on_error: if( property_value != NULL ) { libolecf_property_value_free( &property_value, NULL ); } if( property_section != NULL ) { libolecf_property_section_free( &property_section, NULL ); } if( guid != NULL ) { libfguid_identifier_free( &guid, NULL ); } if( property_set != NULL ) { libolecf_property_set_free( &property_set, NULL ); } if( property_set_stream != NULL ) { libolecf_item_free( &property_set_stream, NULL ); } return( -1 ); }