1 /*! \file deftypes.h 2 * \brief Definition of classes that load type and class dictionaries 3 * \version $Id: deftypes.h,v 1.13 2007/04/01 11:54:24 matt-beard Exp $ 4 * 5 */ 6 /* 7 * Copyright (c) 2005, Matt Beard 8 * 9 * This software is provided 'as-is', without any express or implied warranty. 10 * In no event will the authors be held liable for any damages arising from 11 * the use of this software. 12 * 13 * Permission is granted to anyone to use this software for any purpose, 14 * including commercial applications, and to alter it and redistribute it 15 * freely, subject to the following restrictions: 16 * 17 * 1. The origin of this software must not be misrepresented; you must 18 * not claim that you wrote the original software. If you use this 19 * software in a product, an acknowledgment in the product 20 * documentation would be appreciated but is not required. 21 * 22 * 2. Altered source versions must be plainly marked as such, and must 23 * not be misrepresented as being the original software. 24 * 25 * 3. This notice may not be removed or altered from any source 26 * distribution. 27 */ 28 #ifndef MXFLIB__DICTIONARY_H 29 #define MXFLIB__DICTIONARY_H 30 31 // STL Includes 32 #include <string> 33 #include <list> 34 35 36 namespace mxflib 37 { 38 // DRAGONS: Why are there two different (but similar) in memory versions of type records? 39 // The answer is that as some types depend on others the loading process requires stacking 40 // part-processed entries for later completion. It is not easy to stack the simple struct 41 // version, partly because of the char pointers to strings and partly because of the fact 42 // that the compound sub-items are linked by their position in the array rather than a pointer 43 // giving ownership - however these same features are required in order to allow data to be 44 // built at compile-time which is highly desirable. When a type definition table made from 45 // the "constant" struct version is loaded it is first copied to a list of classes for easy 46 // manipulation during further processing. 47 48 //! Enumeration identifying the type of an in-memory type definition entry to be processed by LoadTypes() 49 enum TypeClass 50 { 51 TypeNULL = 0, //!< Special token used to end a list of types 52 TypeBasic, //!< Basic type definition (the atomic definition of a type) 53 TypeInterpretation, //!< Interpretation - physically identical to another type, but with different symantics 54 TypeMultiple, //!< Multiple an array or batch of zero or more of another single type 55 TypeCompound, //!< Compound structure of two or more of another type, which may be different types, with a fixed layout 56 TypeSub, //!< An individual sub-item in a compound, or value in an enum 57 TypeEnum, //!< Enumeration type, with one or more named values 58 TypeLabel, //!< Define a label value 59 TypeSymbolSpace //!< Define the default symbol space for all types in this list 60 }; 61 62 //! Referencing kinds for Types 63 enum TypeRef 64 { 65 TypeRefUndefined = -1, //!< Not defined yet for this type (used to differentiate not defined and specifically defined as "none") 66 TypeRefNone = 0, //!< Not a reference 67 TypeRefStrong, //!< A strong reference 68 TypeRefWeak, //!< A weak reference 69 TypeRefTarget, //!< A target of a strong (or weak) reference 70 TypeRefGlobal //!< A global reference - may be to a definition in the file, or to a published definition (outside the scope of the file) 71 }; 72 73 //! Single entry for a type to be defined - can be stored as a compile-time built structure 74 struct ConstTypeRecord 75 { 76 TypeClass Class; //!< The class of type being defined by this entry 77 const char *Type; //!< The name of this type 78 const char *Detail; //!< The human readable description of this type 79 const char *Base; //!< The base type for an interpretation or multiple, or the type for a compound type sub-item 80 const char *UL; //!< The UL for this type (if known) 81 const char *Value; //!< Value if this is an enumerated value, or mask if this is a label 82 int Size; //!< The size in bytes of a basic type, or the number of entries in a multiple 83 bool Endian; //!< Used with basic types: "true" if this type gets endian swapped on reading/writing on a little-endian platform 84 bool IsBatch; //!< Used with multiple types: "true" is this type has an 8-byte Count-and-Size header 85 TypeRef RefType; //!< Reference type of this item (if a reference or target) 86 const char *RefTarget; //!< Type of the reference target (if this is a referencing type) or NULL 87 const char *SymSpace; //!< SymbolSpace for this type, or NULL if none specified (will inherit) 88 }; 89 90 // Forward declare TypeRecord to allow TypeRecordPtr to be defined early 91 class TypeRecord; 92 93 //! A smart pointer to a TypeRecord 94 typedef SmartPtr<TypeRecord> TypeRecordPtr; 95 96 //! List of smart pointers to TypeRecords 97 typedef std::list<TypeRecordPtr> TypeRecordList; 98 99 //! List of TypeRecordLists 100 typedef std::list<TypeRecordList> TypeRecordListList; 101 102 //! Single entry for a type to be defined - built at run-time and can be stacked if required to allow out-of-order definitions 103 class TypeRecord : public RefCount<TypeRecord> 104 { 105 public: 106 TypeClass Class; //!< The class of type being defined by this entry 107 std::string Type; //!< The name of this type 108 std::string Detail; //!< The human readable description of this type 109 std::string Base; //!< The base type for an interpretation or multiple, or the type for a compound type sub-item 110 ULPtr UL; //!< The UL for this type (NULL or "" if not known) 111 std::string Value; //!< Value if this is an enumerated value, or mask if this is a label 112 int Size; //!< The size in bytes of a basic type, or the number of entries in a multiple 113 bool Endian; //!< Used with basic types: "true" if this type gets endian swapped on reading/writing on a little-endian platform 114 bool IsBatch; //!< Used with multiple types: "true" is this type has an 8-byte Count-and-Size header 115 TypeRef RefType; //!< Reference type of this item (if a reference or target) 116 std::string RefTarget; //!< Type of the reference target (if this is a referencing type) 117 SymbolSpacePtr SymSpace; //!< SymbolSpace for this type, or NULL if none specified (will inherit) 118 TypeRecordList Children; //!< Used with compound types: Sub-items within this compound 119 120 public: 121 //! Build an empty TypeRecord TypeRecord()122 TypeRecord() 123 { 124 Class = TypeNULL; 125 Size = 0; 126 Endian = false; 127 IsBatch = false; 128 RefType = TypeRefUndefined; 129 } 130 }; 131 132 //! Load types from the specified XML definitions 133 /*! \return 0 if all OK 134 * \return -1 on error 135 */ 136 int LoadTypes(char *TypesFile, SymbolSpacePtr DefaultSymbolSpace = MXFLibSymbols); 137 138 //! Load types from the specified in-memory definitions 139 /*! \note The last entry in the array must be a terminating entry with Class == TypeNULL 140 * \return 0 if all OK 141 * \return -1 on error 142 * \note If any part of the dictionary loading fails the loading will continue unless FastFail is set to true 143 */ 144 int LoadTypes(const ConstTypeRecord *TypesData, SymbolSpacePtr DefaultSymbolSpace = MXFLibSymbols); 145 146 //! Load types from the specified in-memory definitions 147 /*! \return 0 if all OK 148 * \return -1 on error 149 * \note If any part of the dictionary loading fails the loading will continue unless FastFail is set to true 150 */ 151 int LoadTypes(TypeRecordList &TypesData, SymbolSpacePtr DefaultSymbolSpace = MXFLibSymbols); 152 153 //! Find the traits for a given type - DEPRECATED 154 /*! <b>DEPRECATED - Use MDTraits::Find()</B> 155 */ LookupTraits(const char * Name)156 inline MDTraitsPtr LookupTraits(const char* Name) { return MDTraits::Find(std::string(Name)); } 157 158 //! Disable automatic loading of built-in traits 159 /*! \note This needs to be called early as they may have already been loaded! 160 * \ret false if the traits have already been loaded (or already disabled) 161 */ 162 bool DisableBuiltInTraits(void); 163 164 165 /* Define macros for static type definitions */ 166 167 //! MXFLIB_TYPE_START - Use to start a type definition block 168 #define MXFLIB_TYPE_START(Name) const ConstTypeRecord Name[] = { 169 170 //! MXFLIB_TYPE_START_SYM - Use to start a type definition block and define a default symbol space 171 #define MXFLIB_TYPE_START_SYM(Name, Sym) const ConstTypeRecord Name[] = { { TypeSymbolSpace, "", "", "", "", "", 0, false, false, TypeRefUndefined, NULL, Sym }, 172 173 //! MXFLIB_TYPE_BASIC - Use to define a "Basic" type 174 /*! \param Name The name of the type being defined 175 * \param Detail A human readable description of the type 176 * \param Size The number of bytes used to store this type (must be > 0) 177 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 178 * \param Endian "true" if this type gets endian swapped on reading/writing on a little-endian platform 179 */ 180 #define MXFLIB_TYPE_BASIC(Name, Detail, UL, Size, Endian) { TypeBasic, Name, Detail, "", UL, "", Size, Endian, false, TypeRefUndefined, NULL, NULL }, 181 182 //! MXFLIB_TYPE_BASIC_SYM - Use to define a "Basic" type and override the default symbol space 183 /*! \param Name The name of the type being defined 184 * \param Detail A human readable description of the type 185 * \param Size The number of bytes used to store this type (must be > 0) 186 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 187 * \param Endian "true" if this type gets endian swapped on reading/writing on a little-endian platform 188 * \param Sym The name of the symbol space for this type 189 */ 190 #define MXFLIB_TYPE_BASIC_SYM(Name, Detail, UL, Size, Endian, Sym) { TypeBasic, Name, Detail, "", UL, "", Size, Endian, false, TypeRefUndefined, NULL, Sym }, 191 192 //! MXFLIB_TYPE_BASIC_REF - Use to define a "Basic" type that is a reference source or target 193 /*! \param Name The name of the type being defined 194 * \param Detail A human readable description of the type 195 * \param Size The number of bytes used to store this type (must be > 0) 196 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 197 * \param Endian "true" if this type gets endian swapped on reading/writing on a little-endian platform 198 * \param RefType The reference type (RefWeak, RefStrong or RefTarget) 199 * \param RefTarget The type of the reference target 200 */ 201 #define MXFLIB_TYPE_BASIC_REF(Name, Detail, UL, Size, Endian, RefType, RefTarget) { TypeBasic, Name, Detail, "", UL, "", Size, Endian, false, RefType, RefTarget, NULL }, 202 203 //! MXFLIB_TYPE_BASIC_REF_SYM - Use to define a "Basic" type that is a reference source or target and override the default symbol space 204 /*! \param Name The name of the type being defined 205 * \param Detail A human readable description of the type 206 * \param Size The number of bytes used to store this type (must be > 0) 207 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 208 * \param Endian "true" if this type gets endian swapped on reading/writing on a little-endian platform 209 * \param RefType The reference type (RefWeak, RefStrong or RefTarget) 210 * \param RefTarget The type of the reference target 211 * \param Sym The name of the symbol space for this type 212 */ 213 #define MXFLIB_TYPE_BASIC_REF_SYM(Name, Detail, UL, Size, Endian, RefType, RefTarget, Sym) { TypeBasic, Name, Detail, "", UL, "", Size, Endian, false, RefType, RefTarget, Sym }, 214 215 //! MXFLIB_TYPE_INTERPRETATION - Use to define an "Interpretation" type 216 /*! \param Name The name of the type being defined 217 * \param Detail A human readable description of the type 218 * \param Base The type that this is an interpretation of 219 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 220 * \param Size If non-zero this fixes the number of entries in the variable-length base array 221 */ 222 #define MXFLIB_TYPE_INTERPRETATION(Name, Detail, Base, UL, Size) { TypeInterpretation, Name, Detail, Base, UL, "", Size, false, false, TypeRefUndefined, NULL, NULL }, 223 224 //! MXFLIB_TYPE_INTERPRETATION_SYM - Use to define an "Interpretation" type and override the default symbol space 225 /*! \param Name The name of the type being defined 226 * \param Detail A human readable description of the type 227 * \param Base The type that this is an interpretation of 228 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 229 * \param Size If non-zero this fixes the number of entries in the variable-length base array 230 * \param Sym The name of the symbol space for this type 231 */ 232 #define MXFLIB_TYPE_INTERPRETATION_SYM(Name, Detail, Base, UL, Size, Sym) { TypeInterpretation, Name, Detail, Base, UL, "", Size, false, false, TypeRefUndefined, NULL, Sym }, 233 234 //! MXFLIB_TYPE_INTERPRETATION_REF - Use to define an "Interpretation" type that is a reference source or target 235 /*! \param Name The name of the type being defined 236 * \param Detail A human readable description of the type 237 * \param Base The type that this is an interpretation of 238 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 239 * \param Size If non-zero this fixes the number of entries in the variable-length base array 240 * \param RefType The reference type (RefWeak, RefStrong or RefTarget) 241 * \param RefTarget The type of the reference target 242 */ 243 #define MXFLIB_TYPE_INTERPRETATION_REF(Name, Detail, Base, UL, Size, RefType, RefTarget) { TypeInterpretation, Name, Detail, Base, UL, "", Size, false, false, RefType, RefTarget, NULL }, 244 245 //! MXFLIB_TYPE_INTERPRETATION_REF_SYM - Use to define an "Interpretation" type that is a reference source or target and override the default symbol space 246 /*! \param Name The name of the type being defined 247 * \param Detail A human readable description of the type 248 * \param Base The type that this is an interpretation of 249 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 250 * \param Size If non-zero this fixes the number of entries in the variable-length base array 251 * \param RefType The reference type (RefWeak, RefStrong or RefTarget) 252 * \param RefTarget The type of the reference target 253 * \param Sym The name of the symbol space for this type 254 */ 255 #define MXFLIB_TYPE_INTERPRETATION_REF_SYM(Name, Detail, Base, UL, Size, RefType, RefTarget, Sym) { TypeInterpretation, Name, Detail, Base, UL, "", Size, false, false, RefType, RefTarget, Sym }, 256 257 //! MXFLIB_TYPE_MULTIPLE - Use to define a "Multiple" type 258 /*! \param Name The name of the type being defined 259 * \param Detail A human readable description of the type 260 * \param Base The type of which this is a multiple 261 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 262 * \param IsBatch "true" is this type has an 8-byte Count-and-Size header 263 * \param Size If non-zero this fixes the number of entries, if zero the size is variable 264 */ 265 #define MXFLIB_TYPE_MULTIPLE(Name, Detail, Base, UL, IsBatch, Size) { TypeMultiple, Name, Detail, Base, UL, "", Size, false, IsBatch, TypeRefUndefined, NULL, NULL }, 266 267 //! MXFLIB_TYPE_MULTIPLE_SYM - Use to define a "Multiple" type and override the default symbol space 268 /*! \param Name The name of the type being defined 269 * \param Detail A human readable description of the type 270 * \param Base The type of which this is a multiple 271 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 272 * \param IsBatch "true" is this type has an 8-byte Count-and-Size header 273 * \param Size If non-zero this fixes the number of entries, if zero the size is variable 274 * \param Sym The name of the symbol space for this type 275 */ 276 #define MXFLIB_TYPE_MULTIPLE_SYM(Name, Detail, Base, UL, IsBatch, Size, Sym) { TypeMultiple, Name, Detail, Base, UL, "", Size, false, IsBatch, TypeRefUndefined, NULL, Sym }, 277 278 //! MXFLIB_TYPE_MULTIPLE_REF - Use to define a "Multiple" type that is a reference source or target 279 /*! \param Name The name of the type being defined 280 * \param Detail A human readable description of the type 281 * \param Base The type of which this is a multiple 282 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 283 * \param IsBatch "true" is this type has an 8-byte Count-and-Size header 284 * \param Size If non-zero this fixes the number of entries, if zero the size is variable 285 * \param RefType The reference type (RefWeak, RefStrong or RefTarget) 286 * \param RefTarget The type of the reference target 287 */ 288 #define MXFLIB_TYPE_MULTIPLE_REF(Name, Detail, Base, UL, IsBatch, Size, RefType, RefTarget) { TypeMultiple, Name, Detail, Base, UL, "", Size, false, IsBatch, RefType, RefTarget, NULL }, 289 290 //! MXFLIB_TYPE_MULTIPLE_REF_SYM - Use to define a "Multiple" type that is a reference source or target and override the default symbol space 291 /*! \param Name The name of the type being defined 292 * \param Detail A human readable description of the type 293 * \param Base The type of which this is a multiple 294 * \param UL The UL, or endian-swapped UUID, for this type (or "" to force one to be generated) 295 * \param IsBatch "true" is this type has an 8-byte Count-and-Size header 296 * \param Size If non-zero this fixes the number of entries, if zero the size is variable 297 * \param RefType The reference type (RefWeak, RefStrong or RefTarget) 298 * \param RefTarget The type of the reference target 299 * \param Sym The name of the symbol space for this type 300 */ 301 #define MXFLIB_TYPE_MULTIPLE_REF_SYM(Name, Detail, Base, UL, IsBatch, Size, RefType, RefTarget, Sym) { TypeMultiple, Name, Detail, Base, UL, "", Size, false, IsBatch, RefType, RefTarget, Sym }, 302 303 //! MXFLIB_TYPE_COMPOUND - Use to start the definition of a "Compound" type 304 /*! \param Name The name of the type being defined 305 * \param Detail A human readable description of the type 306 */ 307 #define MXFLIB_TYPE_COMPOUND(Name, Detail, UL) { TypeCompound, Name, Detail, "", UL, "", 0, false, false, TypeRefUndefined, NULL, NULL }, 308 309 //! MXFLIB_TYPE_COMPOUND_SYM - Use to start the definition of a "Compound" type and override the default symbol space 310 /*! \param Name The name of the type being defined 311 * \param Detail A human readable description of the type 312 * \param Sym The name of the symbol space for this type 313 */ 314 #define MXFLIB_TYPE_COMPOUND_SYM(Name, Detail, UL, Sym) { TypeCompound, Name, Detail, "", UL, "", 0, false, false, TypeRefUndefined, NULL, Sym }, 315 316 //! MXFLIB_TYPE_COMPOUND_ITEM - Use to define an item within the current "Compound" type 317 /*! \param Name The name of the item being defined 318 * \param Detail A human readable description of the item 319 * \param Type The type of this item within the compound 320 * \param UL The UL, or endian-swapped UUID, for this item (or "" to force one to be generated) 321 * \param Size If non-zero this fixes the number of entries in a variable-length array 322 */ 323 #define MXFLIB_TYPE_COMPOUND_ITEM(Name, Detail, Type, UL, Size) { TypeSub, Name, Detail, Type, UL, "", Size, false, false, TypeRefUndefined, NULL, NULL }, 324 325 //! MXFLIB_TYPE_COMPOUND_END - Use to end definition of a "Compound" type 326 #define MXFLIB_TYPE_COMPOUND_END 327 328 //! MXFLIB_TYPE_ENUM - Use to start the definition of an "Enumeration" type 329 /*! \param Name The name of the type being defined 330 * \param Detail A human readable description of the type 331 * \param Type The type of the values in this enumeration 332 */ 333 #define MXFLIB_TYPE_ENUM(Name, Detail, Type, UL) { TypeEnum, Name, Detail, Type, UL, "", 0, false, false, TypeRefUndefined, NULL, NULL }, 334 335 //! MXFLIB_TYPE_ENUM_SYM - Use to start the definition of a "Enumeration" type and override the default symbol space 336 /*! \param Name The name of the type being defined 337 * \param Detail A human readable description of the type 338 * \param Type The type of the values in this enumeration 339 * \param Sym The name of the symbol space for this type 340 */ 341 #define MXFLIB_TYPE_ENUM_SYM(Name, Detail, Type, UL, Sym) { TypeEnum, Name, Detail, Type, UL, "", 0, false, false, TypeRefUndefined, NULL, Sym }, 342 343 //! MXFLIB_TYPE_ENUM_VALUE - Use to define a value for the current "Enumeration" type 344 /*! \param Name The name of the value being defined 345 * \param Detail A human readable description of the value 346 * \param Value The value being defined 347 */ 348 #define MXFLIB_TYPE_ENUM_VALUE(Name, Detail, Value) { TypeSub, Name, Detail, "", "", Value, 0, false, false, TypeRefUndefined, NULL, NULL }, 349 350 //! MXFLIB_LABEL - Use to define a label 351 /*! \param Name The name of the label being defined 352 * \param Detail A human readable description of the label 353 * \param UL The UL, or end-swapped UUID of thsi label 354 */ 355 #define MXFLIB_LABEL(Name, Detail, UL) { TypeLabel, Name, Detail, "", UL, NULL, 0, false, false, TypeRefUndefined, NULL, NULL }, 356 357 //! MXFLIB_LABEL_SYM - Use to define a label and override the default symbol space 358 /*! \param Name The name of the label being defined 359 * \param Detail A human readable description of the label 360 * \param UL The UL, or end-swapped UUID of thsi label 361 * \param Sym The name of the symbol space for this type 362 */ 363 #define MXFLIB_LABEL_SYM(Name, Detail, UL, Sym) { TypeLabel, Name, Detail, "", UL, NULL, 0, false, false, TypeRefUndefined, NULL, Sym }, 364 365 //! MXFLIB_MASKED_LABEL - Use to define a masked label 366 /*! \param Name The name of the label being defined 367 * \param Detail A human readable description of the label 368 * \param UL The UL, or end-swapped UUID of thsi label 369 * \param Mask The mask of bits that can change in this label 370 */ 371 #define MXFLIB_MASKED_LABEL(Name, Detail, UL, Mask) { TypeLabel, Name, Detail, "", UL, Mask, 0, false, false, TypeRefUndefined, NULL, NULL }, 372 373 //! MXFLIB_MASKED_LABEL_SYM - Use to define a masked label and override the default symbol space 374 /*! \param Name The name of the label being defined 375 * \param Detail A human readable description of the label 376 * \param UL The UL, or end-swapped UUID of thsi label 377 * \param Mask The mask of bits that can change in this label 378 * \param Sym The name of the symbol space for this type 379 */ 380 #define MXFLIB_MASKED_LABEL_SYM(Name, Detail, UL, Mask, Sym) { TypeLabel, Name, Detail, "", UL, Mask, 0, false, false, TypeRefUndefined, NULL, Sym }, 381 382 383 //! MXFLIB_TYPE_ENUM_END - Use to end definition of a "Enumeration" type 384 #define MXFLIB_TYPE_ENUM_END 385 386 //! MXFLIB_TYPE_END - Use to end a type definition block 387 #define MXFLIB_TYPE_END { TypeNULL, "", "", "", "", "", 0, false, false, TypeRefUndefined, NULL, NULL } }; 388 389 /* Example usage: 390 MXFLIB_TYPE_START(TypeArray) 391 MXFLIB_TYPE_BASIC("UInt8", "Unsigned 8 bit integer", "urn:x-ul:060E2B34.0104.0101.01010100.00000000", 1, false) 392 MXFLIB_TYPE_BASIC("UInt16", "Unsigned 16 bit integer", "urn:x-ul:060E2B34.0104.0101.01010200.00000000", 2, true) 393 MXFLIB_TYPE_BASIC("Int32", "32 bit integer", "urn:x-ul:060E2B34.0104.0101.01010700.00000000", 4, true) 394 395 MXFLIB_TYPE_INTERPRETATION("VersionType", "Version number (created from major*256 + minor)", "UInt16", "urn:x-ul:060E2B34.0104.0101.03010300.00000000", 0) 396 MXFLIB_TYPE_INTERPRETATION("UTF16", "Unicode UTF-16 coded character", "UInt16", "urn:x-ul:060E2B34.0104.0101.01100100.00000000", 0) 397 MXFLIB_TYPE_INTERPRETATION("Boolean", "Boolean", "UInt8", "urn:x-ul:060E2B34.0104.0101.01040100.00000000", 0) 398 399 MXFLIB_TYPE_MULTIPLE("UTF16String", "Unicode UTF-16 coded string", "UTF16", "urn:x-ul:060E2B34.0104.0101.01100200.00000000", false, 0) 400 MXFLIB_TYPE_MULTIPLE("Int32Array", "Array of Int32 values", "Int32", "urn:x-ul:060E2B34.0104.0101.04010900.00000000", false, 0) 401 MXFLIB_TYPE_MULTIPLE("Int32Batch", "Batch of Int32 values", "Int32", "urn:x-ul:060E2B34.0104.0101.04030200.00000000", true, 0) 402 MXFLIB_TYPE_MULTIPLE("Int32Pair", "Pair of Int32 values", "Int32", "", false, 2) 403 404 MXFLIB_TYPE_COMPOUND("Rational", "Rational", "urn:x-ul:060E2B34.0104.0101.03010100.00000000") 405 MXFLIB_TYPE_COMPOUND_ITEM("Numerator", "Numerator", "Int32", "urn:x-ul:060E2B34.0104.0101.03010101.00000000", 0) 406 MXFLIB_TYPE_COMPOUND_ITEM("Denominator", "Denominator", "Int32", "urn:x-ul:060E2B34.0104.0101.03010102.00000000", 0) 407 MXFLIB_TYPE_COMPOUND_END 408 MXFLIB_TYPE_END 409 */ 410 } 411 412 413 namespace mxflib 414 { 415 //! Enumeration identifying the type of an in-memory type definition entry to be processed by LoadTypes() 416 enum ClassType 417 { 418 ClassNULL = 0, //!< Special token used to end a list of classes or the end of a set, pack or vector 419 ClassPack, //!< Pack definition 420 ClassSet, //!< Local set definition 421 ClassVector, //!< Vector (with 8-byte count and size header) definition 422 ClassArray, //!< Array definition 423 ClassItem, //!< Definition of an item in a set, pack, vector or array 424 ClassRename, //!< Rename of a set or pack without new children 425 ClassSymbolSpace //!< Define the default symbol space for all classes in this list 426 }; 427 428 //! Usage types for classes 429 enum ClassUsage 430 { 431 ClassUsageNULL = 0, //!< Not a usage - flag used to signify no usage supplied (or not required) 432 ClassUsageOptional, //!< Item is optional, if present the decoder may ignore it 433 ClassUsageDecoderRequired, //!< Item is optional, but if present the decoder must use this value 434 ClassUsageEncoderRequired, //!< Item must be encoded, but decoder may ignore the value 435 ClassUsageRequired, //!< Item must be encoded and the decoder must use this value 436 ClassUsageBestEffort, //!< As ClassUsageRequired, but an "Incomplete" set of metadata may signal unknown by using a distinguished value 437 ClassUsageToxic, //!< Item must not be encoded - kept for compatibility! 438 ClassUsageDark //!< Item is dark - no longer makes sense: kept for compatibility 439 }; 440 441 //! Referencing types for classes - an exact copy of the type ref kinds 442 typedef TypeRef ClassRef; 443 444 //! ClassRef version of TypeRefUndefined 445 const ClassRef ClassRefUndefined = TypeRefUndefined; 446 447 //! ClassRef version of TypeRefNone 448 const ClassRef ClassRefNone = TypeRefNone; 449 450 //! ClassRef version of TypeRefStrong 451 const ClassRef ClassRefStrong = TypeRefStrong; 452 453 //! ClassRef version of TypeRefWeak 454 const ClassRef ClassRefWeak = TypeRefWeak; 455 456 //! ClassRef version of TypeRefGlobal 457 const ClassRef ClassRefGlobal = TypeRefGlobal; 458 459 //! ClassRef version of TypeRefTarget 460 const ClassRef ClassRefTarget = TypeRefTarget; 461 462 463 //! Single entry for a class to be defined - can be stored as a compile-time built structure 464 struct ConstClassRecord 465 { 466 ClassType Class; //!< The type of class being defined by this entry 467 unsigned int MinSize; //!< The minimum size of an item, or the tag size for a set (0 = no lower limit) 468 unsigned int MaxSize; //!< The maximum size of an item, or the length size/format for a set (0 = no upper limit) 469 const char *Name; //!< The name of this class 470 const char *Detail; //!< The human readable description of this type 471 ClassUsage Usage; //!< The usage type for this class 472 const char *Base; //!< The type of an item, or base type if redefining 473 UInt16 Tag; //!< The 2-byte tag, or zero 474 const char *UL; //!< The UL for this class or item (if known) 475 const char *Default; //!< Default value as a string, or NULL if none 476 const char *DValue; //!< Distinguished value as a string, or NULL if none 477 ClassRef RefType; //!< Reference type of this item (if a reference or target) 478 const char *RefTarget; //!< Type of the reference target (if this is a referencing type) 479 const char *SymSpace; //!< SymbolSpace for this class, or NULL if none specified (will inherit) 480 bool ExtendSubs; //!< If this entry is extending a class, should sub-classes also be extended? 481 }; 482 483 // Forward declare ClassRecord to allow ClassRecordPtr to be defined early 484 class ClassRecord; 485 486 //! A smart pointer to a ClassRecord 487 typedef SmartPtr<ClassRecord> ClassRecordPtr; 488 489 //! List of smart pointers to ClassRecords 490 typedef std::list<ClassRecordPtr> ClassRecordList; 491 492 //! List of ClassRecordLists 493 typedef std::list<ClassRecordList> ClassRecordListList; 494 495 //! Single entry for a class to be defined - built at run-time and can be stacked if required to allow out-of-order definitions 496 class ClassRecord : public RefCount<ClassRecord> 497 { 498 public: 499 ClassType Class; //!< The type of class being defined by this entry 500 unsigned int MinSize; //!< The minimum size of an item, or the tag size for a set (0 = no lower limit) 501 unsigned int MaxSize; //!< The maximum size of an item, or the length size/format for a set (0 = no upper limit) 502 std::string Name; //!< The name of this class 503 std::string Detail; //!< The human readable description of this type 504 ClassUsage Usage; //!< The usage type for this class 505 std::string Base; //!< The type of an item, or base type if redefining 506 UInt16 Tag; //!< The 2-byte tag, or zero 507 ULPtr UL; //!< The UL for this class or item (or NULL if not known) 508 bool HasDefault; //!< True if the item has a default value 509 std::string Default; //!< Default value as a string 510 bool HasDValue; //!< True if the item has a distinguished value 511 std::string DValue; //!< Distinguished value as a string 512 ClassRecordList Children; //!< Sub-items within this class (if it is a set or pack) 513 ClassRef RefType; //!< Reference type of this item (if a reference or target) 514 std::string RefTarget; //!< Type of the reference target (if this is a referencing type) 515 SymbolSpacePtr SymSpace; //!< SymbolSpace for this class, or NULL if none specified (will inherit) 516 bool ExtendSubs; //!< If this entry is extending a class, should sub-classes also be extended? 517 518 public: 519 //! Build an empty ClassRecord ClassRecord()520 ClassRecord() 521 { 522 Class = ClassNULL; 523 MinSize = 0; 524 MaxSize = 0; 525 Usage = ClassUsageNULL; 526 Tag = 0; 527 HasDefault = false; 528 HasDValue = false; 529 RefType = ClassRefUndefined; 530 ExtendSubs = true; 531 } 532 }; 533 534 535 //! Load classes from the specified in-memory definitions 536 /*! \return 0 if all OK 537 * \return -1 on error 538 */ 539 int LoadClasses(ClassRecordList &ClassesData, SymbolSpacePtr DefaultSymbolSpace = MXFLibSymbols); 540 541 //! Load classeses from the specified in-memory definitions 542 /*! \note There must be enough terminating entries (with Class == TypeNULL) to end the list 543 * \return 0 if all OK 544 * \return -1 on error 545 */ 546 int LoadClasses(const ConstClassRecord *ClassData, SymbolSpacePtr DefaultSymbolSpace = MXFLibSymbols); 547 548 549 /* Define macros for static type definitions */ 550 551 //! MXFLIB_CLASS_START - Use to start a class definition block 552 #define MXFLIB_CLASS_START(Name) const ConstClassRecord Name[] = { 553 554 //! MXFLIB_CLASS_START_SYM - Use to start a class definition block and define a default symbol space 555 #define MXFLIB_CLASS_START_SYM(Name, Sym) const ConstClassRecord Name[] = { { ClassSymbolSpace, 0, 0, "", "", ClassUsageNULL, "", 0, "", NULL, NULL, ClassRefUndefined, "", Sym, true }, 556 557 //! MXFLIB_CLASS_SET - Use to define a local set that has 2-byte tags and 2-byte lengths 558 /*! \param Name The name of the set being defined 559 * \param Detail A human readable description of the set 560 * \param Base The base class if this set is a derived class, else "" 561 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 562 */ 563 #define MXFLIB_CLASS_SET(Name, Detail, Base, UL) { ClassSet, 2, 2, Name, Detail, ClassUsageNULL, Base, 0, UL, NULL, NULL, ClassRefUndefined, "", NULL, true }, 564 565 //! MXFLIB_CLASS_SET_SYM - Use to define a local set that has 2-byte tags and 2-byte lengths and override the default symbol space 566 /*! \param Name The name of the set being defined 567 * \param Detail A human readable description of the set 568 * \param Base The base class if this set is a derived class, else "" 569 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 570 * \param Sym The name of the symbol space for this set 571 */ 572 #define MXFLIB_CLASS_SET_SYM(Name, Detail, Base, UL, Sym) { ClassSet, 2, 2, Name, Detail, ClassUsageNULL, Base, 0, UL, NULL, NULL, ClassRefUndefined, "", Sym, true }, 573 574 //! MXFLIB_CLASS_SET_NOSUB - Use to extend a local set that has 2-byte tags and 2-byte lengths, without extending sub-classes 575 /*! \param Name The name of the set being extended 576 * \param Detail A human readable description of the set 577 * \param Base The base class if this set is a derived class, else "" 578 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 579 */ 580 #define MXFLIB_CLASS_SET_NOSUB(Name, Detail, Base, UL) { ClassSet, 2, 2, Name, Detail, ClassUsageNULL, Base, 0, UL, NULL, NULL, ClassRefUndefined, "", NULL, false }, 581 582 //! MXFLIB_CLASS_SET_NOSUB_SYM - Use to extend a local set that has 2-byte tags and 2-byte lengths, without extending sub-classes, and override the default symbol space 583 /*! \param Name The name of the set being extended 584 * \param Detail A human readable description of the set 585 * \param Base The base class if this set is a derived class, else "" 586 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 587 * \param Sym The name of the symbol space for this set 588 */ 589 #define MXFLIB_CLASS_SET_NOSUB_SYM(Name, Detail, Base, UL, Sym) { ClassSet, 2, 2, Name, Detail, ClassUsageNULL, Base, 0, UL, NULL, NULL, ClassRefUndefined, "", Sym, false }, 590 591 //! MXFLIB_CLASS_SET_END - Use to end a set definition 592 #define MXFLIB_CLASS_SET_END { ClassNULL, 0, 0, "", "", ClassUsageNULL, "", 0, "", NULL, NULL, ClassRefUndefined, "", NULL, true }, 593 594 //! MXFLIB_CLASS_FIXEDPACK - Use to define a fixed length pack (defined length pack) 595 /*! \param Name The name of the pack being defined 596 * \param Detail A human readable description of the pack 597 * \param Base The base class if this pack is a derived class, else "" 598 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 599 */ 600 #define MXFLIB_CLASS_FIXEDPACK(Name, Detail, Base, UL) { ClassPack, 0, 0, Name, Detail, ClassUsageNULL, Base, 0, UL, NULL, NULL, ClassRefUndefined, "", NULL, true }, 601 602 //! MXFLIB_CLASS_FIXEDPACK_SYM - Use to define a fixed length pack (defined length pack) and override the default symbol space 603 /*! \param Name The name of the pack being defined 604 * \param Detail A human readable description of the pack 605 * \param Base The base class if this pack is a derived class, else "" 606 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 607 * \param Sym The name of the symbol space for this set 608 */ 609 #define MXFLIB_CLASS_FIXEDPACK_SYM(Name, Detail, Base, UL, Sym) { ClassPack, 0, 0, Name, Detail, ClassUsageNULL, Base, 0, UL, NULL, NULL, ClassRefUndefined, "", Sym, true }, 610 611 //! MXFLIB_CLASS_FIXEDPACK - Use to extend a fixed length pack (defined length pack, without extending sub-classes 612 /*! \param Name The name of the pack being extended 613 * \param Detail A human readable description of the pack 614 * \param Base The base class if this pack is a derived class, else "" 615 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 616 */ 617 #define MXFLIB_CLASS_FIXEDPACK_NOSUB(Name, Detail, Base, UL) { ClassPack, 0, 0, Name, Detail, ClassUsageNULL, Base, 0, UL, NULL, NULL, ClassRefUndefined, "", NULL, false }, 618 619 //! MXFLIB_CLASS_FIXEDPACK_SYM - Use to extend a fixed length pack (defined length pack), without extending sub-classes, and override the default symbol space 620 /*! \param Name The name of the pack being extended 621 * \param Detail A human readable description of the pack 622 * \param Base The base class if this pack is a derived class, else "" 623 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 624 * \param Sym The name of the symbol space for this set 625 */ 626 #define MXFLIB_CLASS_FIXEDPACK_NOSUB_SYM(Name, Detail, Base, UL, Sym) { ClassPack, 0, 0, Name, Detail, ClassUsageNULL, Base, 0, UL, NULL, NULL, ClassRefUndefined, "", Sym, false }, 627 628 //! MXFLIB_CLASS_FIXEDPACK_END - Use to end a pack definition 629 #define MXFLIB_CLASS_FIXEDPACK_END { ClassNULL, 0, 0, "", "", ClassUsageNULL, "", 0, "", NULL, NULL, ClassRefUndefined, "", NULL, true }, 630 631 //! MXFLIB_CLASS_ITEM - Use to define a single item in a set or pack 632 /*! \param Name The name of the item being defined 633 * \param Detail A human readable description of the item 634 * \param Usage The usage type of this item (ClassUsageRequired, ClassUsageOptional, etc.) 635 * \param Type The type of this item 636 * \param Tag The tag for this item as a string of hex bytes e.g. "03 2b" (if in a set, else "") 637 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 638 * \param Default The default value for this item as a string (or NULL if none) 639 * \param DValue The distinguished value for this item as a string (or NULL if none) 640 */ 641 #define MXFLIB_CLASS_ITEM(Name, Detail, Usage, Type, MinSize, MaxSize, Tag, UL, Default, DValue) { ClassItem, MinSize, MaxSize, Name, Detail, Usage, Type, Tag, UL, Default, DValue, ClassRefUndefined, "", NULL, true }, 642 643 //! MXFLIB_CLASS_ITEM_REF - Use to define a single item in a set or pack that is a reference source or target 644 /*! \param Name The name of the item being defined 645 * \param Detail A human readable description of the item 646 * \param Usage The usage type of this item (ClassUsageRequired, ClassUsageOptional, etc.) 647 * \param Type The type of this item 648 * \param Tag The tag for this item as a string of hex bytes e.g. "03 2b" (if in a set, else "") 649 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 650 * \param Default The default value for this item as a string (or NULL if none) 651 * \param DValue The distinguished value for this item as a string (or NULL if none) 652 * \param RefType The reference type (RefWeak, RefStrong or RefTarget) 653 * \param RefTarget The type of the reference target 654 */ 655 #define MXFLIB_CLASS_ITEM_REF(Name, Detail, Usage, Type, MinSize, MaxSize, Tag, UL, RefType, RefTarget, Default, DValue) { ClassItem, MinSize, MaxSize, Name, Detail, Usage, Type, Tag, UL, Default, DValue, RefType, RefTarget, NULL, true }, 656 657 //! MXFLIB_CLASS_ITEM_SYM - Use to define a single item in a set or pack and override the default symbol space 658 /*! \param Name The name of the item being defined 659 * \param Detail A human readable description of the item 660 * \param Usage The usage type of this item (ClassUsageRequired, ClassUsageOptional, etc.) 661 * \param Type The type of this item 662 * \param Tag The tag for this item as a string of hex bytes e.g. "03 2b" (if in a set, else "") 663 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 664 * \param Default The default value for this item as a string (or NULL if none) 665 * \param DValue The distinguished value for this item as a string (or NULL if none) 666 * \param Sym The name of the symbol space for this set 667 */ 668 #define MXFLIB_CLASS_ITEM_SYM(Name, Detail, Usage, Type, MinSize, MaxSize, Tag, UL, Default, DValue, Sym) { ClassItem, MinSize, MaxSize, Name, Detail, Usage, Type, Tag, UL, Default, DValue, ClassRefUndefined, "", Sym, true }, 669 670 //! MXFLIB_CLASS_ITEM_REF_SYM - Use to define a single item in a set or pack that is a reference source or target and override the default symbol space 671 /*! \param Name The name of the item being defined 672 * \param Detail A human readable description of the item 673 * \param Usage The usage type of this item (ClassUsageRequired, ClassUsageOptional, etc.) 674 * \param Type The type of this item 675 * \param Tag The tag for this item as a string of hex bytes e.g. "03 2b" (if in a set, else "") 676 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 677 * \param RefType The reference type (RefWeak, RefStrong or RefTarget) 678 * \param RefTarget The type of the reference target 679 * \param Default The default value for this item as a string (or NULL if none) 680 * \param DValue The distinguished value for this item as a string (or NULL if none) 681 * \param Sym The name of the symbol space for this set 682 */ 683 #define MXFLIB_CLASS_ITEM_REF_SYM(Name, Detail, Usage, Type, MinSize, MaxSize, Tag, UL, RefType, RefTarget, Default, DValue, Sym) { ClassItem, MinSize, MaxSize, Name, Detail, Usage, Type, Tag, UL, Default, DValue, RefType, RefTarget, Sym, true }, 684 685 //! MXFLIB_CLASS_VECTOR - Use to define a vector holding items 686 /*! \param Name The name of the vector being defined 687 * \param Detail A human readable description of the vector 688 * \param Usage The usage type of this vector (ClassUsageRequired, ClassUsageOptional, etc.) 689 * \param Tag The tag for this vector as a string of hex bytes e.g. "03 2b" (if in a set, else "") 690 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 691 */ 692 #define MXFLIB_CLASS_VECTOR(Name, Detail, Usage, Tag, UL) { ClassVector, 0, 0, Name, Detail, Usage, "", Tag, UL, NULL, NULL, ClassRefUndefined, "", NULL, true }, 693 694 //! MXFLIB_CLASS_VECTOR_REF - Use to define a vector holding items that are reference sources or targets 695 /*! \param Name The name of the vector being defined 696 * \param Detail A human readable description of the vector 697 * \param Usage The usage type of this vector (ClassUsageRequired, ClassUsageOptional, etc.) 698 * \param Tag The tag for this vector as a string of hex bytes e.g. "03 2b" (if in a set, else "") 699 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 700 * \param RefType The reference type (RefWeak, RefStrong or RefTarget) 701 * \param RefTarget The type of the reference target 702 */ 703 #define MXFLIB_CLASS_VECTOR_REF(Name, Detail, Usage, Tag, UL, RefType, RefTarget) { ClassVector, 0, 0, Name, Detail, Usage, "", Tag, UL, NULL, NULL, RefType, RefTarget, NULL, true }, 704 705 //! MXFLIB_CLASS_VECTOR_END - Use to end a vector definition 706 #define MXFLIB_CLASS_VECTOR_END { ClassNULL, 0, 0, "", "", ClassUsageNULL, "", 0, "", NULL, NULL, ClassRefUndefined, "", NULL, true }, 707 708 //! MXFLIB_CLASS_ARRAY - Use to define an array holding items 709 /*! \param Name The name of the array being defined 710 * \param Detail A human readable description of the array 711 * \param Usage The usage type of this array (ClassUsageRequired, ClassUsageOptional, etc.) 712 * \param Tag The tag for this array as a string of hex bytes e.g. "03 2b" (if in a set, else "") 713 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 714 */ 715 #define MXFLIB_CLASS_ARRAY(Name, Detail, Usage, Tag, UL) { ClassArray, 0, 0, Name, Detail, Usage, "", Tag, UL, NULL, NULL, ClassRefUndefined, "", NULL, true }, 716 717 //! MXFLIB_CLASS_ARRAY - Use to define an array holding items 718 /*! \param Name The name of the array being defined 719 * \param Detail A human readable description of the array 720 * \param Usage The usage type of this array (ClassUsageRequired, ClassUsageOptional, etc.) 721 * \param Tag The tag for this array as a string of hex bytes e.g. "03 2b" (if in a set, else "") 722 * \param UL The UL of this class as a hex string e.g. "06 0e 2b 34 etc." (if one exists, else "") 723 */ 724 #define MXFLIB_CLASS_ARRAY_REF(Name, Detail, Usage, Tag, UL, RefType, RefTarget) { ClassArray, 0, 0, Name, Detail, Usage, "", Tag, UL, NULL, NULL, RefType, RefTarget, NULL, true }, 725 726 //! MXFLIB_CLASS_ARRAY_END - Use to end a array definition 727 #define MXFLIB_CLASS_ARRAY_END { ClassNULL, 0, 0, "", "", ClassUsageNULL, "", 0, "", NULL, NULL, ClassRefUndefined, "", NULL, true }, 728 729 //! MXFLIB_CLASS_RENAME - Use to rename a set or pack without defining new members 730 /*! \param Name The name of the class being defined 731 * \param Detail A human readable description of the class 732 * \param Base The base class of which this is a rename 733 * \param UL The UL of this class (if one exists, else "") 734 */ 735 #define MXFLIB_CLASS_RENAME(Name, Detail, Base, UL) { ClassRename, 0, 0, Name, Detail, ClassUsageNULL, Base, 0, UL, NULL, NULL, ClassRefUndefined, "", NULL, true }, 736 737 //! MXFLIB_CLASS_END - Use to end a class definition block 738 #define MXFLIB_CLASS_END { ClassNULL, 0, 0, "", "", ClassUsageNULL, "", 0, "", NULL, NULL, ClassRefUndefined, "", NULL, true } }; 739 740 741 /* Example usage: 742 MXFLIB_CLASS_RENAME("KLVFill", "KLV Filler packet", "RAW", "06 0E 2B 34 01 01 01 01 03 01 02 10 01 00 00 00") 743 MXFLIB_CLASS_FIXEDPACK("PartitionMetadata", "Identifies a Partition Pack", "") 744 MXFLIB_CLASS_ITEM("MajorVersion", "Major Version number of MXF byte-level format (non-backwards compatible version number)", ClassUsageRequired, "UInt16", 2, 2, "06 0e 2b 34 01 01 01 04 03 01 02 01 06 00 00 00", "", "0001", "") 745 MXFLIB_CLASS_ITEM("MinorVersion", "Minor Version number of MXF byte-level format (backwards compatible version number)", ClassUsageRequired, "UInt16", 2, 2, "06 0e 2b 34 01 01 01 04 03 01 02 01 06 00 00 00", "", "0001", "") 746 ... 747 MXFLIB_CLASS_ITEM_REF("PrimaryPackage", "The primary Package in this file", ClassUsageOptional, "UUID", 16, 16, "06 0e 2b 34 01 01 01 04 06 01 01 04 01 08 00 00", "3b 08", "", "", RefWeak, "GenericPackage") 748 ... 749 MXFLIB_CLASS_VECTOR("EssenceContainers", "The unordered batch of Universal Labels of Essence Containers used in or referenced by this file", ClassUsageRequired, "06 0e 2b 34 01 01 01 05 01 02 02 10 02 01 00 00", "", "") 750 MXFLIB_CLASS_ITEM("EssenceContainer", "Universal Labels of Essence Container", ClassUsageRequired, "Label", 16, 16, "", "", "", "") 751 MXFLIB_CLASS_VECTOR_END 752 MXFLIB_CLASS_END 753 754 MXFLIB_CLASS_RENAME("OpenHeader", "Open Header Partition Pack", "PartitionMetadata", "06 0e 2b 34 02 05 01 01 0d 01 02 01 01 02 01 00") 755 MXFLIB_CLASS_RENAME("OpenCompleteHeader", "Open Complete Header Partition Pack", "PartitionMetadata", "06 0e 2b 34 02 05 01 01 0d 01 02 01 01 02 03 00") 756 757 <PrimaryPackage detail="The primary Package in this file" use="optional" type="UUID" minLength="16" maxLength="16" key="3b 08" globalKey="06 0e 2b 34 01 01 01 04 06 01 01 04 01 08 00 00" ref="weak" target="GenericPackage"/> 758 */ 759 } 760 761 762 namespace mxflib 763 { 764 //! Enumeration identifying the type of an in-memory dictionary definition entry to be processed by LoadDictionary() 765 enum DictionaryType 766 { 767 DictionaryNULL = 0, //!< Special token used to end a list of dictionary entries 768 DictionaryTypes, //!< Types dictionary befinition 769 DictionaryClasses //!< Class dictionary definition 770 }; 771 772 //! Single entry for a dictionary to be defined - can be stored as a compile-time built structure 773 struct ConstDictionaryRecord 774 { 775 DictionaryType Type; //!< The type of dictionary being defined by this entry 776 const void *Dict; //!< Pointer to either a ConstTypeRecord array or a ConstClassRecord array holding the dictionary to load 777 }; 778 779 // Forward declare Dictionary to allow DictionaryPtr to be defined early 780 class Dictionary; 781 782 //! A smart pointer to a Dictionary 783 typedef SmartPtr<Dictionary> DictionaryPtr; 784 785 //! List of smart pointers to Dictionary objects 786 typedef std::list<DictionaryPtr> DictionaryList; 787 788 //! Run-time dictionary definition - built from other run-time record definitions 789 class Dictionary : public RefCount<Dictionary> 790 { 791 public: 792 TypeRecordListList Types; //!< All the types to define 793 ClassRecordListList Classes; //!< All the classes to define 794 }; 795 796 797 //! Load dictionary from the specified in-memory definitions with a default symbol space 798 /*! \return 0 if all OK 799 * \return -1 on error 800 */ 801 int LoadDictionary(DictionaryPtr &DictionaryData, SymbolSpacePtr DefaultSymbolSpace, bool FastFail = false); 802 803 //! Load dictionary from the specified in-memory definitions 804 /*! \return 0 if all OK 805 * \return -1 on error 806 */ 807 inline int LoadDictionary(DictionaryPtr &DictionaryData, bool FastFail = false, SymbolSpacePtr DefaultSymbolSpace = MXFLibSymbols) 808 { 809 return LoadDictionary(DictionaryData, DefaultSymbolSpace, FastFail ); 810 } 811 812 //! Load dictionary from the specified in-memory definitions with a default symbol space 813 /*! \note There must be a terminating entry (with Type == DictionaryNULL) to end the list 814 * \return 0 if all OK 815 * \return -1 on error 816 */ 817 int LoadDictionary(const ConstDictionaryRecord *DictionaryData, SymbolSpacePtr DefaultSymbolSpace, bool FastFail = false); 818 819 //! Load dictionary from the specified in-memory definitions 820 /*! \note There must be a terminating entry (with Type == DictionaryNULL) to end the list 821 * \return 0 if all OK 822 * \return -1 on error 823 */ 824 inline int LoadDictionary(const ConstDictionaryRecord *DictionaryData, bool FastFail = false, SymbolSpacePtr DefaultSymbolSpace = MXFLibSymbols) 825 { 826 return LoadDictionary(DictionaryData, DefaultSymbolSpace, FastFail); 827 } 828 829 //! Load dictionary from the specified XML definitions with a default symbol space 830 /*! \return 0 if all OK 831 * \return -1 on error 832 */ 833 int LoadDictionary(const char *DictFile, SymbolSpacePtr DefaultSymbolSpace, bool FastFail = false); 834 835 //! Load dictionary from the specified XML definitions with a default symbol space 836 /*! \return 0 if all OK 837 * \return -1 on error 838 */ 839 inline int LoadDictionary(std::string DictFile, SymbolSpacePtr DefaultSymbolSpace, bool FastFail = false) 840 { 841 return LoadDictionary(DictFile.c_str(), DefaultSymbolSpace, FastFail ); 842 } 843 844 //! Load dictionary from the specified XML definitions 845 /*! \return 0 if all OK 846 * \return -1 on error 847 */ 848 inline int LoadDictionary(const char *DictFile, bool FastFail = false, SymbolSpacePtr DefaultSymbolSpace = MXFLibSymbols) 849 { 850 return LoadDictionary(DictFile, DefaultSymbolSpace, FastFail ); 851 } 852 853 //! Load dictionary from the specified XML definitions 854 /*! \return 0 if all OK 855 * \return -1 on error 856 */ 857 inline int LoadDictionary(std::string DictFile, bool FastFail = false, SymbolSpacePtr DefaultSymbolSpace = MXFLibSymbols) 858 { 859 return LoadDictionary(DictFile.c_str(), DefaultSymbolSpace, FastFail ); 860 } 861 862 863 //! MXFLIB_DICTIONARY_START - Use to start a type definition block 864 #define MXFLIB_DICTIONARY_START(Name) const ConstDictionaryRecord Name[] = { 865 866 //! MXFLIB_DICTIONARY_TYPES - Add a set of types to the current dictionary 867 #define MXFLIB_DICTIONARY_TYPES(Types) { DictionaryTypes, Types }, 868 869 //! MXFLIB_DICTIONARY_CLASSES - Add a set of classes to the current dictionary 870 #define MXFLIB_DICTIONARY_CLASSES(Classes) { DictionaryClasses, Classes }, 871 872 //! MXFLIB_DICTIONARY_END - Use to end a dictionary definition block 873 #define MXFLIB_DICTIONARY_END { DictionaryNULL, NULL } }; 874 875 /* Example usage: 876 MXFLIB_DICTIONARY_START(Dict) 877 MXFLIB_DICTIONARY_TYPES(MyTypes) 878 MXFLIB_DICTIONARY_CLASSES(MyClasses) 879 MXFLIB_DICTIONARY_END 880 */ 881 } 882 883 namespace mxflib 884 { 885 class Label; 886 887 // A Smart pointer to a Label 888 typedef SmartPtr<Label> LabelPtr; 889 890 //! A UL or end-swapped UUID label 891 class Label : public RefCount<Label> 892 { 893 protected: 894 UL Value; //!< The value of this label 895 UInt8 Mask[16]; //!< Mask of ignore bits, each set bit flags a bit to be ignored when comparing 896 bool NonZeroMask; //!< True if there is a non-zero mask 897 std::string Name; //!< The XML-Tag-valid name for this label 898 std::string Detail; //!< The human-readable description for this label 899 900 protected: 901 //! Type of the Label map (map of UL to LabelPtr) 902 typedef std::map<UL, LabelPtr> LabelULMap; 903 904 //! Type of the Label multi-map (map of UL to LabelPtr) 905 typedef std::multimap<UL, LabelPtr> LabelULMultiMap; 906 907 //! Map of all existing labels that don't use masking 908 static LabelULMap LabelMap; 909 910 //! Map of all existing labels that use masking - this is a multimap to allow the same base with different masks 911 static LabelULMultiMap LabelMultiMap; 912 913 protected: 914 // Private constructor - to build a new label one of the Insert() functions must be called Label(std::string LabelName,std::string Detail,const UInt8 * LabelUL,const UInt8 * LabelMask)915 Label(std::string LabelName, std::string Detail, const UInt8 *LabelUL, const UInt8 *LabelMask) 916 : Value(LabelUL), Detail(Detail) 917 { 918 Init(LabelName, LabelMask); 919 } 920 921 // Private constructor - to build a new label one of the Insert() functions must be called Label(std::string LabelName,std::string Detail,const UUID & LabelULasUUID,const UInt8 * LabelMask)922 Label(std::string LabelName, std::string Detail, const UUID &LabelULasUUID, const UInt8 *LabelMask) 923 : Value(LabelULasUUID), Detail(Detail) 924 { 925 Init(LabelName, LabelMask); 926 } 927 928 // Constructor common part - called by constructors Init(std::string LabelName,const UInt8 * LabelMask)929 void Init(std::string LabelName, const UInt8 *LabelMask) 930 { 931 Name = LabelName; 932 933 if(LabelMask) 934 { 935 memcpy(Mask, LabelMask, 16); 936 NonZeroMask = true; 937 } 938 else 939 { 940 memset(Mask, 0, 16); 941 NonZeroMask = false; 942 } 943 } 944 945 public: 946 //! Get the name of this label GetName(void)947 std::string GetName(void) { return Name; }; 948 949 //! Get the detail for this label GetDetail(void)950 std::string GetDetail(void) { return Detail; }; 951 952 //! Return true if this label uses a (non-zero) mask HasMask(void)953 bool HasMask(void) { return NonZeroMask; } 954 955 public: 956 //! Construct and add a label from a byte array 957 /*! \return true if succeeded, else false 958 */ 959 static bool Insert(std::string Name, std::string Detail, const UInt8 *LabelValue, const UInt8 *LabelMask = NULL); 960 961 //! Construct and add a label from a UL smart pointer 962 /*! \return true if succeeded, else false 963 */ 964 static bool Insert(std::string Name, std::string Detail, const ULPtr &LabelValue, const UInt8 *LabelMask = NULL); 965 966 //! Construct and add a label from a UL reference 967 /*! \return true if succeeded, else false 968 */ 969 static bool Insert(std::string Name, std::string Detail, const UL &LabelValue, const UInt8 *LabelMask = NULL); 970 971 //! Construct and add a label from a UUID smart pointer 972 /*! \return true if succeeded, else false 973 */ 974 static bool Insert(std::string Name, std::string Detail, const UUIDPtr &LabelValue, const UInt8 *LabelMask = NULL); 975 976 //! Construct and add a label from a UUID reference 977 /*! \return true if succeeded, else false 978 */ 979 static bool Insert(std::string Name, std::string Detail, const mxflib::UUID &LabelValue, const UInt8 *LabelMask = NULL); 980 981 public: 982 //! Find a label with a given value, from a UL reference 983 static LabelPtr Find(const UL &LabelValue); 984 985 //! Find a label with a given value, from a ULPtr Find(const ULPtr & LabelValue)986 static LabelPtr Find(const ULPtr &LabelValue) 987 { 988 return Find(*LabelValue); 989 } 990 991 //! Find a label with a given value, from the label bytes Find(const UInt8 * LabelValue)992 static LabelPtr Find(const UInt8 *LabelValue) 993 { 994 /* Make a value UL and use that in the main search */ 995 UL ValueUL(LabelValue); 996 return Find(ValueUL); 997 } 998 }; 999 } 1000 1001 #endif // MXFLIB__DICTIONARY_H 1002 1003