// // Copyright Aliaksei Levin (levlam@telegram.org), Arseny Smirnov (arseny30@gmail.com) 2014-2019 // // Distributed under the Boost Software License, Version 1.0. (See accompanying // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) // #pragma once #include "td/telegram/files/FileLocation.h" #include "td/telegram/files/FileType.h" #include "td/telegram/net/DcId.h" #include "td/telegram/PhotoSizeSource.hpp" #include "td/telegram/Version.h" #include "td/utils/common.h" #include "td/utils/tl_helpers.h" #include "td/utils/Variant.h" namespace td { template void PartialRemoteFileLocation::store(StorerT &storer) const { using td::store; store(file_id_, storer); store(part_count_, storer); store(part_size_, storer); store(ready_part_count_, storer); store(is_big_, storer); } template void PartialRemoteFileLocation::parse(ParserT &parser) { using td::parse; parse(file_id_, parser); parse(part_count_, parser); parse(part_size_, parser); parse(ready_part_count_, parser); parse(is_big_, parser); } template void PhotoRemoteFileLocation::store(StorerT &storer) const { using td::store; bool has_secret = secret_ != 0; bool has_source = source_.get_type() != PhotoSizeSource::Type::Empty; BEGIN_STORE_FLAGS(); STORE_FLAG(has_secret); STORE_FLAG(has_source); END_STORE_FLAGS(); store(id_, storer); store(access_hash_, storer); store(volume_id_, storer); if (has_secret) { store(secret_, storer); } store(local_id_, storer); if (has_source) { store(source_, storer); } } template void PhotoRemoteFileLocation::parse(ParserT &parser) { using td::parse; bool has_secret = true; bool has_source = false; if (parser.version() >= static_cast(Version::AddPhotoSizeSource)) { BEGIN_PARSE_FLAGS(); PARSE_FLAG(has_secret); PARSE_FLAG(has_source); END_PARSE_FLAGS(); } parse(id_, parser); parse(access_hash_, parser); parse(volume_id_, parser); if (has_secret) { parse(secret_, parser); } else { secret_ = 0; } parse(local_id_, parser); if (has_source) { parse(source_, parser); } else { source_ = PhotoSizeSource(); } } template void PhotoRemoteFileLocation::AsKey::store(StorerT &storer) const { using td::store; store(key.id_, storer); store(key.volume_id_, storer); store(key.local_id_, storer); } template void WebRemoteFileLocation::store(StorerT &storer) const { using td::store; store(url_, storer); store(access_hash_, storer); } template void WebRemoteFileLocation::parse(ParserT &parser) { using td::parse; parse(url_, parser); parse(access_hash_, parser); } template void WebRemoteFileLocation::AsKey::store(StorerT &storer) const { td::store(key.url_, storer); } template void CommonRemoteFileLocation::store(StorerT &storer) const { using td::store; store(id_, storer); store(access_hash_, storer); } template void CommonRemoteFileLocation::parse(ParserT &parser) { using td::parse; parse(id_, parser); parse(access_hash_, parser); } template void CommonRemoteFileLocation::AsKey::store(StorerT &storer) const { td::store(key.id_, storer); } template void FullRemoteFileLocation::store(StorerT &storer) const { using ::td::store; store(full_type(), storer); store(dc_id_.get_value(), storer); if (!file_reference_.empty()) { store(file_reference_, storer); } variant_.visit([&](auto &&value) { using td::store; store(value, storer); }); } template void FullRemoteFileLocation::parse(ParserT &parser) { using ::td::parse; int32 raw_type; parse(raw_type, parser); web_location_flag_ = (raw_type & WEB_LOCATION_FLAG) != 0; raw_type &= ~WEB_LOCATION_FLAG; bool has_file_reference = (raw_type & FILE_REFERENCE_FLAG) != 0; raw_type &= ~FILE_REFERENCE_FLAG; if (raw_type < 0 || raw_type >= static_cast(FileType::Size)) { return parser.set_error("Invalid FileType in FullRemoteFileLocation"); } file_type_ = static_cast(raw_type); int32 dc_id_value; parse(dc_id_value, parser); dc_id_ = DcId::from_value(dc_id_value); if (has_file_reference) { parse(file_reference_, parser); file_reference_.clear(); } switch (location_type()) { case LocationType::Web: { variant_ = WebRemoteFileLocation(); return web().parse(parser); } case LocationType::Photo: { variant_ = PhotoRemoteFileLocation(); return photo().parse(parser); } case LocationType::Common: { variant_ = CommonRemoteFileLocation(); return common().parse(parser); } case LocationType::None: { break; } } parser.set_error("Invalid FileType in FullRemoteFileLocation"); } template void FullRemoteFileLocation::AsKey::store(StorerT &storer) const { using td::store; store(key.key_type(), storer); key.variant_.visit([&](auto &&value) { using td::store; store(value.as_key(), storer); }); } template void RemoteFileLocation::store(StorerT &storer) const { td::store(variant_, storer); } template void RemoteFileLocation::parse(ParserT &parser) { td::parse(variant_, parser); } template void PartialLocalFileLocation::store(StorerT &storer) const { using td::store; store(file_type_, storer); store(path_, storer); store(part_size_, storer); int32 deprecated_ready_part_count = -1; store(deprecated_ready_part_count, storer); store(iv_, storer); store(ready_bitmask_, storer); } template void PartialLocalFileLocation::parse(ParserT &parser) { using td::parse; parse(file_type_, parser); if (file_type_ < FileType::Thumbnail || file_type_ >= FileType::Size) { return parser.set_error("Invalid type in PartialLocalFileLocation"); } parse(path_, parser); parse(part_size_, parser); int32 deprecated_ready_part_count; parse(deprecated_ready_part_count, parser); parse(iv_, parser); if (deprecated_ready_part_count == -1) { parse(ready_bitmask_, parser); } else { CHECK(0 <= deprecated_ready_part_count); CHECK(deprecated_ready_part_count <= (1 << 22)); ready_bitmask_ = Bitmask(Bitmask::Ones{}, deprecated_ready_part_count).encode(); } } template void FullLocalFileLocation::store(StorerT &storer) const { using td::store; store(file_type_, storer); store(mtime_nsec_, storer); store(path_, storer); } template void FullLocalFileLocation::parse(ParserT &parser) { using td::parse; parse(file_type_, parser); if (file_type_ < FileType::Thumbnail || file_type_ >= FileType::Size) { return parser.set_error("Invalid type in FullLocalFileLocation"); } parse(mtime_nsec_, parser); parse(path_, parser); } template void PartialLocalFileLocationPtr::store(StorerT &storer) const { td::store(*location_, storer); } template void PartialLocalFileLocationPtr::parse(ParserT &parser) { td::parse(*location_, parser); } template void LocalFileLocation::store(StorerT &storer) const { td::store(variant_, storer); } template void LocalFileLocation::parse(ParserT &parser) { td::parse(variant_, parser); } template void FullGenerateFileLocation::store(StorerT &storer) const { using td::store; store(file_type_, storer); store(original_path_, storer); store(conversion_, storer); } template void FullGenerateFileLocation::parse(ParserT &parser) { using td::parse; parse(file_type_, parser); parse(original_path_, parser); parse(conversion_, parser); } template void GenerateFileLocation::store(StorerT &storer) const { td::store(type_, storer); switch (type_) { case Type::Empty: return; case Type::Full: return td::store(full_, storer); } } template void GenerateFileLocation::parse(ParserT &parser) { td::parse(type_, parser); switch (type_) { case Type::Empty: return; case Type::Full: return td::parse(full_, parser); } return parser.set_error("Invalid type in GenerateFileLocation"); } } // namespace td