Changeset 86659 in vbox
- Timestamp:
- Oct 20, 2020 6:28:06 PM (4 years ago)
- svn:sync-xref-src-repo-rev:
- 141035
- Location:
- trunk/src/VBox/Main
- Files:
-
- 7 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Main/UnattendedTemplates/ol_ks.cfg
r86650 r86659 82 82 glibc-headers 83 83 gcc 84 @@VBOX_ GUEST_OS_COND_VERSION@@**8.0.0**84 @@VBOX_COND_GUEST_VERSION[>8.0.0]@@ 85 85 elfutils-libelf-devel 86 @@VBOX_ GUEST_OS_COND_END@@86 @@VBOX_COND_END@@ 87 87 dkms 88 88 make -
trunk/src/VBox/Main/UnattendedTemplates/ol_postinstall.sh
r86650 r86659 202 202 log_command_in_target yum -y install binutils 203 203 log_command_in_target yum -y install make 204 @@VBOX_ GUEST_OS_COND_VERSION@@**8.0.0**204 @@VBOX_COND_GUEST_VERSION[>8.0.0]@@ 205 205 log_command_in_target yum -y install elfutils-libelf-devel 206 @@VBOX_ GUEST_OS_COND_END@@206 @@VBOX_COND_END@@ 207 207 log_command_in_target yum -y install dkms 208 208 log_command_in_target yum -y install make -
trunk/src/VBox/Main/UnattendedTemplates/redhat67_ks.cfg
r86650 r86659 82 82 glibc-headers 83 83 gcc 84 @@VBOX_ GUEST_OS_COND_VERSION@@**8.0.0**84 @@VBOX_COND_GUEST_VERSION[>8.0.0]@@ 85 85 elfutils-libelf-devel 86 @@VBOX_ GUEST_OS_COND_END@@86 @@VBOX_COND_END@@ 87 87 dkms 88 88 make -
trunk/src/VBox/Main/UnattendedTemplates/redhat_postinstall.sh
r86650 r86659 178 178 log_command_in_target yum -y install binutils 179 179 log_command_in_target yum -y install make 180 @@VBOX_ GUEST_OS_COND_VERSION@@**8.0.0**180 @@VBOX_COND_GUEST_VERSION[>8.0.0]@@ 181 181 log_command_in_target yum -y install elfutils-libelf-devel 182 @@VBOX_ GUEST_OS_COND_END@@182 @@VBOX_COND_END@@ 183 183 log_command_in_target yum -y install dkms 184 184 log_command_in_target yum -y install make -
trunk/src/VBox/Main/include/UnattendedInstaller.h
r86650 r86659 520 520 /** 521 521 * RHEL 7 installer (same as RHEL 6). 522 * The class was added for better handling any possible subtle difference between RHEL6 and RHEL7. 522 523 */ 523 524 class UnattendedRhel7Installer : public UnattendedRhel6Installer … … 540 541 /** 541 542 * RHEL 8 installer (same as RHEL 7). 543 * The class was added for better handling any possible subtle difference between RHEL7 and RHEL8. 542 544 */ 543 545 class UnattendedRhel8Installer : public UnattendedRhel7Installer … … 605 607 606 608 /** 607 * Oracle Linux 6 installer. 609 * Oracle Linux 6 installer. Same as RHEL 6, except for the templates. 610 * The reason of adding new class is to sepatate the RHEL from OL. 608 611 */ 609 612 class UnattendedOracleLinux6Installer : public UnattendedRhel6Installer … … 621 624 622 625 /** 623 * Oracle Linux 7 installer. 626 * Oracle Linux 7 installer. Same as OL 6. 627 * The class was added for better handling any possible subtle difference between OL6 and OL7. 624 628 */ 625 629 class UnattendedOracleLinux7Installer : public UnattendedOracleLinux6Installer … … 641 645 642 646 /** 643 * Oracle Linux 8 installer. 647 * Oracle Linux 8 installer. Same as OL 7. 648 * The class was added for better handling any possible subtle difference between OL7 and OL8. 644 649 */ 645 650 class UnattendedOracleLinux8Installer : public UnattendedOracleLinux7Installer -
trunk/src/VBox/Main/include/UnattendedScript.h
r86650 r86659 96 96 virtual HRESULT getConditional(const char *pachPlaceholder, size_t cchPlaceholder, bool *pfOutputting); 97 97 98 99 /**100 * Get the result of a conditional for special version of guest OS.101 *102 * @returns COM status code.103 * @param pachPlaceholder The placholder string. Not zero terminated.104 * @param cchPlaceholder The length of the placeholder.105 * @param cchContent The length of placeholder content.106 * @param pcchCorrect The length of part which must be excluded from the final content of107 * the placeholder.108 * @param pfOutputting Where to return the result of the conditional.109 * This holds the current outputting state on input110 * in case someone want to sanity check anything.111 */112 virtual HRESULT getGuestOSConditional(const char *pachPlaceholder,113 size_t cchPlaceholder,114 size_t cchContent,115 size_t *pcchCorrect,116 bool *pfOutputting);117 98 }; 118 99 -
trunk/src/VBox/Main/src-server/UnattendedScript.cpp
r86650 r86659 59 59 static const char s_szPrefixCond[] = "@@VBOX_COND_"; 60 60 static const char s_szPrefixCondEnd[] = "@@VBOX_COND_END@@"; 61 static const char s_szPrefixCondGuestOs[] = "@@VBOX_GUEST_OS_COND_";62 static const char s_szPrefixCondGuestOsEnd[] = "@@VBOX_GUEST_OS_COND_END@@";63 61 64 62 struct … … 71 69 size_t offTemplate = 0; 72 70 size_t cchTemplate = mStrScriptFullContent.length(); 73 size_t cchInternalCorrect = 0;//used in logic handling the placeholder @@VBOX_GUEST_OS_COND_XXX@@74 71 rStrDst.setNull(); 75 72 for (;;) … … 86 83 try 87 84 { 88 rStrDst.append(mStrScriptFullContent, offTemplate + cchInternalCorrect, cchToCopy - + cchInternalCorrect);85 rStrDst.append(mStrScriptFullContent, offTemplate , cchToCopy); 89 86 } 90 87 catch (std::bad_alloc &) … … 95 92 } 96 93 offTemplate += cchToCopy; 97 cchInternalCorrect = 0;//don't forget to reset98 94 } 99 95 … … 112 108 && (ch = pszPlaceholder[cchPlaceholder]) != '\0' 113 109 && ( ch == '_' 110 || ch == '[' 111 || ch == ']' 112 || ch == '.' 113 || ch == '>' 114 || ch == '<' 114 115 || RT_C_IS_UPPER(ch) 115 116 || RT_C_IS_DIGIT(ch)) ) … … 128 129 || pszPlaceholder[cchPlaceholder - 2] != '@' 129 130 || ( strncmp(pszPlaceholder, s_szPrefixInsert, sizeof(s_szPrefixInsert) - 1) != 0 130 && strncmp(pszPlaceholder, s_szPrefixCond, sizeof(s_szPrefixCond) - 1) != 0 131 && strncmp(pszPlaceholder, s_szPrefixCondGuestOs, sizeof(s_szPrefixCondGuestOs) - 1) != 0) ) 131 && strncmp(pszPlaceholder, s_szPrefixCond, sizeof(s_szPrefixCond) - 1) != 0 ) ) 132 132 { 133 133 hrc = mpSetError->setError(E_FAIL, mpSetError->tr("Malformed template placeholder '%.*s'"), … … 188 188 * one from the condition. 189 189 */ 190 else if ( strncmp(pszPlaceholder, s_szPrefixCond, sizeof(s_szPrefixCond) - 1U) == 0 ) 191 { 190 else 191 { 192 Assert(strncmp(pszPlaceholder, s_szPrefixCond, sizeof(s_szPrefixCond) - 1) == 0); 192 193 if (cConds + 1 < RT_ELEMENTS(aConds)) 193 194 { … … 195 196 bool fNewOutputting = fOutputting; 196 197 hrc = getConditional(pszPlaceholder, cchPlaceholder, &fNewOutputting); 197 if (SUCCEEDED(hrc))198 fOutputting = fOutputting && fNewOutputting;199 else200 break;201 cConds++;202 }203 else204 {205 hrc = mpSetError->setErrorBoth(E_FAIL, VERR_PARSE_ERROR,206 mpSetError->tr("Too deep conditional nesting at offset %zu (%#zx)"),207 offPlaceholder, offPlaceholder);208 break;209 }210 }211 /*212 * @@VBOX_GUEST_OS_COND_END@@: Pop one item of the conditional stack.213 */214 else if ( strncmp(pszPlaceholder, s_szPrefixCondGuestOsEnd, sizeof(s_szPrefixCondGuestOsEnd) - 1U) == 0 )215 {216 if (cConds > 0)217 {218 cConds--;219 fOutputting = aConds[cConds].fSavedOutputting;220 }221 else222 {223 hrc = mpSetError->setErrorBoth(E_FAIL, VERR_PARSE_ERROR,224 mpSetError->tr("%s without @@VBOX_GUEST_OS_COND_XXX@@ at offset %zu (%#zx)"),225 s_szPrefixCondGuestOsEnd, offPlaceholder, offPlaceholder);226 break;227 }228 }229 /*230 * @@VBOX_GUEST_OS_COND_XXX@@: Push the previous outputting state and combine it with the231 * one from the condition.232 */233 else234 {235 Assert(strncmp(pszPlaceholder, s_szPrefixCondGuestOs, sizeof(s_szPrefixCondGuestOs) - 1) == 0);236 if (cConds + 1 < RT_ELEMENTS(aConds))237 {238 aConds[cConds].fSavedOutputting = fOutputting;239 bool fNewOutputting = fOutputting;240 241 //offTemplate is the beginning of content, offEndContent is the end of content242 //@@PLACEHOLDER_BEGIN@@Content@@PLACEHOLDER_END@@243 // ^ ^244 // | |245 // offTemplate offEndContent246 size_t offEndContent = mStrScriptFullContent.find(s_szPrefix, offTemplate);247 size_t cchContent = offEndContent - offTemplate - 1;248 hrc = getGuestOSConditional(pszPlaceholder, cchPlaceholder, cchContent, &cchInternalCorrect, &fNewOutputting);249 198 if (SUCCEEDED(hrc)) 250 199 fOutputting = fOutputting && fNewOutputting; … … 499 448 } 500 449 501 HRESULT UnattendedScriptTemplate::getGuestOSConditional(const char *pachPlaceholder,502 size_t cchPlaceholder,503 size_t cchContent,504 size_t *cchCorrect,505 bool *pfOutputting)506 {507 #define IS_PLACEHOLDER_MATCH(a_szMatch) \508 ( cchPlaceholder == sizeof("@@VBOX_GUEST_OS_COND_" a_szMatch "@@") - 1U \509 && memcmp(pachPlaceholder, "@@VBOX_GUEST_OS_COND_" a_szMatch "@@", sizeof("@@VBOX_GUEST_OS_COND_" a_szMatch "@@") - 1U) == 0)510 511 if ( IS_PLACEHOLDER_MATCH("VERSION") )512 {513 Utf8Str strT(pachPlaceholder + cchPlaceholder, cchContent);514 RTCList<RTCString> partList = strT.split("**");515 Utf8Str strRequiredOSVersion;516 if (partList.size() == 2)//when the version is placed together with the placeholder in one line in the file517 {518 //The case when the string has been splitted on the 2 parts:519 //1. OS version520 //2. Actual content521 strRequiredOSVersion.assign(partList.at(0));522 //cchCorrect = "**" + length of OS version string + "**"523 *cchCorrect = 2 + partList.at(0).length() + 2;// must be subtracted from the cchContent524 }525 else if (partList.size() == 3)//when the version is placed on a standalone line in the file526 {527 //The case when the string has been splitted on the 3 parts:528 //1. Empty string or string with only "\n"529 //2. OS version530 //3. Actual content531 strRequiredOSVersion.assign(partList.at(1));532 *cchCorrect = 2 + partList.at(0).length() + partList.at(1).length() + 2;// must be subtracted from the cchContent533 }534 else//case with wrong string syntax535 {536 *cchCorrect = 0;537 *pfOutputting = false;538 LogRel(("Malformed content of the template @@VBOX_GUEST_OS_COND_VERSION@@\n"));539 return S_OK;540 }541 542 if (strRequiredOSVersion.isEmpty())543 *pfOutputting = false;544 else545 {546 Utf8Str strDetectedOSVersion = mpUnattended->i_getDetectedOSVersion();547 RTCList<RTCString> partListRequired = strRequiredOSVersion.split(".");548 RTCList<RTCString> partListDetected = strDetectedOSVersion.split(".");549 *pfOutputting = false;//initially is set to "false"550 551 /** @todo r=vvp: Should we check the string with a requested OS version for digits?552 * (with RTLocCIsDigit()) */553 //Major version must be presented554 if ( partListDetected.at(0).toUInt32() >= partListRequired.at(0).toUInt32() )//comparison major versions555 {556 //OS major versions are equal or detected guest OS major version is greater. Go further.557 if (partListDetected.size() > 1 && partListRequired.size() > 1)//comparison minor versions558 {559 if (partListDetected.at(1).toUInt32() >= partListRequired.at(1).toUInt32())560 //OS minor versions are equal or detected guest OS minor version is greater. Go further.561 *pfOutputting = true;562 else563 //The detected guest OS minor version is less than the requested one.564 *pfOutputting = false;565 }566 else567 //OS minor versions are absent.568 *pfOutputting = true;569 }570 else571 //The detected guest OS major version is less than the requested one.572 *pfOutputting = false;573 }574 }575 else576 return mpSetError->setErrorBoth(E_FAIL, VERR_NOT_FOUND, mpSetError->tr("Unknown conditional placeholder '%.*s'"),577 cchPlaceholder, pachPlaceholder);578 return S_OK;579 #undef IS_PLACEHOLDER_MATCH580 }581 582 450 HRESULT UnattendedScriptTemplate::getConditional(const char *pachPlaceholder, size_t cchPlaceholder, bool *pfOutputting) 583 451 { … … 585 453 ( cchPlaceholder == sizeof("@@VBOX_COND_" a_szMatch "@@") - 1U \ 586 454 && memcmp(pachPlaceholder, "@@VBOX_COND_" a_szMatch "@@", sizeof("@@VBOX_COND_" a_szMatch "@@") - 1U) == 0) 455 #define IS_PLACEHOLDER_PARTIALLY_MATCH(a_szMatch) \ 456 (memcmp(pachPlaceholder, "@@VBOX_COND_" a_szMatch, sizeof("@@VBOX_COND_" a_szMatch) - 1U) == 0) 587 457 588 458 /* Install Guest Additions: */ … … 623 493 else if (IS_PLACEHOLDER_MATCH("HAS_PROXY")) 624 494 *pfOutputting = mpUnattended->i_getProxy().isNotEmpty(); 495 else if (IS_PLACEHOLDER_PARTIALLY_MATCH("GUEST_VERSION")) 496 { 497 //parse the placeholder and extract the OS version from there 498 RTCString strPlaceHolder(pachPlaceholder); 499 size_t startPos = sizeof("@@VBOX_COND_GUEST_VERSION") - 1;//-1 is for '\n' 500 size_t endPos = strPlaceHolder.find("@@", startPos + 2); 501 //next part should look like [>8.0.0] for example where: 502 // - "[,]" is just the brackets to wrap up the condition; 503 // - ">" is "greater". Also possible comparison is "<"; 504 // - 8.0.0 is required guest OS version. 505 //The end of placeholder is "@@" like for others. 506 507 if ( strPlaceHolder[endPos] == '@' 508 && strPlaceHolder[endPos+1] == '@' ) 509 { 510 if ( strPlaceHolder[startPos++] == '[' && strPlaceHolder[--endPos] == ']' ) 511 { 512 char chComp = strPlaceHolder[startPos++]; 513 RTCString strRequiredOSVersion = strPlaceHolder.substr(startPos, endPos - startPos); 514 RTCString strDetectedOSVersion = mpUnattended->i_getDetectedOSVersion(); 515 int res = RTStrVersionCompare(strDetectedOSVersion.c_str(), strRequiredOSVersion.c_str()); 516 if ( res >= 0 && chComp == '>' ) 517 *pfOutputting = true; 518 else if ( res < 0 && chComp == '<' ) 519 *pfOutputting = true; 520 else 521 *pfOutputting = false; 522 } 523 } 524 else 525 *pfOutputting = false;//initially is set to "false" 526 } 625 527 else 626 528 return mpSetError->setErrorBoth(E_FAIL, VERR_NOT_FOUND, mpSetError->tr("Unknown conditional placeholder '%.*s'"),
Note:
See TracChangeset
for help on using the changeset viewer.