2020-03-31 17:59:35 +02:00
|
|
|
/*
|
|
|
|
* plist.h
|
|
|
|
*
|
|
|
|
* Created on: 31 Mar 2020
|
|
|
|
* Author: jief
|
|
|
|
*/
|
|
|
|
|
|
|
|
#ifndef PLATFORM_PLIST_H_
|
|
|
|
#define PLATFORM_PLIST_H_
|
|
|
|
|
2020-04-22 19:52:21 +02:00
|
|
|
/* XML Tags */
|
|
|
|
#define kXMLTagPList "plist"
|
|
|
|
#define kXMLTagDict "dict"
|
|
|
|
#define kXMLTagKey "key"
|
|
|
|
#define kXMLTagString "string"
|
|
|
|
#define kXMLTagInteger "integer"
|
|
|
|
#define kXMLTagData "data"
|
|
|
|
#define kXMLTagDate "date"
|
|
|
|
#define kXMLTagFalse "false/"
|
|
|
|
#define kXMLTagTrue "true/"
|
|
|
|
#define kXMLTagArray "array"
|
|
|
|
#define kXMLTagReference "reference"
|
|
|
|
#define kXMLTagID "ID="
|
|
|
|
#define kXMLTagIDREF "IDREF="
|
|
|
|
#define kXMLTagFloat "real"
|
|
|
|
|
|
|
|
|
2020-08-17 21:40:52 +02:00
|
|
|
typedef enum {
|
|
|
|
kTagTypeNone,
|
2020-08-18 18:45:44 +02:00
|
|
|
kTagTypeDict, // 1
|
|
|
|
kTagTypeKey, // 2
|
|
|
|
kTagTypeString, // 3
|
|
|
|
kTagTypeInteger,// 4
|
|
|
|
kTagTypeData, // 5
|
|
|
|
kTagTypeDate, // 6
|
|
|
|
kTagTypeFalse, // 7
|
|
|
|
kTagTypeTrue, // 8
|
|
|
|
kTagTypeArray, // 9
|
|
|
|
kTagTypeFloat // 10
|
2020-08-17 21:40:52 +02:00
|
|
|
} TAG_TYPE;
|
|
|
|
|
2020-08-18 18:45:44 +02:00
|
|
|
class TagStruct;
|
|
|
|
extern XObjArray<TagStruct> gTagsFree;
|
|
|
|
|
2020-08-17 21:40:52 +02:00
|
|
|
|
|
|
|
class TagStruct
|
|
|
|
{
|
2020-08-18 18:45:44 +02:00
|
|
|
UINTN type; // type is private. Use is... functions.
|
|
|
|
XString8 _string;
|
|
|
|
INTN _intValue;
|
|
|
|
float _floatValue;
|
|
|
|
UINT8 *_data;
|
|
|
|
UINTN _dataLen;
|
|
|
|
TagStruct *_tag;
|
|
|
|
TagStruct *_nextTag;
|
|
|
|
|
2020-08-17 21:40:52 +02:00
|
|
|
public:
|
2020-08-18 18:45:44 +02:00
|
|
|
|
|
|
|
TagStruct() : type(kTagTypeNone), _string(), _intValue(0), _floatValue(0), _data(0), _dataLen(0), /*offset(0), */_tag(NULL), _nextTag(NULL) {}
|
2020-08-17 21:40:52 +02:00
|
|
|
TagStruct(const TagStruct& other) = delete; // Can be defined if needed
|
|
|
|
const TagStruct& operator = ( const TagStruct & ) = delete; // Can be defined if needed
|
|
|
|
~TagStruct() {}
|
2020-08-18 18:45:44 +02:00
|
|
|
|
|
|
|
void FreeTag();
|
|
|
|
|
|
|
|
// Property<XString8> string();
|
|
|
|
bool isDict() { return type == kTagTypeDict; }
|
|
|
|
bool isKey() { return type == kTagTypeKey; }
|
|
|
|
bool isString() { return type == kTagTypeString; }
|
|
|
|
bool isInt() { return type == kTagTypeInteger; }
|
|
|
|
bool isFloat() { return type == kTagTypeFloat; }
|
|
|
|
bool isBool() { return type == kTagTypeTrue || type == kTagTypeFalse; }
|
|
|
|
bool isData() { return type == kTagTypeData; }
|
|
|
|
bool isDate() { return type == kTagTypeDate; }
|
|
|
|
bool isArray() { return type == kTagTypeArray; }
|
|
|
|
|
|
|
|
TagStruct* nextTagValue()
|
|
|
|
{
|
|
|
|
return _nextTag;
|
|
|
|
}
|
|
|
|
void setNextTagValue(TagStruct* nextTag)
|
|
|
|
{
|
|
|
|
if ( nextTag == NULL ) panic("TagStruct::setDictNextTagValue() : nextTag == NULL ");
|
|
|
|
if ( _nextTag != NULL ) panic("TagStruct::setDictNextTagValue() : _nextTag != NULL ");
|
|
|
|
_nextTag = nextTag;
|
|
|
|
}
|
|
|
|
|
|
|
|
const XString8 getTypeAsXString8() {
|
|
|
|
if ( isDict() ) return "Dict"_XS8;
|
|
|
|
if ( isKey() ) return "Dict"_XS8;
|
|
|
|
if ( isString() ) return "Dict"_XS8;
|
|
|
|
if ( isInt() ) return "Dict"_XS8;
|
|
|
|
if ( isFloat() ) return "Dict"_XS8;
|
|
|
|
if ( isBool() ) return "Dict"_XS8;
|
|
|
|
if ( isData() ) return "Dict"_XS8;
|
|
|
|
if ( isDate() ) return "Dict"_XS8;
|
|
|
|
if ( isArray() ) return "Dict"_XS8;
|
|
|
|
panic("Unknown type %lld : this is bug", type);
|
|
|
|
}
|
|
|
|
|
|
|
|
// getter and setter
|
|
|
|
UINT8* dataValue()
|
|
|
|
{
|
|
|
|
if ( !isData() ) panic("TagStruct::dataValue() : !isData() ");
|
|
|
|
return _data;
|
|
|
|
}
|
|
|
|
const XString8& dataStringValue()
|
|
|
|
{
|
|
|
|
if ( !isData() ) panic("TagStruct::dataStringValue() : !isData() ");
|
|
|
|
return _string;
|
|
|
|
}
|
|
|
|
UINTN dataLenValue()
|
|
|
|
{
|
|
|
|
if ( !isData() ) panic("TagStruct::dataLenValue() : !isData() ");
|
|
|
|
return _dataLen;
|
|
|
|
}
|
|
|
|
void setDataValue(UINT8* data, UINTN dataLen)
|
|
|
|
{
|
|
|
|
if ( data == NULL ) panic("TagStruct::setDictValue() : _data == NULL ");
|
|
|
|
_data = data;
|
|
|
|
_dataLen = dataLen;
|
|
|
|
type = kTagTypeData;
|
|
|
|
}
|
|
|
|
|
|
|
|
const XString8& dateValue()
|
|
|
|
{
|
|
|
|
if ( !isDict() ) panic("TagStruct::dictValue() : !isDict() ");
|
|
|
|
return _string;
|
|
|
|
}
|
|
|
|
void setDateValue(const XString8& xstring)
|
|
|
|
{
|
|
|
|
if ( xstring.isEmpty() ) panic("TagStruct::setDateValue() : xstring.isEmpty() ");
|
|
|
|
type = kTagTypeDate;
|
|
|
|
_string = xstring;
|
|
|
|
}
|
|
|
|
|
|
|
|
TagStruct* dictTagValue()
|
|
|
|
{
|
|
|
|
if ( !isDict() ) panic("TagStruct::dictValue() : !isDict() ");
|
|
|
|
return _tag;
|
|
|
|
}
|
|
|
|
void setDictTagValue(TagStruct* tagList)
|
|
|
|
{
|
|
|
|
if ( tagList == NULL ) panic("TagStruct::setDictValue() : tagList == NULL ");
|
|
|
|
if ( _tag != NULL ) panic("TagStruct::setDictValue() : _tag != NULL ");
|
|
|
|
if ( _nextTag != NULL ) panic("TagStruct::setDictValue() : _nextTag != NULL ");
|
|
|
|
_tag = tagList;
|
|
|
|
_nextTag = NULL;
|
|
|
|
type = kTagTypeDict;
|
|
|
|
}
|
|
|
|
|
|
|
|
TagStruct* arrayTagValue()
|
|
|
|
{
|
|
|
|
if ( !isArray() ) panic("TagStruct::arrayValue() : !isArray() ");
|
|
|
|
return _tag;
|
|
|
|
}
|
|
|
|
void setArrayTagValue(TagStruct* tag)
|
|
|
|
{
|
|
|
|
// Array value with tagList = NULL is allowed
|
|
|
|
//if ( tag == NULL ) panic("TagStruct::setArrayValue() : tag == NULL ");
|
|
|
|
if ( _tag != NULL ) panic("TagStruct::setArrayValue() : _tag != NULL ");
|
|
|
|
if ( _nextTag != NULL ) panic("TagStruct::setArrayTagValue() : _nextTag != NULL ");
|
|
|
|
_tag = tag;
|
|
|
|
type = kTagTypeArray;
|
|
|
|
}
|
|
|
|
|
|
|
|
XString8& keyValue()
|
|
|
|
{
|
|
|
|
if ( !isKey() ) panic("TagStruct::keyValue() : !isKey() ");
|
|
|
|
return _string;
|
|
|
|
}
|
|
|
|
TagStruct* keyTagValue()
|
|
|
|
{
|
|
|
|
if ( !isKey() ) panic("TagStruct::keyTagValue() : !isKey() ");
|
|
|
|
return _tag;
|
|
|
|
}
|
|
|
|
void setKeyValue(const XString8& xstring, TagStruct* subTag)
|
|
|
|
{
|
|
|
|
if ( xstring.isEmpty() ) panic("TagStruct::setKeyValue() : xstring.isEmpty() ");
|
|
|
|
type = kTagTypeKey;
|
|
|
|
_string = xstring;
|
|
|
|
_tag = subTag;
|
|
|
|
}
|
|
|
|
|
|
|
|
const XString8& stringValue()
|
|
|
|
{
|
|
|
|
if ( !isString() ) panic("TagStruct::stringValue() : !isString() ");
|
|
|
|
return _string;
|
|
|
|
}
|
|
|
|
void setStringValue(const XString8& xstring)
|
|
|
|
{
|
|
|
|
// empty string is allowed
|
|
|
|
//if ( xstring.isEmpty() ) panic("TagStruct::setStringValue() : xstring.isEmpty() ");
|
|
|
|
type = kTagTypeString;
|
|
|
|
_string = xstring;
|
|
|
|
}
|
|
|
|
|
|
|
|
INTN intValue()
|
|
|
|
{
|
|
|
|
if ( !isInt() ) panic("TagStruct::intValue() : !isInt() ");
|
|
|
|
return _intValue;
|
|
|
|
}
|
|
|
|
void setIntValue(INTN i)
|
|
|
|
{
|
|
|
|
type = kTagTypeInteger;
|
|
|
|
_intValue = i;
|
|
|
|
}
|
|
|
|
|
|
|
|
float floatValue()
|
|
|
|
{
|
|
|
|
if ( !isFloat() ) panic("TagStruct::floatValue() : !isFloat() ");
|
|
|
|
return _floatValue;
|
|
|
|
}
|
|
|
|
void setFloatValue(float f)
|
|
|
|
{
|
|
|
|
type = kTagTypeFloat;
|
|
|
|
_floatValue = f;
|
|
|
|
}
|
|
|
|
|
|
|
|
INTN boolValue()
|
|
|
|
{
|
|
|
|
if ( !isBool() ) panic("TagStruct::boolValue() : !isBool() ");
|
|
|
|
return type == kTagTypeTrue;
|
|
|
|
}
|
|
|
|
void setBoolValue(bool b)
|
|
|
|
{
|
|
|
|
if ( b ) type = kTagTypeTrue;
|
|
|
|
else type = kTagTypeFalse;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Convenience method
|
|
|
|
bool isTrue()
|
|
|
|
{
|
|
|
|
if ( isBool() ) return boolValue();
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
bool isFalse()
|
|
|
|
{
|
|
|
|
if ( isBool() ) return !boolValue();
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
bool isTrueOrYy()
|
|
|
|
{
|
|
|
|
if ( isBool() ) return boolValue();
|
|
|
|
if ( isString() && stringValue().notEmpty() && (stringValue()[0] == 'y' || stringValue()[0] == 'Y') ) return true;
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
bool isTrueOrYes()
|
|
|
|
{
|
|
|
|
if ( isBool() ) return boolValue();
|
|
|
|
if ( isString() && stringValue().equal("Yes"_XS8) ) return true;
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
bool isFalseOrNn()
|
|
|
|
{
|
|
|
|
if ( isBool() ) return !boolValue();
|
|
|
|
if ( isString() && stringValue().notEmpty() && (stringValue()[0] == 'n' || stringValue()[0] == 'N') ) return true;
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
TagStruct* dictOrArrayTagValue()
|
|
|
|
{
|
|
|
|
if ( isDict() ) return dictTagValue();
|
|
|
|
if ( isArray() ) return arrayTagValue();
|
|
|
|
panic("TagStruct::dictOrArrayTagValue() : !isDict() && isArray() ");
|
|
|
|
}
|
2020-08-17 21:40:52 +02:00
|
|
|
};
|
2020-03-31 17:59:35 +02:00
|
|
|
|
2020-08-17 21:40:52 +02:00
|
|
|
typedef TagStruct* TagPtr;
|
2020-03-31 17:59:35 +02:00
|
|
|
|
2020-04-22 19:52:21 +02:00
|
|
|
typedef union {
|
|
|
|
struct {
|
|
|
|
float fNum; //4 bytes
|
|
|
|
UINT32 pad; // else 4
|
|
|
|
} B;
|
|
|
|
CHAR8 *string;
|
|
|
|
} FlMix;
|
2020-03-31 17:59:35 +02:00
|
|
|
|
|
|
|
|
2020-04-16 09:15:26 +02:00
|
|
|
CHAR8*
|
|
|
|
XMLDecode (
|
|
|
|
CHAR8 *src
|
|
|
|
);
|
|
|
|
|
|
|
|
EFI_STATUS
|
2020-05-15 05:23:33 +02:00
|
|
|
ParseXML(
|
2020-04-16 09:15:26 +02:00
|
|
|
CONST CHAR8 *buffer,
|
|
|
|
TagPtr *dict,
|
|
|
|
UINT32 bufSize
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
|
|
//VOID RenderSVGfont(NSVGfont *fontSVG);
|
|
|
|
|
|
|
|
TagPtr
|
2020-04-23 11:08:10 +02:00
|
|
|
GetProperty(
|
2020-04-16 09:15:26 +02:00
|
|
|
TagPtr dict,
|
|
|
|
CONST CHAR8* key
|
|
|
|
);
|
|
|
|
|
|
|
|
EFI_STATUS
|
|
|
|
XMLParseNextTag (
|
|
|
|
CHAR8 *buffer,
|
|
|
|
TagPtr *tag,
|
|
|
|
UINT32 *lenPtr
|
|
|
|
);
|
|
|
|
|
|
|
|
VOID
|
|
|
|
FreeTag (
|
|
|
|
TagPtr tag
|
|
|
|
);
|
|
|
|
|
|
|
|
EFI_STATUS
|
|
|
|
GetNextTag (
|
|
|
|
UINT8 *buffer,
|
|
|
|
CHAR8 **tag,
|
|
|
|
UINT32 *start,
|
|
|
|
UINT32 *length
|
|
|
|
);
|
|
|
|
|
|
|
|
INTN
|
|
|
|
GetTagCount (
|
|
|
|
TagPtr dict
|
|
|
|
);
|
|
|
|
|
|
|
|
EFI_STATUS
|
2020-05-11 08:30:45 +02:00
|
|
|
GetElement(
|
2020-04-16 09:15:26 +02:00
|
|
|
TagPtr dict,
|
|
|
|
INTN id,
|
|
|
|
TagPtr *dict1
|
|
|
|
);
|
|
|
|
|
|
|
|
BOOLEAN
|
2020-05-11 08:30:45 +02:00
|
|
|
IsPropertyTrue(
|
2020-04-16 09:15:26 +02:00
|
|
|
TagPtr Prop
|
|
|
|
);
|
|
|
|
|
|
|
|
BOOLEAN
|
2020-05-11 08:30:45 +02:00
|
|
|
IsPropertyFalse(
|
2020-04-16 09:15:26 +02:00
|
|
|
TagPtr Prop
|
|
|
|
);
|
|
|
|
|
|
|
|
INTN
|
2020-04-23 11:08:10 +02:00
|
|
|
GetPropertyInteger(
|
2020-04-16 09:15:26 +02:00
|
|
|
TagPtr Prop,
|
|
|
|
INTN Default
|
|
|
|
);
|
|
|
|
|
2020-04-22 19:52:21 +02:00
|
|
|
float GetPropertyFloat (TagPtr Prop, float Default);
|
|
|
|
|
2020-04-16 09:15:26 +02:00
|
|
|
|
2020-03-31 17:59:35 +02:00
|
|
|
#endif /* PLATFORM_PLIST_H_ */
|