/* * ConfigPlist.h * * Created on: Oct 9, 2020 * Author: jief */ #ifndef _CONFIGPLISTCLASS_Boot_H_ #define _CONFIGPLISTCLASS_Boot_H_ #include "../../cpp_lib/XmlLiteSimpleTypes.h" #include "../../cpp_lib/XmlLiteCompositeTypes.h" #include "../../cpp_lib/XmlLiteParser.h" #include "../../include/BootTypes.h" class Boot_Class : public XmlDict { using super = XmlDict; class XMPDetectionClass : public XmlUnion { using super = XmlUnion; protected: XmlStrictBool xmlBool = XmlStrictBool(); XmlInt8 xmlInt8 = XmlInt8(); XmlString8AllowEmpty xmlString8 = XmlString8AllowEmpty(); XmlUnionField m_fields[3] = { xmlBool, xmlInt8, xmlString8 }; virtual void getFields(XmlUnionField** fields, size_t* nb) override { *fields = m_fields; *nb = sizeof(m_fields)/sizeof(m_fields[0]); }; virtual XBool validate(XmlLiteParser* xmlLiteParser, const XString8& xmlPath, const XmlParserPosition& keyPos, XBool generateErrors) override { RETURN_IF_FALSE( super::validate(xmlLiteParser, xmlPath, keyPos, generateErrors) ); if ( xmlBool.isDefined() ) return true; // ok, whatever XBool value is if ( xmlInt8.isDefined() ) { if ( xmlInt8.value() < -1 || xmlInt8.value() > 2 ) { xmlLiteParser->addWarning(generateErrors, S8Printf("XMPDetection can -1, 0, 1 or 2 for tag '%s:%d'.", xmlPath.c_str(), keyPos.getLine())); xmlInt8.reset(); xmlInt8.setInt8Value(-1); } return true; } if ( xmlString8.value().startWithOrEqualToIC("n") ) return true; if ( xmlString8.value().startWithOrEqualToIC("-") ) return true; xmlLiteParser->addWarning(generateErrors, S8Printf("Expect a boolean, an int8 or a string starting with 'n' or '-' for '%s:%d'.", xmlPath.c_str(), keyPos.getLine())); return false; // parsing can continue. } public: int8_t dgetValue() const { if ( xmlBool.isDefined() ) return xmlBool.value() ? 0 : -1; if ( xmlInt8.isDefined() ) return xmlInt8.value(); if ( xmlString8.isDefined() ) { if ( xmlString8.value().startWithOrEqualToIC("n") ) return -1; if ( xmlString8.value().startWithOrEqualToIC("-") ) return -1; } return 0; } }; public: XmlInt32 Timeout = XmlInt32(); XmlBool SkipHibernateTimeout = XmlBool(); XmlBool DisableCloverHotkeys = XmlBool(); XmlString8AllowEmpty BootArgs = XmlString8AllowEmpty(); XmlBool NeverDoRecovery = XmlBool(); XmlStringW DefaultVolume = XmlStringW(); XmlString8AllowEmpty DefaultLoader = XmlString8AllowEmpty(); XmlBoolYesNo Debug = XmlBoolYesNo(); XmlBool FastBoot = XmlBool(); XmlBool NoEarlyProgress = XmlBool(); XmlBool NeverHibernate = XmlBool(); XmlBool StrictHibernate = XmlBool(); XmlBool RtcHibernateAware = XmlBool(); XmlBool HibernationFixup = XmlBool(); XmlBool SignatureFixup = XmlBool(); XmlBool SecureBootSetupMode = XmlBool(); XmlString8AllowEmpty SecureBootPolicy = XmlString8AllowEmpty(); XmlStringWArray WhiteList = XmlStringWArray(); XmlStringWArray BlackList = XmlStringWArray(); XMPDetectionClass XMPDetection = XMPDetectionClass(); XmlString8AllowEmpty Legacy = XmlString8AllowEmpty(); XmlUInt16 LegacyBiosDefaultEntry = XmlUInt16(); class CustomLogoUnion: public XmlUnion { using super = XmlUnion; public: XmlBool xmlBool = XmlBool(); XmlString8AllowEmpty xmlString8 = XmlString8AllowEmpty(); XmlData xmlData = XmlData(); XmlUnionField m_fields[3] = { xmlBool, xmlString8, xmlData}; virtual void getFields(XmlUnionField** fields, size_t* nb) override { *fields = m_fields; *nb = sizeof(m_fields)/sizeof(m_fields[0]); }; virtual XBool validate(XmlLiteParser* xmlLiteParser, const XString8& xmlPath, const XmlParserPosition& keyPos, XBool generateErrors) override { RETURN_IF_FALSE( super::validate(xmlLiteParser, xmlPath, keyPos, generateErrors) ); if ( !xmlString8.isDefined() ) return true; if ( xmlString8.value().isEqualIC("Apple") ) return true; if ( xmlString8.value().isEqualIC("Alternate") ) return true; if ( xmlString8.value().isEqualIC("Theme") ) return true; xmlLiteParser->addWarning(generateErrors, S8Printf("Expect a boolean or \"Apple\", \"Alternate\", \"Theme\" or an image pathname for tag '%s:%d'.", xmlPath.c_str(), keyPos.getLine())); return false; // parsing can continue. } } CustomLogo = CustomLogoUnion(); XmlDictField m_fields[23] = { {"Timeout", Timeout}, {"SkipHibernateTimeout", SkipHibernateTimeout}, {"DisableCloverHotkeys", DisableCloverHotkeys}, {"Arguments", BootArgs}, {"NeverDoRecovery", NeverDoRecovery}, {"DefaultVolume", DefaultVolume}, {"DefaultLoader", DefaultLoader}, {"Debug", Debug}, {"Fast", FastBoot}, {"NoEarlyProgress", NoEarlyProgress}, {"NeverHibernate", NeverHibernate}, {"StrictHibernate", StrictHibernate}, {"RtcHibernateAware", RtcHibernateAware}, {"HibernationFixup", HibernationFixup}, {"SignatureFixup", SignatureFixup}, {"Secure", SecureBootSetupMode}, {"Policy", SecureBootPolicy}, {"WhiteList", WhiteList}, {"BlackList", BlackList}, {"XMPDetection", XMPDetection}, {"Legacy", Legacy}, {"LegacyBiosDefaultEntry", LegacyBiosDefaultEntry}, {"CustomLogo", CustomLogo}, }; public: virtual void getFields(XmlDictField** fields, size_t* nb) override { *fields = m_fields; *nb = sizeof(m_fields)/sizeof(m_fields[0]); }; /* dget method means get value and returns default if undefined. dget = short for defaultget */ int64_t dgetTimeout() const { return Timeout.isDefined() ? Timeout.value() : -1; }; XBool dgetSkipHibernateTimeout() const { return SkipHibernateTimeout.isDefined() ? SkipHibernateTimeout.value() : XBool(false); }; XBool dgetDisableCloverHotkeys() const { return DisableCloverHotkeys.isDefined() ? DisableCloverHotkeys.value() : XBool(false); }; const XString8& dgetBootArgs() const { return BootArgs.isDefined() ? BootArgs.value() : NullXString8; }; XBool dgetNeverDoRecovery() const { return NeverDoRecovery.isDefined() ? NeverDoRecovery.value() : XBool(false); }; const decltype(DefaultVolume)::ValueType& dgetDefaultVolume() const { if ( !DefaultVolume.isDefined() ) return DefaultVolume.nullValue; if ( DefaultVolume.value().isEqualIC("LastBootedVolume") ) return DefaultVolume.nullValue; return DefaultVolume.isDefined() ? DefaultVolume.value() : DefaultVolume.nullValue; }; const XString8& dgetDefaultLoader() const { return DefaultLoader.isDefined() ? DefaultLoader.value() : NullXString8; }; XBool dgetDebugLog() const { return Debug.isDefined() ? Debug.value() : XBool(false); }; XBool dgetFastBoot() const { return FastBoot.isDefined() ? FastBoot.value() : XBool(false); }; XBool dgetNoEarlyProgress() const { return NoEarlyProgress.isDefined() ? NoEarlyProgress.value() : XBool(false); }; XBool dgetNeverHibernate() const { return NeverHibernate.isDefined() ? NeverHibernate.value() : XBool(false); }; XBool dgetStrictHibernate() const { return StrictHibernate.isDefined() ? StrictHibernate.value() : XBool(false); }; XBool dgetRtcHibernateAware() const { return RtcHibernateAware.isDefined() ? RtcHibernateAware.value() : XBool(false); }; XBool dgetHibernationFixup() const { return HibernationFixup.isDefined() ? HibernationFixup.value() : XBool(false); }; XBool dgetSignatureFixup() const { return SignatureFixup.isDefined() ? SignatureFixup.value() : XBool(false); }; INT8 dgetSecureSetting() const { return isDefined() ? SecureBootSetupMode.isDefined() ? (int)SecureBootSetupMode.value() : -1 : 0; }; // to Rename to SecureBootSetupMode // TODO: different default value if section is not defined UINT8 dgetSecureBootPolicy() const { if ( !SecureBootPolicy.isDefined() ) return 0; if ( SecureBootPolicy.value().length() < 1 ) return 0; if ((SecureBootPolicy.value()[0] == 'D') || (SecureBootPolicy.value()[0] == 'd')) { // Deny all images return SECURE_BOOT_POLICY_DENY; } else if ((SecureBootPolicy.value()[0] == 'A') || (SecureBootPolicy.value()[0] == 'a')) { // Allow all images return SECURE_BOOT_POLICY_ALLOW; } else if ((SecureBootPolicy.value()[0] == 'Q') || (SecureBootPolicy.value()[0] == 'q')) { // Query user return SECURE_BOOT_POLICY_QUERY; } else if ((SecureBootPolicy.value()[0] == 'I') || (SecureBootPolicy.value()[0] == 'i')) { // Insert return SECURE_BOOT_POLICY_INSERT; } else if ((SecureBootPolicy.value()[0] == 'W') || (SecureBootPolicy.value()[0] == 'w')) { // White list return SECURE_BOOT_POLICY_WHITELIST; } else if ((SecureBootPolicy.value()[0] == 'B') || (SecureBootPolicy.value()[0] == 'b')) { // Black list return SECURE_BOOT_POLICY_BLACKLIST; } else if ((SecureBootPolicy.value()[0] == 'U') || (SecureBootPolicy.value()[0] == 'u')) { // User policy return SECURE_BOOT_POLICY_USER; } return 0; } const decltype(WhiteList)::ValueType& dgetSecureBootWhiteList() const { return WhiteList.isDefined() ? WhiteList.value() : WhiteList.nullValue; }; const decltype(BlackList)::ValueType& dgetSecureBootBlackList() const { return BlackList.isDefined() ? BlackList.value() : BlackList.nullValue; }; // int8_t dgetXMPDetection() const { // if ( XMPDetection.xmlBool.isDefined() ) return XMPDetection.xmlBool.value(); // if ( XMPDetection.xmlInt8.isDefined() ) return XMPDetection.xmlInt8.value(); // return 0; // }; int8_t dgetXMPDetection() const { return XMPDetection.dgetValue(); } XString8 dgetLegacyBoot(XBool isFirmwareClover) const { return isDefined() ? Legacy.isDefined() ? Legacy.value() : isFirmwareClover ? "PBR"_XS8 : "LegacyBiosDefault"_XS8 : NullXString8; }; // TODO: different default value if section is not defined UINT16 dgetLegacyBiosDefaultEntry() const { return LegacyBiosDefaultEntry.isDefined() ? LegacyBiosDefaultEntry.value() : 0; }; const XString8& dgetCustomLogoAsXString8() const { return CustomLogo.xmlString8.isDefined() ? CustomLogo.xmlString8.value() : NullXString8; }; const XBuffer& dgetCustomLogoAsData() const { return CustomLogo.xmlData.isDefined() ? CustomLogo.xmlData.value() : XBuffer::NullXBuffer; }; /* calculated values */ XBool dgetLastBootedVolume() const { return DefaultVolume.isDefined() ? DefaultVolume.value() == "LastBootedVolume"_XS8 : false; } UINT8 dgetCustomLogoType() const { if ( CustomLogo.xmlBool.isDefined() ) return CustomLogo.xmlBool.value() ? CUSTOM_BOOT_APPLE : CUSTOM_BOOT_USER_DISABLED; if ( CustomLogo.xmlString8.isDefined() ) { if ( CustomLogo.xmlString8.value() == "Apple"_XS8 ) return CUSTOM_BOOT_APPLE; if ( CustomLogo.xmlString8.value() == "Alternate"_XS8 ) return CUSTOM_BOOT_ALT_APPLE; if ( CustomLogo.xmlString8.value() == "Theme"_XS8 ) return CUSTOM_BOOT_THEME; return CUSTOM_BOOT_USER; } if ( CustomLogo.xmlData.isDefined() ) { return CUSTOM_BOOT_USER; } return CUSTOM_BOOT_DISABLED; } /**/ virtual void reset() override { super::reset(); }; private: }; #endif /* _CONFIGPLISTCLASS_Boot_H_ */