diff --git a/SandboxiePlus/SandMan/Wizards/NewBoxWizard.cpp b/SandboxiePlus/SandMan/Wizards/NewBoxWizard.cpp index b798ba55..e0bd42e1 100644 --- a/SandboxiePlus/SandMan/Wizards/NewBoxWizard.cpp +++ b/SandboxiePlus/SandMan/Wizards/NewBoxWizard.cpp @@ -95,125 +95,87 @@ SB_STATUS CNewBoxWizard::TryToCreateBox() if (!Status.IsError()) { CSandBoxPtr pBox = theAPI->GetBoxByName(BoxName); - - switch (BoxType) - { - case CSandBoxPlus::eHardenedPlus: - pBox->SetBool("UsePrivacyMode", true); - case CSandBoxPlus::eHardened: - pBox->SetBool("UseSecurityMode", true); - break; - - case CSandBoxPlus::eDefaultPlus: - pBox->SetBool("UsePrivacyMode", true); - case CSandBoxPlus::eDefault: - break; - - case CSandBoxPlus::eAppBoxPlus: - pBox->SetBool("UsePrivacyMode", true); - case CSandBoxPlus::eAppBox: - pBox->SetBool("NoSecurityIsolation", true); - //pBox->InsertText("Template", "NoUACProxy"); // proxy is always needed for exes in the box - pBox->InsertText("Template", "RpcPortBindingsExt"); - break; - } - - if (BlackBox) { - pBox->SetBool("UseFileImage", true); - pBox->SetBool("ConfidentialBox", true); - } - - QRgb rgb = theGUI->GetBoxColor(BoxType); - pBox->SetText("BorderColor", QString("#%1%2%3").arg(qBlue(rgb), 2, 16, QChar('0')).arg(qGreen(rgb), 2, 16, QChar('0')).arg(qRed(rgb), 2, 16, QChar('0')) + ",ttl"); - - - QString Location = field("boxLocation").toString(); - if (!Location.isEmpty()) { - pBox->SetText("FileRootPath", Location); - theAPI->UpdateBoxPaths(pBox.data()); - } - - if (field("boxVersion").toInt() == 1) { - pBox->SetBool("UseFileDeleteV2", true); - pBox->SetBool("UseRegDeleteV2", true); - } - if(!field("separateUser").toBool()) - pBox->SetBool("SeparateUserFolders", false); - if(field("useVolumeSN").toBool()) - pBox->SetBool("UseVolumeSerialNumbers", true); - - if (field("autoRemove").toBool()) { - pBox->SetBool("AutoDelete", true); - pBox->SetBool("AutoRemove", true); - } - else if(field("autoDelete").toBool()) - pBox->SetBool("AutoDelete", true); - if(field("autoRecover").toBool()) - pBox->SetBool("AutoRecover", true); - - if (field("blockNetwork").toInt() == 1) { // device based - //pBox->InsertText("AllowNetworkAccess", ",n"); - pBox->InsertText("ClosedFilePath", "!,InternetAccessDevices"); - //pBox->InsertText("ClosedFilePath", ",InternetAccessDevices"); - } - else if (field("blockNetwork").toInt() == 2) { // using WFP - pBox->InsertText("AllowNetworkAccess", "!,n"); - //pBox->InsertText("AllowNetworkAccess", ",n"); - //pBox->InsertText("ClosedFilePath", ",InternetAccessDevices"); - } - pBox->SetBool("BlockNetworkFiles", !field("shareAccess").toBool()); - - if (field("fakeAdmin").toBool()) { - pBox->SetBool("DropAdminRights", true); - pBox->SetBool("FakeAdminRights", true); - } - if(field("msiServer").toBool()) - pBox->SetBool("MsiInstallerExemptions", true); - - if(field("boxToken").toBool()) - pBox->SetBool("SandboxieLogon", true); - - if(field("imagesProtection").toBool()) - pBox->SetBool("ProtectHostImages", true); - + // SharedTemplate + const QString TEMPLATE_PREFIX = "Template_Local_"; + const QString DISABLE_WIZARD_SETTINGS = "#DisableWizardSettings"; + const QString REMOVE_DEFAULT_ALL = "#RemoveDefaultAll"; + const QString REMOVE_DEFAULT_RECOVERS = "#RemoveDefaultRecovers"; + const QString REMOVE_DEFAULT_TEMPLATES = "#RemoveDefaultTemplates"; + const QString ENABLED_PREFIX = "Enabled="; + const QString CFGLVL_PREFIX = "ConfigLevel="; + const QString TMPL_PREFIX = "Tmpl."; + const QString BOX_DISABLED_SUFFIX = "Disabled"; + const QStringList SPECIAL_SETTINGS = { "BorderColor", "BoxIcon", "BoxNameTitle", "ConfigLevel", "CopyLimitKb" }; + QString templateName = "SharedTemplate"; - QString templateFullName = QString("Template_Local_%1").arg(templateName); + QString templateFullName = TEMPLATE_PREFIX + templateName; QString templateSettings = theAPI->SbieIniGetEx(templateFullName, ""); QString templateComment = tr("Add your settings after this line."); - if (templateSettings.isNull()) { - QString templateBase = QString("Tmpl.Title=%1\r\nTmpl.Class=Local\r\nTmpl.Comment=%2\r\n").arg(templateName, templateComment); + bool disableWizardSettings = templateSettings.contains(DISABLE_WIZARD_SETTINGS + "=y"); + bool removeDefaultAll = templateSettings.contains(REMOVE_DEFAULT_ALL + "=y"); + bool removeDefaultRecovers = templateSettings.contains(REMOVE_DEFAULT_RECOVERS + "=y"); + bool removeDefaultTemplates = templateSettings.contains(REMOVE_DEFAULT_TEMPLATES + "=y"); + + // Create base template + if (templateSettings.isEmpty()) { + QString templateBase = QStringLiteral("Tmpl.Title=%1\nTmpl.Class=Local\n%3=y\n%4=n\n%5=n\n%6=n\nTmpl.Comment=%2") + .arg(templateName, templateComment, DISABLE_WIZARD_SETTINGS, REMOVE_DEFAULT_ALL, REMOVE_DEFAULT_RECOVERS, REMOVE_DEFAULT_TEMPLATES); theAPI->SbieIniSet(templateFullName, "", templateBase); } - if (field("sharedTemplate").toInt() == 1) { // insert template + QString boxSettings = theAPI->SbieIniGetEx(BoxName, ""); + QStringList boxSettingsLines = boxSettings.split("\n", Qt::SkipEmptyParts); + + int sharedTemplateType = field("sharedTemplate").toInt(); + switch (sharedTemplateType) + { + case 0: + case 1: + case 2: + // Remove default settings + if (removeDefaultRecovers || removeDefaultAll) { + pBox->DelValue("RecoverFolder"); + } + if (removeDefaultTemplates || removeDefaultAll) { + pBox->DelValue("Template"); + } + if (removeDefaultAll) { + for (const QString& bLine : boxSettingsLines) { + QStringList bParts = bLine.split("=", Qt::SkipEmptyParts); + if (bParts.size() == 2) { + QString bKey = bParts[0].trimmed(); + QString bValue = bParts[1].trimmed(); + if (!bLine.startsWith(ENABLED_PREFIX) && !bLine.startsWith(CFGLVL_PREFIX)) { // Do not remove Enabled and ConfigLevel + pBox->DelValue(bKey, bValue); + } + } + } + } + break; + default: + // Default case + break; + } + if (sharedTemplateType == 1) { // Insert template QString insertValue = templateFullName.replace("Template_", ""); pBox->InsertText("Template", insertValue); } - else if (field("sharedTemplate").toInt() == 2) { // append to config - QStringList templateSettingsLines = templateSettings.split("\r\n", Qt::SkipEmptyParts); - - for (const QString& tLine : templateSettingsLines) { - if (tLine.startsWith("Enabled=") || - tLine.startsWith("ConfigLevel=") || - tLine.startsWith("Tmpl.") || - tLine.startsWith("#")) { - continue; // Skip lines that start with these prefixes - } - - QStringList tParts = tLine.split('='); + else if (sharedTemplateType == 2) { // Append to config + for (const QString& tLine : templateSettings.split("\n", Qt::SkipEmptyParts)) { + QStringList tParts = tLine.split("=", Qt::SkipEmptyParts); if (tParts.size() != 2) { continue; // Skip lines that don't have exactly one '=' character } - QString tKey = tParts[0].trimmed(); QString tValue = tParts[1].trimmed(); - if (tLine.endsWith("=y") || - tLine.endsWith("=Y") || - tLine.endsWith("=n") || - tLine.endsWith("=N")) { + if (tKey.startsWith(ENABLED_PREFIX) || tKey.startsWith(TMPL_PREFIX) || tKey.startsWith("#") || tKey.endsWith(BOX_DISABLED_SUFFIX)) { + continue; // Skip lines that start or end with one of these + } + + if (tValue.compare("y", Qt::CaseInsensitive) == 0 || tValue.compare("n", Qt::CaseInsensitive) == 0 || SPECIAL_SETTINGS.contains(tKey)) { pBox->SetText(tKey, tValue); } else { @@ -221,24 +183,106 @@ SB_STATUS CNewBoxWizard::TryToCreateBox() } } } - - if (!Password.isEmpty()) - pBox->ImBoxCreate(ImageSize / 1024, Password); - - if (field("boxVersion").toInt() == 1) { - if (theConf->GetBool("Options/WarnDeleteV2", true)) { - bool State = false; - CCheckableMessageBox::question(this, "Sandboxie-Plus", - tr("The new sandbox has been created using the new Virtualization Scheme Version 2, if you experience any unexpected issues with this box," - " please switch to the Virtualization Scheme to Version 1 and report the issue," - " the option to change this preset can be found in the Box Options in the Box Structure group.") - , tr("Don't show this message again."), &State, QDialogButtonBox::Ok, QDialogButtonBox::Ok, QMessageBox::Information); - - if (State) - theConf->SetValue("Options/WarnDeleteV2", false); + // + if (!disableWizardSettings) { + switch (BoxType) + { + case CSandBoxPlus::eHardenedPlus: + pBox->SetBool("UsePrivacyMode", true); + case CSandBoxPlus::eHardened: + pBox->SetBool("UseSecurityMode", true); + break; + + case CSandBoxPlus::eDefaultPlus: + pBox->SetBool("UsePrivacyMode", true); + case CSandBoxPlus::eDefault: + break; + + case CSandBoxPlus::eAppBoxPlus: + pBox->SetBool("UsePrivacyMode", true); + case CSandBoxPlus::eAppBox: + pBox->SetBool("NoSecurityIsolation", true); + //pBox->InsertText("Template", "NoUACProxy"); // proxy is always needed for exes in the box + pBox->InsertText("Template", "RpcPortBindingsExt"); + break; + } + + if (BlackBox) { + pBox->SetBool("UseFileImage", true); + pBox->SetBool("ConfidentialBox", true); + } + + QRgb rgb = theGUI->GetBoxColor(BoxType); + pBox->SetText("BorderColor", QString("#%1%2%3").arg(qBlue(rgb), 2, 16, QChar('0')).arg(qGreen(rgb), 2, 16, QChar('0')).arg(qRed(rgb), 2, 16, QChar('0')) + ",ttl"); + + + QString Location = field("boxLocation").toString(); + if (!Location.isEmpty()) { + pBox->SetText("FileRootPath", Location); + theAPI->UpdateBoxPaths(pBox.data()); + } + + if (field("boxVersion").toInt() == 1) { + pBox->SetBool("UseFileDeleteV2", true); + pBox->SetBool("UseRegDeleteV2", true); + } + if(!field("separateUser").toBool()) + pBox->SetBool("SeparateUserFolders", false); + if(field("useVolumeSN").toBool()) + pBox->SetBool("UseVolumeSerialNumbers", true); + + if (field("autoRemove").toBool()) { + pBox->SetBool("AutoDelete", true); + pBox->SetBool("AutoRemove", true); + } + else if(field("autoDelete").toBool()) + pBox->SetBool("AutoDelete", true); + if(field("autoRecover").toBool()) + pBox->SetBool("AutoRecover", true); + + if (field("blockNetwork").toInt() == 1) { // device based + //pBox->InsertText("AllowNetworkAccess", ",n"); + pBox->InsertText("ClosedFilePath", "!,InternetAccessDevices"); + //pBox->InsertText("ClosedFilePath", ",InternetAccessDevices"); + } + else if (field("blockNetwork").toInt() == 2) { // using WFP + pBox->InsertText("AllowNetworkAccess", "!,n"); + //pBox->InsertText("AllowNetworkAccess", ",n"); + //pBox->InsertText("ClosedFilePath", ",InternetAccessDevices"); + } + pBox->SetBool("BlockNetworkFiles", !field("shareAccess").toBool()); + + if (field("fakeAdmin").toBool()) { + pBox->SetBool("DropAdminRights", true); + pBox->SetBool("FakeAdminRights", true); + } + if(field("msiServer").toBool()) + pBox->SetBool("MsiInstallerExemptions", true); + + if(field("boxToken").toBool()) + pBox->SetBool("SandboxieLogon", true); + + if(field("imagesProtection").toBool()) + pBox->SetBool("ProtectHostImages", true); + + if (!Password.isEmpty()) + pBox->ImBoxCreate(ImageSize / 1024, Password); + + if (field("boxVersion").toInt() == 1) { + if (theConf->GetBool("Options/WarnDeleteV2", true)) { + bool State = false; + CCheckableMessageBox::question(this, "Sandboxie-Plus", + tr("The new sandbox has been created using the new Virtualization Scheme Version 2, if you experience any unexpected issues with this box," + " please switch to the Virtualization Scheme to Version 1 and report the issue," + " the option to change this preset can be found in the Box Options in the Box Structure group.") + , tr("Don't show this message again."), &State, QDialogButtonBox::Ok, QDialogButtonBox::Ok, QMessageBox::Information); + + if (State) + theConf->SetValue("Options/WarnDeleteV2", false); + } } } - } + } return Status; }