This commit is contained in:
parent
a59698b0eb
commit
418d095d24
|
@ -15,6 +15,7 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
|||
### Added
|
||||
- added hwid display
|
||||
- added Language Spoof "CustomLCID=1033" [#4024](https://github.com/sandboxie-plus/Sandboxie/pull/4024) (thanks Yeyixiao)
|
||||
- added option to always run the sandman UI as admin [#4090](https://github.com/sandboxie-plus/Sandboxie/issues/4090)
|
||||
|
||||
### Fixed
|
||||
- fixed Getting two advanced supporter certificate popups everytime I open Sandbox Settings on any sandbox [#4074](https://github.com/sandboxie-plus/Sandboxie/issues/4074)
|
||||
|
|
|
@ -2196,7 +2196,41 @@ Unlike the preview channel, it does not include untested, potentially breaking,
|
|||
<string>Sandboxie.ini Presets</string>
|
||||
</attribute>
|
||||
<layout class="QGridLayout" name="gridLayout_19">
|
||||
<item row="7" column="0">
|
||||
<item row="6" column="2" colspan="2">
|
||||
<widget class="QCheckBox" name="chkAdminOnlyFP">
|
||||
<property name="text">
|
||||
<string>Only Administrator user accounts can use Pause Forcing Programs command</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="8" column="2">
|
||||
<spacer name="horizontalSpacer_24">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="0" column="2">
|
||||
<widget class="QCheckBox" name="chkWatchConfig">
|
||||
<property name="text">
|
||||
<string>Watch Sandboxie.ini for changes</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="2">
|
||||
<widget class="QCheckBox" name="chkAdminOnly">
|
||||
<property name="text">
|
||||
<string>Only Administrator user accounts can make changes</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="8" column="0">
|
||||
<spacer name="verticalSpacer_7">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Vertical</enum>
|
||||
|
@ -2209,46 +2243,10 @@ Unlike the preview channel, it does not include untested, potentially breaking,
|
|||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="6" column="2">
|
||||
<widget class="QCheckBox" name="chkClearPass">
|
||||
<property name="text">
|
||||
<string>Clear password when main window becomes hidden</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="5" column="2" colspan="2">
|
||||
<widget class="QCheckBox" name="chkAdminOnlyFP">
|
||||
<property name="text">
|
||||
<string>Only Administrator user accounts can use Pause Forcing Programs command</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="2">
|
||||
<widget class="QCheckBox" name="chkWatchConfig">
|
||||
<property name="text">
|
||||
<string>Watch Sandboxie.ini for changes</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="3" rowspan="2">
|
||||
<widget class="QPushButton" name="btnSetPassword">
|
||||
<property name="text">
|
||||
<string>Change Password</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="2">
|
||||
<widget class="QCheckBox" name="chkAdminOnly">
|
||||
<property name="text">
|
||||
<string>Only Administrator user accounts can make changes</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0" colspan="2">
|
||||
<item row="2" column="0" colspan="2">
|
||||
<widget class="QLabel" name="lblProtection">
|
||||
<property name="font">
|
||||
<font>
|
||||
<weight>75</weight>
|
||||
<bold>true</bold>
|
||||
<kerning>true</kerning>
|
||||
</font>
|
||||
|
@ -2258,25 +2256,33 @@ Unlike the preview channel, it does not include untested, potentially breaking,
|
|||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="2">
|
||||
<item row="7" column="2">
|
||||
<widget class="QCheckBox" name="chkClearPass">
|
||||
<property name="text">
|
||||
<string>Clear password when main window becomes hidden</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="4" column="2">
|
||||
<widget class="QCheckBox" name="chkPassRequired">
|
||||
<property name="text">
|
||||
<string>Password must be entered in order to make changes</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="7" column="2">
|
||||
<spacer name="horizontalSpacer_24">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
<item row="4" column="3" rowspan="2">
|
||||
<widget class="QPushButton" name="btnSetPassword">
|
||||
<property name="text">
|
||||
<string>Change Password</string>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="2">
|
||||
<widget class="QCheckBox" name="chkSkipUAC">
|
||||
<property name="text">
|
||||
<string>Always run SandMan UI as Admin</string>
|
||||
</property>
|
||||
</spacer>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
|
|
|
@ -164,4 +164,336 @@ bool AutorunEnable (bool is_enable)
|
|||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
// Skip UAC
|
||||
|
||||
#define SKIP_UAC_TASK_NAME APP_NAME L"_SkipUac"
|
||||
|
||||
#include <comdef.h>
|
||||
#include <taskschd.h>
|
||||
|
||||
struct MBSTR
|
||||
{
|
||||
MBSTR (LPCWSTR asString = nullptr)
|
||||
{
|
||||
ms_bstr = asString ? SysAllocString (asString) : nullptr;
|
||||
}
|
||||
|
||||
~MBSTR ()
|
||||
{
|
||||
Free ();
|
||||
}
|
||||
|
||||
operator BSTR() const
|
||||
{
|
||||
return ms_bstr;
|
||||
}
|
||||
|
||||
MBSTR& operator=(LPCWSTR asString)
|
||||
{
|
||||
if (asString != ms_bstr)
|
||||
{
|
||||
Free ();
|
||||
ms_bstr = asString ? ::SysAllocString (asString) : NULL;
|
||||
}
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
void Free ()
|
||||
{
|
||||
if (ms_bstr)
|
||||
{
|
||||
SysFreeString (ms_bstr);
|
||||
ms_bstr = nullptr;
|
||||
}
|
||||
}
|
||||
protected:
|
||||
BSTR ms_bstr;
|
||||
};
|
||||
|
||||
bool SkipUacEnable (bool is_enable)
|
||||
{
|
||||
bool result = false;
|
||||
bool action_result = false;
|
||||
|
||||
ITaskService* service = nullptr;
|
||||
ITaskFolder* folder = nullptr;
|
||||
ITaskDefinition* task = nullptr;
|
||||
IRegistrationInfo* reginfo = nullptr;
|
||||
IPrincipal* principal = nullptr;
|
||||
ITaskSettings* settings = nullptr;
|
||||
IActionCollection* action_collection = nullptr;
|
||||
IAction* action = nullptr;
|
||||
IExecAction* exec_action = nullptr;
|
||||
IRegisteredTask* registered_task = nullptr;
|
||||
|
||||
wchar_t szPath[MAX_PATH];
|
||||
if (!GetModuleFileName(NULL, szPath, ARRAYSIZE(szPath)))
|
||||
return false;
|
||||
std::wstring::size_type pos = std::wstring(szPath).find_last_of( L"\\/" );
|
||||
std::wstring dir = std::wstring(szPath).substr(0, pos);
|
||||
|
||||
MBSTR root (L"\\");
|
||||
MBSTR name (SKIP_UAC_TASK_NAME);
|
||||
MBSTR author (APP_NAME);
|
||||
MBSTR path (szPath);
|
||||
MBSTR directory (dir.c_str());
|
||||
MBSTR args (L"$(Arg0)");
|
||||
MBSTR timelimit (L"PT0S");
|
||||
|
||||
VARIANT vtEmpty = {VT_EMPTY};
|
||||
|
||||
if (SUCCEEDED (CoInitializeEx (nullptr, COINIT_APARTMENTTHREADED)))
|
||||
{
|
||||
//if (SUCCEEDED (CoInitializeSecurity (nullptr, -1, nullptr, nullptr, RPC_C_AUTHN_LEVEL_PKT_PRIVACY, RPC_C_IMP_LEVEL_IMPERSONATE, nullptr, 0, nullptr)))
|
||||
{
|
||||
if (SUCCEEDED (CoCreateInstance (CLSID_TaskScheduler, nullptr, CLSCTX_INPROC_SERVER, IID_ITaskService, (LPVOID*)&service)))
|
||||
{
|
||||
if (SUCCEEDED (service->Connect (vtEmpty, vtEmpty, vtEmpty, vtEmpty)))
|
||||
{
|
||||
if (SUCCEEDED (service->GetFolder (root, &folder)))
|
||||
{
|
||||
// create task
|
||||
if (is_enable)
|
||||
{
|
||||
if (SUCCEEDED (service->NewTask (0, &task)))
|
||||
{
|
||||
if (SUCCEEDED (task->get_RegistrationInfo (®info)))
|
||||
{
|
||||
reginfo->put_Author (author);
|
||||
reginfo->Release ();
|
||||
}
|
||||
|
||||
if (SUCCEEDED (task->get_Principal (&principal)))
|
||||
{
|
||||
principal->put_RunLevel (TASK_RUNLEVEL_HIGHEST);
|
||||
principal->Release ();
|
||||
}
|
||||
|
||||
if (SUCCEEDED (task->get_Settings (&settings)))
|
||||
{
|
||||
settings->put_AllowHardTerminate (VARIANT_BOOL (FALSE));
|
||||
settings->put_StartWhenAvailable (VARIANT_BOOL (FALSE));
|
||||
settings->put_DisallowStartIfOnBatteries (VARIANT_BOOL (FALSE));
|
||||
settings->put_StopIfGoingOnBatteries (VARIANT_BOOL (FALSE));
|
||||
settings->put_MultipleInstances (TASK_INSTANCES_PARALLEL);
|
||||
settings->put_ExecutionTimeLimit (timelimit);
|
||||
|
||||
settings->Release ();
|
||||
}
|
||||
|
||||
if (SUCCEEDED (task->get_Actions (&action_collection)))
|
||||
{
|
||||
if (SUCCEEDED (action_collection->Create (TASK_ACTION_EXEC, &action)))
|
||||
{
|
||||
if (SUCCEEDED (action->QueryInterface (IID_IExecAction, (LPVOID*)&exec_action)))
|
||||
{
|
||||
if (
|
||||
SUCCEEDED (exec_action->put_Path (path)) &&
|
||||
SUCCEEDED (exec_action->put_WorkingDirectory (directory)) &&
|
||||
SUCCEEDED (exec_action->put_Arguments (args))
|
||||
)
|
||||
{
|
||||
action_result = true;
|
||||
}
|
||||
|
||||
exec_action->Release ();
|
||||
}
|
||||
|
||||
action->Release ();
|
||||
}
|
||||
|
||||
action_collection->Release ();
|
||||
}
|
||||
|
||||
if (action_result)
|
||||
{
|
||||
if (SUCCEEDED (folder->RegisterTaskDefinition (
|
||||
name,
|
||||
task,
|
||||
TASK_CREATE_OR_UPDATE,
|
||||
vtEmpty,
|
||||
vtEmpty,
|
||||
TASK_LOGON_INTERACTIVE_TOKEN,
|
||||
vtEmpty,
|
||||
®istered_task)
|
||||
))
|
||||
{
|
||||
{
|
||||
//ConfigSet (L"SkipUacIsEnabled", true);
|
||||
result = true;
|
||||
|
||||
registered_task->Release ();
|
||||
}
|
||||
}
|
||||
|
||||
task->Release ();
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// remove task
|
||||
result = SUCCEEDED (folder->DeleteTask (name, 0));
|
||||
|
||||
//ConfigSet (L"SkipUacIsEnabled", false);
|
||||
}
|
||||
|
||||
folder->Release ();
|
||||
}
|
||||
}
|
||||
|
||||
service->Release ();
|
||||
}
|
||||
}
|
||||
|
||||
CoUninitialize ();
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
bool SkipUacRun (bool test_only)
|
||||
{
|
||||
bool result = false;
|
||||
|
||||
ITaskService* service = nullptr;
|
||||
ITaskFolder* folder = nullptr;
|
||||
IRegisteredTask* registered_task = nullptr;
|
||||
|
||||
ITaskDefinition* task = nullptr;
|
||||
IActionCollection* action_collection = nullptr;
|
||||
IAction* action = nullptr;
|
||||
IExecAction* exec_action = nullptr;
|
||||
|
||||
IRunningTask* running_task = nullptr;
|
||||
|
||||
wchar_t szPath[MAX_PATH];
|
||||
if (!GetModuleFileName(NULL, szPath, ARRAYSIZE(szPath)))
|
||||
return false;
|
||||
|
||||
MBSTR root (L"\\");
|
||||
MBSTR name (SKIP_UAC_TASK_NAME);
|
||||
|
||||
VARIANT vtEmpty = {VT_EMPTY};
|
||||
|
||||
if (SUCCEEDED (CoInitializeEx (nullptr, COINIT_APARTMENTTHREADED)))
|
||||
{
|
||||
//if (SUCCEEDED (CoInitializeSecurity (nullptr, -1, nullptr, nullptr, RPC_C_AUTHN_LEVEL_PKT_PRIVACY, RPC_C_IMP_LEVEL_IMPERSONATE, nullptr, 0, nullptr)))
|
||||
{
|
||||
if (SUCCEEDED (CoCreateInstance (CLSID_TaskScheduler, nullptr, CLSCTX_INPROC_SERVER, IID_ITaskService, (LPVOID*)&service)))
|
||||
{
|
||||
if (SUCCEEDED (service->Connect (vtEmpty, vtEmpty, vtEmpty, vtEmpty)))
|
||||
{
|
||||
if (SUCCEEDED (service->GetFolder (root, &folder)))
|
||||
{
|
||||
if (SUCCEEDED (folder->GetTask (name, ®istered_task)))
|
||||
{
|
||||
if (SUCCEEDED (registered_task->get_Definition (&task)))
|
||||
{
|
||||
if (SUCCEEDED (task->get_Actions (&action_collection)))
|
||||
{
|
||||
if (SUCCEEDED (action_collection->get_Item (1, &action)))
|
||||
{
|
||||
if (SUCCEEDED (action->QueryInterface (IID_IExecAction, (LPVOID*)&exec_action)))
|
||||
{
|
||||
BSTR path = nullptr;
|
||||
|
||||
exec_action->get_Path (&path);
|
||||
|
||||
PathUnquoteSpaces (path);
|
||||
|
||||
// check path is to current module
|
||||
if (_wcsicmp (path, szPath) == 0)
|
||||
{
|
||||
if (test_only)
|
||||
{
|
||||
result = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
std::wstring args;
|
||||
|
||||
// get arguments
|
||||
{
|
||||
INT numargs = 0;
|
||||
LPWSTR* arga = CommandLineToArgvW(GetCommandLine(), &numargs);
|
||||
|
||||
for (INT i = 1; i < numargs; i++) {
|
||||
if (i > 1)
|
||||
args.append(L" ");
|
||||
args.append(arga[i]);
|
||||
}
|
||||
|
||||
LocalFree(arga);
|
||||
}
|
||||
|
||||
variant_t params = args.c_str();
|
||||
|
||||
if (SUCCEEDED(registered_task->RunEx(params, TASK_RUN_NO_FLAGS, 0, nullptr, &running_task)))
|
||||
{
|
||||
UINT8 count = 3; // try count
|
||||
|
||||
do
|
||||
{
|
||||
QThread::msleep(250);
|
||||
|
||||
TASK_STATE state = TASK_STATE_UNKNOWN;
|
||||
|
||||
running_task->Refresh();
|
||||
running_task->get_State(&state);
|
||||
|
||||
if (
|
||||
state == TASK_STATE_RUNNING ||
|
||||
state == TASK_STATE_READY ||
|
||||
state == TASK_STATE_DISABLED
|
||||
)
|
||||
{
|
||||
if (
|
||||
state == TASK_STATE_RUNNING ||
|
||||
state == TASK_STATE_READY
|
||||
)
|
||||
{
|
||||
result = true;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
} while (count--);
|
||||
|
||||
running_task->Release();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
exec_action->Release ();
|
||||
}
|
||||
|
||||
action->Release ();
|
||||
}
|
||||
|
||||
action_collection->Release ();
|
||||
}
|
||||
|
||||
task->Release ();
|
||||
}
|
||||
|
||||
registered_task->Release ();
|
||||
}
|
||||
|
||||
folder->Release ();
|
||||
}
|
||||
}
|
||||
|
||||
service->Release ();
|
||||
}
|
||||
}
|
||||
|
||||
CoUninitialize ();
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
|
|
@ -10,3 +10,6 @@ bool IsAdminUser(bool OnlyFull = false);
|
|||
|
||||
bool IsAutorunEnabled();
|
||||
bool AutorunEnable(bool is_enable);
|
||||
|
||||
bool SkipUacRun(bool test_only = false);
|
||||
bool SkipUacEnable(bool is_enable);
|
|
@ -433,6 +433,10 @@ CSettingsWindow::CSettingsWindow(QWidget* parent)
|
|||
|
||||
connect(ui.chkWatchConfig, SIGNAL(stateChanged(int)), this, SLOT(OnOptChanged())); // not sbie ini
|
||||
|
||||
connect(ui.chkSkipUAC, SIGNAL(stateChanged(int)), this, SLOT(OnSkipUAC()));
|
||||
ui.chkSkipUAC->setEnabled(IsElevated());
|
||||
m_SkipUACChanged = false;
|
||||
|
||||
connect(ui.chkAdminOnly, SIGNAL(stateChanged(int)), this, SLOT(OnProtectionChange()));
|
||||
connect(ui.chkPassRequired, SIGNAL(stateChanged(int)), this, SLOT(OnProtectionChange()));
|
||||
connect(ui.btnSetPassword, SIGNAL(clicked(bool)), this, SLOT(OnSetPassword()));
|
||||
|
@ -953,6 +957,7 @@ void CSettingsWindow::LoadSettings()
|
|||
ui.chkMonitorSize->setChecked(theConf->GetBool("Options/WatchBoxSize", false));
|
||||
|
||||
ui.chkWatchConfig->setChecked(theConf->GetBool("Options/WatchIni", true));
|
||||
ui.chkSkipUAC->setChecked(SkipUacRun(true));
|
||||
|
||||
ui.chkScanMenu->setChecked(theConf->GetBool("Options/ScanStartMenu", true));
|
||||
ui.cmbIntegrateMenu->setCurrentIndex(theConf->GetInt("Options/IntegrateStartMenu", 0));
|
||||
|
@ -1657,6 +1662,8 @@ void CSettingsWindow::SaveSettings()
|
|||
theConf->SetValue("Options/WatchBoxSize", ui.chkMonitorSize->isChecked());
|
||||
|
||||
theConf->SetValue("Options/WatchIni", ui.chkWatchConfig->isChecked());
|
||||
if (m_SkipUACChanged)
|
||||
SkipUacEnable(ui.chkSkipUAC->isChecked());
|
||||
|
||||
theConf->SetValue("Options/ScanStartMenu", ui.chkScanMenu->isChecked());
|
||||
int OldIntegrateStartMenu = theConf->GetInt("Options/IntegrateStartMenu", 0);
|
||||
|
|
|
@ -88,6 +88,8 @@ private slots:
|
|||
|
||||
void OnOptChanged();
|
||||
|
||||
void OnSkipUAC() { m_SkipUACChanged = true; OnOptChanged(); }
|
||||
|
||||
void OnChangeGUI() { m_bRebuildUI = true; OnOptChanged(); }
|
||||
void OnFeaturesChanged() { m_FeaturesChanged = true; OnGeneralChanged(); }
|
||||
void OnGeneralChanged() { m_GeneralChanged = true; OnOptChanged(); }
|
||||
|
@ -176,6 +178,7 @@ protected:
|
|||
bool m_VolumeChanged;
|
||||
bool m_CompatChanged;
|
||||
bool m_RunChanged;
|
||||
bool m_SkipUACChanged;
|
||||
bool m_ProtectionChanged;
|
||||
bool m_GeneralChanged;
|
||||
bool m_FeaturesChanged;
|
||||
|
|
Loading…
Reference in New Issue