Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[RFC] Store the default value in a union inside EbmlSemantic #156

Closed
wants to merge 5 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
47 changes: 45 additions & 2 deletions ebml/EbmlElement.h
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,12 @@ extern const EbmlSemanticContext Context_EbmlGlobal;
#define DEFINE_START_SEMANTIC(x) static const EbmlSemantic ContextList_##x[] = {
#define DEFINE_END_SEMANTIC(x) };
#define DEFINE_SEMANTIC_ITEM(m,u,c) EbmlSemantic(m, u, EBML_INFO(c)),
#define DEFINE_SEMANTIC_ITEM_UINT(m,u,d,c) EbmlSemantic(m, u, static_cast<std::uint64_t>(d), EBML_INFO(c)),
#define DEFINE_SEMANTIC_ITEM_SINT(m,u,d,c) EbmlSemantic(m, u, static_cast<std::int64_t>(d), EBML_INFO(c)),
#define DEFINE_SEMANTIC_ITEM_DATE(m,u,d,c) EbmlSemantic(m, u, static_cast<std::int64_t>(d,true), EBML_INFO(c)),
#define DEFINE_SEMANTIC_ITEM_FLOAT(m,u,d,c) EbmlSemantic(m, u, static_cast<double>(d), EBML_INFO(c)),
#define DEFINE_SEMANTIC_ITEM_STRING(m,u,d,c) EbmlSemantic(m, u, static_cast<const char*>(d), EBML_INFO(c)),
#define DEFINE_SEMANTIC_ITEM_UTF8(m,u,d,c) EbmlSemantic(m, u, static_cast<const wchar_t*>(d), EBML_INFO(c)),

#define DECLARE_EBML_MASTER(x) class EBML_DLL_API x : public EbmlMaster { \
public: \
Expand Down Expand Up @@ -222,18 +228,55 @@ class EBML_DLL_API EbmlCallbacks {
*/
class EBML_DLL_API EbmlSemantic {
public:
struct DefaultValues;

constexpr EbmlSemantic(bool aMandatory, bool aUnique, const EbmlCallbacks & aCallbacks)
:Mandatory(aMandatory), Unique(aUnique), Callbacks(aCallbacks) {}
:Mandatory(aMandatory), Unique(aUnique), defaultValue(), Callbacks(aCallbacks) {}

constexpr EbmlSemantic(bool aMandatory, bool aUnique, const DefaultValues &def, const EbmlCallbacks & aGetCallbacks)
:Mandatory(aMandatory), Unique(aUnique), defaultValue(def), Callbacks(aGetCallbacks) {}

inline bool IsMandatory() const { return Mandatory; }
inline bool IsUnique() const { return Unique; }
inline const DefaultValues & DefaultValue() const { return defaultValue; }
inline EbmlElement & Create() const { return EBML_INFO_CREATE(Callbacks); }
inline explicit operator const EbmlCallbacks &() const { return Callbacks; }
inline EbmlCallbacks const &GetCallbacks() const { return Callbacks; }

private:
enum DefaultType {
NO_DEFAULT,
UINTEGER,
SINTEGER,
DATE,
DOUBLE,
STRING,
UNISTRING,
};
struct DefaultValues {
DefaultType type;
union {
std::uint64_t u64;
std::int64_t i64;
double f;
const char* s;
const wchar_t* ws;
};

constexpr DefaultValues(void) : u64(0), type(DefaultType::NO_DEFAULT) {}
constexpr DefaultValues(const DefaultValues &) = default;
constexpr DefaultValues(std::uint64_t u) : u64(u), type(DefaultType::UINTEGER) {}
constexpr DefaultValues(std::int64_t u, bool date = false) : i64(u), type(date ? DefaultType::UINTEGER : DefaultType::DATE) {}
constexpr DefaultValues(double d) : f(d), type(DefaultType::DOUBLE) {}
constexpr DefaultValues(const char *d) : s(d), type(DefaultType::STRING) {}
constexpr DefaultValues(const wchar_t *d) : ws(d), type(DefaultType::UNISTRING) {}

bool HasDefault() const { return type != DefaultType::NO_DEFAULT; }
};

private:
const bool Mandatory; ///< whether the element is mandatory in the context or not
const bool Unique;
const DefaultValues defaultValue;
const EbmlCallbacks & Callbacks;
};

Expand Down
12 changes: 6 additions & 6 deletions src/EbmlHead.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,13 +12,13 @@
namespace libebml {

DEFINE_START_SEMANTIC(EbmlHead)
DEFINE_SEMANTIC_ITEM(true, true, EVersion) ///< EBMLVersion
DEFINE_SEMANTIC_ITEM(true, true, EReadVersion) ///< EBMLReadVersion
DEFINE_SEMANTIC_ITEM(true, true, EMaxIdLength) ///< EBMLMaxIdLength
DEFINE_SEMANTIC_ITEM(true, true, EMaxSizeLength) ///< EBMLMaxSizeLength
DEFINE_SEMANTIC_ITEM_UINT(true, true, 1, EVersion) ///< EBMLVersion
DEFINE_SEMANTIC_ITEM_UINT(true, true, 1, EReadVersion) ///< EBMLReadVersion
DEFINE_SEMANTIC_ITEM_UINT(true, true, 4, EMaxIdLength) ///< EBMLMaxIdLength
DEFINE_SEMANTIC_ITEM_UINT(true, true, 8, EMaxSizeLength) ///< EBMLMaxSizeLength
DEFINE_SEMANTIC_ITEM(true, true, EDocType) ///< DocType
DEFINE_SEMANTIC_ITEM(true, true, EDocTypeVersion) ///< DocTypeVersion
DEFINE_SEMANTIC_ITEM(true, true, EDocTypeReadVersion) ///< DocTypeReadVersion
DEFINE_SEMANTIC_ITEM_UINT(true, true, 1, EDocTypeVersion) ///< DocTypeVersion
DEFINE_SEMANTIC_ITEM_UINT(true, true, 1, EDocTypeReadVersion) ///< DocTypeReadVersion
DEFINE_END_SEMANTIC(EbmlHead)

DEFINE_EBML_MASTER_ORPHAN(EbmlHead, 0x1A45DFA3, 4, "EBMLHead\0ratamapaga")
Expand Down