void deserializer::read()

in src/native/diffs/serialization/legacy/deserializer.cpp [480:565]


void deserializer::read(io::reader &reader)
{
	io::sequential::basic_reader_wrapper seq(reader);

	char magic[4]{};

	seq.read(std::span<char>{magic, sizeof(magic)});

	if (0 != std::memcmp(magic, g_DIFF_MAGIC_VALUE.data(), sizeof(magic)))
	{
		std::string magic_string(magic, 4);
		std::string msg = "Not a valid diff file - invalid magic. Found: " + magic_string;
		throw errors::user_exception(errors::error_code::diff_magic_header_wrong, msg);
	}

	uint64_t version;

	seq.read_uint64_t(&version);

	if (version != g_DIFF_VERSION)
	{
		std::string msg =
			"Not a valid version. Expected: " + std::to_string(g_DIFF_VERSION) + ", Found: " + std::to_string(version);
		throw errors::user_exception(errors::error_code::diff_version_wrong, msg);
	}

	uint64_t length;
	seq.read_uint64_t(&length);

	hashing::hash archive_item_hash;
	archive_item_hash.read(seq);
	auto archive_item = diffs::core::item_definition{length}.with_hash(archive_item_hash);
	if (m_archive.get())
	{
		m_archive->set_archive_item(archive_item);
	}

	seq.read_uint64_t(&length);
	if (length != 0)
	{
		hashing::hash source_item_hash;
		source_item_hash.read(seq);
		auto source_item = diffs::core::item_definition{length}.with_hash(source_item_hash);
		m_archive->set_source_item(source_item);
		m_source_item = source_item;
	}

	uint64_t chunk_count;
	seq.read_uint64_t(&chunk_count);

	std::vector<diffs::core::item_definition> chain_ingredients;

	for (uint64_t i = 0; i < chunk_count; i++)
	{
		chain_ingredients.emplace_back(read_chunk(seq));
	}

	m_all_recipes.emplace_back(std::make_shared<diffs::recipes::basic::chain_recipe>(
		archive_item, std::vector<uint64_t>(), chain_ingredients));

	seq.read_uint64_t(&m_inline_assets_size);
	m_inline_assets_offset = seq.tellg();
	seq.skip(m_inline_assets_size);

	seq.read_uint64_t(&m_remainder_uncompressed_size);
	seq.read_uint64_t(&m_remainder_compressed_size);
	m_remainder_offset = seq.tellg();

	m_diff_size = m_remainder_offset + m_remainder_compressed_size;

	if (m_diff_size != seq.size())
	{
		std::string msg = "diffs::read(). Size mismatch for diff. Size based on reading data: "
		                + std::to_string(m_diff_size) + ". Size from reader: " + std::to_string(reader.size());
		throw errors::user_exception(errors::error_code::diff_read_diff_size_mismatch, msg);
	}

	//
	// Create core items
	//
	create_diff_item(reader);
	create_remainder_items(reader);
	create_inline_assets_item(reader);

	finalize_legacy_recipes();
}