2015-05-24 04:55:12 +00:00
|
|
|
// Copyright 2008 Dolphin Emulator Project
|
2015-05-17 23:08:10 +00:00
|
|
|
// Licensed under GPLv2+
|
2013-04-18 03:09:55 +00:00
|
|
|
// Refer to the license.txt file included.
|
2008-12-08 04:46:09 +00:00
|
|
|
|
2014-02-10 18:54:46 +00:00
|
|
|
#pragma once
|
2008-12-08 04:46:09 +00:00
|
|
|
|
2015-12-08 22:49:48 +00:00
|
|
|
#include <cstring>
|
2015-06-13 10:51:24 +00:00
|
|
|
#include <limits>
|
2015-04-09 15:44:53 +00:00
|
|
|
#include <map>
|
2017-05-19 16:33:21 +00:00
|
|
|
#include <memory>
|
2017-06-03 19:29:08 +00:00
|
|
|
#include <optional>
|
2008-12-08 04:46:09 +00:00
|
|
|
#include <string>
|
|
|
|
#include <vector>
|
|
|
|
|
2014-09-08 01:06:58 +00:00
|
|
|
#include "Common/CommonTypes.h"
|
2015-04-10 20:10:49 +00:00
|
|
|
#include "Common/StringUtil.h"
|
2017-03-03 19:43:52 +00:00
|
|
|
#include "Common/Swap.h"
|
2017-02-11 07:57:47 +00:00
|
|
|
#include "Core/IOS/ES/Formats.h"
|
2016-07-06 18:33:05 +00:00
|
|
|
#include "DiscIO/Enums.h"
|
2008-12-08 04:46:09 +00:00
|
|
|
|
|
|
|
namespace DiscIO
|
|
|
|
{
|
2016-07-06 18:33:05 +00:00
|
|
|
enum class BlobType;
|
|
|
|
|
2015-06-13 10:51:24 +00:00
|
|
|
struct Partition final
|
|
|
|
{
|
|
|
|
Partition() : offset(std::numeric_limits<u64>::max()) {}
|
|
|
|
explicit Partition(u64 offset_) : offset(offset_) {}
|
|
|
|
bool operator==(const Partition& other) const { return offset == other.offset; }
|
|
|
|
bool operator!=(const Partition& other) const { return !(*this == other); }
|
|
|
|
bool operator<(const Partition& other) const { return offset < other.offset; }
|
|
|
|
bool operator>(const Partition& other) const { return other < *this; }
|
|
|
|
bool operator<=(const Partition& other) const { return !(*this < other); }
|
|
|
|
bool operator>=(const Partition& other) const { return !(*this > other); }
|
|
|
|
u64 offset;
|
|
|
|
};
|
|
|
|
|
|
|
|
const Partition PARTITION_NONE(std::numeric_limits<u64>::max() - 1);
|
|
|
|
|
2017-06-06 09:49:01 +00:00
|
|
|
class Volume
|
2008-12-08 04:46:09 +00:00
|
|
|
{
|
2009-08-31 22:42:10 +00:00
|
|
|
public:
|
2017-06-06 09:49:01 +00:00
|
|
|
Volume() {}
|
|
|
|
virtual ~Volume() {}
|
2015-06-13 10:51:24 +00:00
|
|
|
virtual bool Read(u64 _Offset, u64 _Length, u8* _pBuffer, const Partition& partition) const = 0;
|
2016-06-24 08:43:46 +00:00
|
|
|
template <typename T>
|
2017-06-04 08:33:14 +00:00
|
|
|
std::optional<T> ReadSwapped(u64 offset, const Partition& partition) const
|
2016-06-24 08:43:46 +00:00
|
|
|
{
|
|
|
|
T temp;
|
2015-06-13 10:51:24 +00:00
|
|
|
if (!Read(offset, sizeof(T), reinterpret_cast<u8*>(&temp), partition))
|
2017-06-04 08:33:14 +00:00
|
|
|
return {};
|
|
|
|
return Common::FromBigEndian(temp);
|
2016-06-24 08:43:46 +00:00
|
|
|
}
|
2017-06-07 09:49:34 +00:00
|
|
|
std::optional<u64> ReadSwappedAndShifted(u64 offset, const Partition& partition) const
|
|
|
|
{
|
|
|
|
const std::optional<u32> temp = ReadSwapped<u32>(offset, partition);
|
|
|
|
return temp ? static_cast<u64>(*temp) << GetOffsetShift() : std::optional<u64>();
|
|
|
|
}
|
|
|
|
|
2017-06-03 16:14:22 +00:00
|
|
|
virtual std::vector<Partition> GetPartitions() const { return {}; }
|
2015-06-13 10:51:24 +00:00
|
|
|
virtual Partition GetGamePartition() const { return PARTITION_NONE; }
|
2017-06-20 19:51:40 +00:00
|
|
|
virtual std::optional<u32> GetPartitionType(const Partition& partition) const { return {}; }
|
2017-06-03 19:29:08 +00:00
|
|
|
std::optional<u64> GetTitleID() const { return GetTitleID(GetGamePartition()); }
|
|
|
|
virtual std::optional<u64> GetTitleID(const Partition& partition) const { return {}; }
|
2017-05-20 16:33:36 +00:00
|
|
|
virtual const IOS::ES::TicketReader& GetTicket(const Partition& partition) const
|
|
|
|
{
|
|
|
|
return INVALID_TICKET;
|
|
|
|
}
|
|
|
|
virtual const IOS::ES::TMDReader& GetTMD(const Partition& partition) const { return INVALID_TMD; }
|
2015-06-13 10:51:24 +00:00
|
|
|
std::string GetGameID() const { return GetGameID(GetGamePartition()); }
|
|
|
|
virtual std::string GetGameID(const Partition& partition) const = 0;
|
|
|
|
std::string GetMakerID() const { return GetMakerID(GetGamePartition()); }
|
|
|
|
virtual std::string GetMakerID(const Partition& partition) const = 0;
|
2017-06-04 08:33:14 +00:00
|
|
|
std::optional<u16> GetRevision() const { return GetRevision(GetGamePartition()); }
|
|
|
|
virtual std::optional<u16> GetRevision(const Partition& partition) const = 0;
|
2015-06-13 10:51:24 +00:00
|
|
|
std::string GetInternalName() const { return GetInternalName(GetGamePartition()); }
|
|
|
|
virtual std::string GetInternalName(const Partition& partition) const = 0;
|
2017-06-03 16:14:22 +00:00
|
|
|
virtual std::map<Language, std::string> GetShortNames() const { return {}; }
|
|
|
|
virtual std::map<Language, std::string> GetLongNames() const { return {}; }
|
|
|
|
virtual std::map<Language, std::string> GetShortMakers() const { return {}; }
|
|
|
|
virtual std::map<Language, std::string> GetLongMakers() const { return {}; }
|
|
|
|
virtual std::map<Language, std::string> GetDescriptions() const { return {}; }
|
2016-06-24 08:43:46 +00:00
|
|
|
virtual std::vector<u32> GetBanner(int* width, int* height) const = 0;
|
2015-06-13 10:51:24 +00:00
|
|
|
std::string GetApploaderDate() const { return GetApploaderDate(GetGamePartition()); }
|
|
|
|
virtual std::string GetApploaderDate(const Partition& partition) const = 0;
|
2016-06-24 08:43:46 +00:00
|
|
|
// 0 is the first disc, 1 is the second disc
|
2017-06-04 08:33:14 +00:00
|
|
|
std::optional<u8> GetDiscNumber() const { return GetDiscNumber(GetGamePartition()); }
|
|
|
|
virtual std::optional<u8> GetDiscNumber(const Partition& partition) const { return 0; }
|
2016-07-06 18:33:05 +00:00
|
|
|
virtual Platform GetVolumeType() const = 0;
|
2016-06-24 08:43:46 +00:00
|
|
|
virtual bool SupportsIntegrityCheck() const { return false; }
|
2015-06-13 10:51:24 +00:00
|
|
|
virtual bool CheckIntegrity(const Partition& partition) const { return false; }
|
2017-07-16 12:49:28 +00:00
|
|
|
// May be inaccurate for WADs
|
2016-12-23 17:41:21 +00:00
|
|
|
virtual Region GetRegion() const = 0;
|
2015-06-13 10:51:24 +00:00
|
|
|
Country GetCountry() const { return GetCountry(GetGamePartition()); }
|
|
|
|
virtual Country GetCountry(const Partition& partition) const = 0;
|
2016-06-24 08:43:46 +00:00
|
|
|
virtual BlobType GetBlobType() const = 0;
|
2015-06-13 10:51:24 +00:00
|
|
|
// Size of virtual disc (may be inaccurate depending on the blob type)
|
2016-06-24 08:43:46 +00:00
|
|
|
virtual u64 GetSize() const = 0;
|
|
|
|
// Size on disc (compressed size)
|
|
|
|
virtual u64 GetRawSize() const = 0;
|
|
|
|
|
|
|
|
static std::vector<u32> GetWiiBanner(int* width, int* height, u64 title_id);
|
2015-12-03 16:29:59 +00:00
|
|
|
|
2015-04-10 20:10:49 +00:00
|
|
|
protected:
|
2016-06-24 08:43:46 +00:00
|
|
|
template <u32 N>
|
|
|
|
std::string DecodeString(const char (&data)[N]) const
|
|
|
|
{
|
|
|
|
// strnlen to trim NULLs
|
|
|
|
std::string string(data, strnlen(data, sizeof(data)));
|
|
|
|
|
2016-12-23 17:41:21 +00:00
|
|
|
if (GetRegion() == Region::NTSC_J)
|
2016-06-24 08:43:46 +00:00
|
|
|
return SHIFTJISToUTF8(string);
|
|
|
|
else
|
|
|
|
return CP1252ToUTF8(string);
|
|
|
|
}
|
|
|
|
|
2017-06-07 09:49:34 +00:00
|
|
|
virtual u32 GetOffsetShift() const { return 0; }
|
2016-07-06 18:33:05 +00:00
|
|
|
static std::map<Language, std::string> ReadWiiNames(const std::vector<u8>& data);
|
2016-06-24 08:43:46 +00:00
|
|
|
|
|
|
|
static const size_t NUMBER_OF_LANGUAGES = 10;
|
|
|
|
static const size_t NAME_STRING_LENGTH = 42;
|
|
|
|
static const size_t NAME_BYTES_LENGTH = NAME_STRING_LENGTH * sizeof(u16);
|
|
|
|
static const size_t NAMES_TOTAL_BYTES = NAME_BYTES_LENGTH * NUMBER_OF_LANGUAGES;
|
2017-05-20 16:33:36 +00:00
|
|
|
|
|
|
|
static const IOS::ES::TicketReader INVALID_TICKET;
|
|
|
|
static const IOS::ES::TMDReader INVALID_TMD;
|
2008-12-08 04:46:09 +00:00
|
|
|
};
|
2009-07-03 22:34:51 +00:00
|
|
|
|
2017-06-06 09:49:01 +00:00
|
|
|
std::unique_ptr<Volume> CreateVolumeFromFilename(const std::string& filename);
|
2017-05-19 16:33:21 +00:00
|
|
|
|
2016-06-24 08:43:46 +00:00
|
|
|
} // namespace
|