commit
be74d08923
96
CHANGELOG.md
96
CHANGELOG.md
|
@ -4,20 +4,85 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
## [0.5.5 / 5.46.4] - 2021-01-17
|
||||||
|
|
||||||
|
### Added
|
||||||
|
- added "SandboxService=..." to force selected services to be started in the sandbox
|
||||||
|
- added template cleanup functionality to plus UI
|
||||||
|
- allow internet prompt now also allow internet access pemanently
|
||||||
|
- added browse button for box root folder in the SandMan UI
|
||||||
|
- added explorer info message
|
||||||
|
- added option to keep the sandman UI always on top
|
||||||
|
- added drag and drop file on to sandman exe to open/run it sandboxed
|
||||||
|
- added start SandMan UI when a sandboxed application starts
|
||||||
|
- recovery window can now list all files
|
||||||
|
- added file cunter to recovery window
|
||||||
|
- when "NoAddProcessToJob=y" is specified chrome and alike now can fully use the job system
|
||||||
|
-- Note: "NoAddProcessToJob=y" reduces the box isolation, but the affected functions are mostly covered by UIPI anyways
|
||||||
|
- added obtimized default column widths to tha sbie view
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
- updated templates (thanks isaak654)
|
||||||
|
- when trying to take a snapshot of an empty sandbox a proper error message is displayed
|
||||||
|
- new layout for the recovery window
|
||||||
|
- sbie view sorting is now case insensitive
|
||||||
|
|
||||||
|
### Fixed
|
||||||
|
- fixed issue child window closing terminating application when main was hidden
|
||||||
|
- fixed issues with non modal windows
|
||||||
|
- fixed issues connecting in portable mode to driver
|
||||||
|
- fixed minor issues with snapshot window
|
||||||
|
- fixed missing error message when atempting to create an aleady existing sandbox
|
||||||
|
- fixed issue allowing to save setting when a sandbox was alrady deleted
|
||||||
|
- fixed issues with disabled items in dark mode
|
||||||
|
- fixed some dialogs not closing on esc
|
||||||
|
- fixed tab stops on many windows
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
## [0.5.4d / 5.46.3] - 2021-01-11
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
- improved access tracing, removed redundant entries
|
||||||
|
- OpenIpcPath=\BaseNamedObjects\[CoreUI]-* is now hardcoded in the driver no need for the template entry
|
||||||
|
- WindowsFontCache is now open by default
|
||||||
|
- refactored some IPC code in the driver
|
||||||
|
|
||||||
|
### Fixed
|
||||||
|
- fixed issue allowing to bypass the registry isolation, present since Windows 10 Creators Update
|
||||||
|
- fixed creation time not always being properly updated in the SandMan UI
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
## [0.5.4c / 5.46.2] - 2021-01-10
|
||||||
|
|
||||||
|
### Added
|
||||||
|
- added "CallTrace=*" to log all system calls to the access log
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
- improved IPC logging code
|
||||||
|
- improved MSG_2101 logging
|
||||||
|
|
||||||
|
### Fixed
|
||||||
|
- fixed more issues with IPC tracing
|
||||||
|
- fixed SBIE2101 issue with Chrome and derivatives
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
## [0.5.4b / 5.46.1] - 2021-01-08
|
## [0.5.4b / 5.46.1] - 2021-01-08
|
||||||
|
|
||||||
### Added
|
### Added
|
||||||
- added "RunServiceAsSystem=..." allows specific named services to be ran as system
|
- added "RunServiceAsSystem=..." allows specific named services to be run as system
|
||||||
|
|
||||||
### Changed
|
### Changed
|
||||||
- refactored some code around SCM access
|
- refactored some code around SCM access
|
||||||
|
|
||||||
### Fixed
|
### Fixed
|
||||||
- fixed a crash issue in SbieSvc.exe introduced with the last build
|
- fixed a crash issue in SbieSvc.exe introduced with the last build
|
||||||
- fixed issue with sandman ui update check
|
- fixed issue with SandMan UI update check
|
||||||
|
|
||||||
### Removed
|
### Removed
|
||||||
- removed "ProtectRpcSs=y" due to incompatybility with new isolation defaults
|
- removed "ProtectRpcSs=y" due to incompatibility with new isolation defaults
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -81,13 +146,13 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||||
### Added
|
### Added
|
||||||
- added prompt to choose if links in the SandMan UI should be opened in a sandboxed or unsandboxed browser
|
- added prompt to choose if links in the SandMan UI should be opened in a sandboxed or unsandboxed browser
|
||||||
- added more recovery options
|
- added more recovery options
|
||||||
- added "ClosedClsid=" to block com objects from being used when they cause compatibility issues
|
- added "ClosedClsid=" to block COM objects from being used when they cause compatibility issues
|
||||||
- added "ClsidTrace=*" option to trace COM usage
|
- added "ClsidTrace=*" option to trace COM usage
|
||||||
- added "ClosedRT=" option to block access to problematic Windows RT interfaces
|
- added "ClosedRT=" option to block access to problematic Windows RT interfaces
|
||||||
- added option to make a link for any selected process to SandMan UI
|
- added option to make a link for any selected process to SandMan UI
|
||||||
- added option to reset all hidden messages
|
- added option to reset all hidden messages
|
||||||
- added more process presets "force program" and "allow internet access"
|
- added more process presets "force program" and "allow internet access"
|
||||||
- added "SpecialImage=chrome,some_electron_app.exe" option to sandboxie.ini, valid image types "chrome", "firefox"
|
- added "SpecialImage=chrome,some_electron_app.exe" option to Sandboxie.ini, valid image types "chrome", "firefox"
|
||||||
-- with this option you can enable special hardcoded workarounds to new obscure forks of those browsers
|
-- with this option you can enable special hardcoded workarounds to new obscure forks of those browsers
|
||||||
- added German translation (thanks bastik-1001) to the SandMan UI
|
- added German translation (thanks bastik-1001) to the SandMan UI
|
||||||
- added Russian translation (thanks lufog) to the SandMan UI
|
- added Russian translation (thanks lufog) to the SandMan UI
|
||||||
|
@ -109,7 +174,7 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||||
- fixed missing template setup when creating new boxes
|
- fixed missing template setup when creating new boxes
|
||||||
|
|
||||||
### removed
|
### removed
|
||||||
- removed obsolete "OpenDefaultClsid=n" use "ClosedClsid=" with the apropriate values instead
|
- removed obsolete "OpenDefaultClsid=n" use "ClosedClsid=" with the appropriate values instead
|
||||||
- removed suspend/resume menu entry, pooling that state wastes substantial CPU cycles; use task explorer for that functionality
|
- removed suspend/resume menu entry, pooling that state wastes substantial CPU cycles; use task explorer for that functionality
|
||||||
|
|
||||||
|
|
||||||
|
@ -126,9 +191,9 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||||
## [0.5.2 / 5.45.1] - 2020-12-23
|
## [0.5.2 / 5.45.1] - 2020-12-23
|
||||||
|
|
||||||
### Added
|
### Added
|
||||||
- added advanced new box creation dialog to SandMan UI
|
- added advanced new box creation dialogue to SandMan UI
|
||||||
- added show/hide tray context menu entry
|
- added show/hide tray context menu entry
|
||||||
- added refresh button to file recovery dialog
|
- added refresh button to file recovery dialogue
|
||||||
- added mechanism to load icons from {install-dir}/Icons/{icon}.png for UI customization
|
- added mechanism to load icons from {install-dir}/Icons/{icon}.png for UI customization
|
||||||
- added tray indicator to show disabled forced program status in the SandMan UI
|
- added tray indicator to show disabled forced program status in the SandMan UI
|
||||||
- added program name suggestions to box options in SandMan UI
|
- added program name suggestions to box options in SandMan UI
|
||||||
|
@ -138,7 +203,7 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||||
- reorganized the advanced box options a bit
|
- reorganized the advanced box options a bit
|
||||||
- changed icons (thanks Valinwolf for picking the new ones)
|
- changed icons (thanks Valinwolf for picking the new ones)
|
||||||
- updated Template.ini (thanks isaak654)
|
- updated Template.ini (thanks isaak654)
|
||||||
- increates max value for disable forced process time in SandMan UI
|
- increased max value for disable forced process time in SandMan UI
|
||||||
|
|
||||||
### Fixed
|
### Fixed
|
||||||
- fixed BSOD introduced in 5.45.0 when using Windows 10 "core isolation"
|
- fixed BSOD introduced in 5.45.0 when using Windows 10 "core isolation"
|
||||||
|
@ -173,8 +238,8 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||||
- updated SandMan UI to use Qt5.15.1
|
- updated SandMan UI to use Qt5.15.1
|
||||||
|
|
||||||
### Fixed
|
### Fixed
|
||||||
- fixed crash issue with progress dialog
|
- fixed crash issue with progress dialogue
|
||||||
- fixed progress dialog cancel button not working for update checker
|
- fixed progress dialogue cancel button not working for update checker
|
||||||
- fixed issue around NtQueryDirectoryFile when deleting sandbox content
|
- fixed issue around NtQueryDirectoryFile when deleting sandbox content
|
||||||
- fixed dark theme in the notification window
|
- fixed dark theme in the notification window
|
||||||
- fixed issue with disable force programs tray menu
|
- fixed issue with disable force programs tray menu
|
||||||
|
@ -323,7 +388,7 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||||
-- it caused issues with unity games, will be investigated and re enabled later
|
-- it caused issues with unity games, will be investigated and re enabled later
|
||||||
|
|
||||||
### Fixed
|
### Fixed
|
||||||
- fixed color issue with vertical tabs in dark mode
|
- fixed colour issue with vertical tabs in dark mode
|
||||||
- fixed wrong path separators when adding new forced folders
|
- fixed wrong path separators when adding new forced folders
|
||||||
- fixed directory listing bug introduced in 5.43
|
- fixed directory listing bug introduced in 5.43
|
||||||
- fixed issues with settings window when not being connected to driver
|
- fixed issues with settings window when not being connected to driver
|
||||||
|
@ -357,7 +422,7 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||||
- fixed issues with the new box settings editor
|
- fixed issues with the new box settings editor
|
||||||
|
|
||||||
### Removed
|
### Removed
|
||||||
- removes deprecated workaround in the hooking mechanism for an obsolete antimalware product
|
- removes deprecated workaround in the hooking mechanism for an obsolete anti-malware product
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -412,7 +477,7 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||||
- Sandbox names now replace "_" with " " for display allowing to use names that are made of separated words
|
- Sandbox names now replace "_" with " " for display allowing to use names that are made of separated words
|
||||||
|
|
||||||
### Fixed
|
### Fixed
|
||||||
- added mising PreferExternalManifest itialization to portable mode
|
- added missing PreferExternalManifest initialization to portable mode
|
||||||
- fixed permission issues with sandboxed system processes
|
- fixed permission issues with sandboxed system processes
|
||||||
-- Note: you can use "ExposeBoxedSystem=y" for the old behaviour (debug option)
|
-- Note: you can use "ExposeBoxedSystem=y" for the old behaviour (debug option)
|
||||||
- fixed missing SCM access check for sandboxed services
|
- fixed missing SCM access check for sandboxed services
|
||||||
|
@ -452,7 +517,7 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||||
-- Note: using these options weakens the sandboxing, they are intended for debugging and may be used for better application virtualization later
|
-- Note: using these options weakens the sandboxing, they are intended for debugging and may be used for better application virtualization later
|
||||||
|
|
||||||
### Changed
|
### Changed
|
||||||
- SbieDll.dll when processing InjectDll now looks in the SbieHome folder for the Dll's if the entered path starts with a backslash
|
- SbieDll.dll when processing InjectDll now looks in the SbieHome folder for the DLLs if the entered path starts with a backslash
|
||||||
-- i.e. "InjectDll=\LogAPI\i386\logapi32v.dll" or "InjectDll64=\LogAPI\amd64\logapi64v.dll"
|
-- i.e. "InjectDll=\LogAPI\i386\logapi32v.dll" or "InjectDll64=\LogAPI\amd64\logapi64v.dll"
|
||||||
|
|
||||||
### Fixed
|
### Fixed
|
||||||
|
@ -502,4 +567,3 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||||
|
|
||||||
### Fixed
|
### Fixed
|
||||||
- fixed "Windows Installer Service could not be accessed" that got introduced with Windows 1903
|
- fixed "Windows Installer Service could not be accessed" that got introduced with Windows 1903
|
||||||
|
|
||||||
|
|
|
@ -1557,6 +1557,5 @@ void CAppPage::SetDefaultTemplates6(CBox &box)
|
||||||
void CAppPage::SetDefaultTemplates7(CBox &box)
|
void CAppPage::SetDefaultTemplates7(CBox &box)
|
||||||
{
|
{
|
||||||
box.EnableTemplate(L"BlockPorts", TRUE);
|
box.EnableTemplate(L"BlockPorts", TRUE);
|
||||||
box.EnableTemplate(L"WindowsFontCache", TRUE);
|
|
||||||
box.EnableTemplate(L"qWave", TRUE);
|
box.EnableTemplate(L"qWave", TRUE);
|
||||||
}
|
}
|
||||||
|
|
|
@ -97,13 +97,15 @@ BOOL CMonitorDialog::OnInitDialog()
|
||||||
void CMonitorDialog::OnIdle()
|
void CMonitorDialog::OnIdle()
|
||||||
{
|
{
|
||||||
static const WCHAR *_Unknown = L"(Unk) ";
|
static const WCHAR *_Unknown = L"(Unk) ";
|
||||||
|
static const WCHAR *_SysCall = L"SysCall ";
|
||||||
static const WCHAR *_Pipe = L"Pipe ";
|
static const WCHAR *_Pipe = L"Pipe ";
|
||||||
static const WCHAR *_Ipc = L"Ipc ";
|
static const WCHAR *_Ipc = L"Ipc ";
|
||||||
static const WCHAR *_WinClass = L"WinCls ";
|
static const WCHAR *_WinClass = L"WinCls ";
|
||||||
static const WCHAR *_Drive = L"(Drive) ";
|
static const WCHAR *_Drive = L"(Drive) ";
|
||||||
static const WCHAR *_Clsid = L"Clsid ";
|
static const WCHAR *_Clsid = L"Clsid ";
|
||||||
static const WCHAR *_Image = L"Image ";
|
static const WCHAR *_Image = L"Image ";
|
||||||
static const WCHAR *_FileOrKey = L"File/Key ";
|
static const WCHAR *_File = L"File ";
|
||||||
|
static const WCHAR *_Key = L"Key ";
|
||||||
static const WCHAR *_Other = L"Other ";
|
static const WCHAR *_Other = L"Other ";
|
||||||
static const WCHAR *_Separator = L" -------------------------------";
|
static const WCHAR *_Separator = L" -------------------------------";
|
||||||
|
|
||||||
|
@ -146,7 +148,9 @@ void CMonitorDialog::OnIdle()
|
||||||
type &= 0x0FFF;
|
type &= 0x0FFF;
|
||||||
|
|
||||||
const WCHAR *PrefixPtr = _Unknown;
|
const WCHAR *PrefixPtr = _Unknown;
|
||||||
if (type == MONITOR_PIPE)
|
if (type == MONITOR_SYSCALL)
|
||||||
|
PrefixPtr = _SysCall;
|
||||||
|
else if (type == MONITOR_PIPE)
|
||||||
PrefixPtr = _Pipe;
|
PrefixPtr = _Pipe;
|
||||||
else if (type == MONITOR_IPC)
|
else if (type == MONITOR_IPC)
|
||||||
PrefixPtr = _Ipc;
|
PrefixPtr = _Ipc;
|
||||||
|
@ -158,8 +162,10 @@ void CMonitorDialog::OnIdle()
|
||||||
PrefixPtr = _Clsid;
|
PrefixPtr = _Clsid;
|
||||||
else if (type == MONITOR_IMAGE)
|
else if (type == MONITOR_IMAGE)
|
||||||
PrefixPtr = _Image;
|
PrefixPtr = _Image;
|
||||||
else if (type == MONITOR_FILE_OR_KEY)
|
else if (type == MONITOR_FILE)
|
||||||
PrefixPtr = _FileOrKey;
|
PrefixPtr = _File;
|
||||||
|
else if (type == MONITOR_KEY)
|
||||||
|
PrefixPtr = _Key;
|
||||||
else if (type == MONITOR_OTHER)
|
else if (type == MONITOR_OTHER)
|
||||||
PrefixPtr = _Other;
|
PrefixPtr = _Other;
|
||||||
wcsncpy(name, PrefixPtr, 9);
|
wcsncpy(name, PrefixPtr, 9);
|
||||||
|
@ -189,7 +195,11 @@ void CMonitorDialog::OnIdle()
|
||||||
wcscat(name, _Separator);
|
wcscat(name, _Separator);
|
||||||
listbox->AddString(name);
|
listbox->AddString(name);
|
||||||
|
|
||||||
wcscpy(name, _FileOrKey);
|
wcscpy(name, _File);
|
||||||
|
wcscat(name, _Separator);
|
||||||
|
listbox->AddString(name);
|
||||||
|
|
||||||
|
wcscpy(name, _Key);
|
||||||
wcscat(name, _Separator);
|
wcscat(name, _Separator);
|
||||||
listbox->AddString(name);
|
listbox->AddString(name);
|
||||||
|
|
||||||
|
|
|
@ -142,7 +142,7 @@ BOOL CShellDialog::OnInitDialog()
|
||||||
|
|
||||||
CUserSettings &user = CUserSettings::GetInstance();
|
CUserSettings &user = CUserSettings::GetInstance();
|
||||||
user.GetBool(_EnableLogonStart, logonstart, TRUE);
|
user.GetBool(_EnableLogonStart, logonstart, TRUE);
|
||||||
user.GetBool(_EnableAutoStart, autostart, FALSE);
|
user.GetBool(_EnableAutoStart, autostart, TRUE);
|
||||||
user.GetBool(_AddDesktopIcon, desktop, TRUE);
|
user.GetBool(_AddDesktopIcon, desktop, TRUE);
|
||||||
user.GetBool(_AddQuickLaunchIcon, quicklaunch, TRUE);
|
user.GetBool(_AddQuickLaunchIcon, quicklaunch, TRUE);
|
||||||
user.GetBool(_AddContextMenu, contextmenu, TRUE);
|
user.GetBool(_AddContextMenu, contextmenu, TRUE);
|
||||||
|
|
|
@ -21,8 +21,8 @@
|
||||||
#ifndef _MY_VERSION_H
|
#ifndef _MY_VERSION_H
|
||||||
#define _MY_VERSION_H
|
#define _MY_VERSION_H
|
||||||
|
|
||||||
#define MY_VERSION_BINARY 5,46,1
|
#define MY_VERSION_BINARY 5,46,4
|
||||||
#define MY_VERSION_STRING "5.46.1"
|
#define MY_VERSION_STRING "5.46.4"
|
||||||
#define MY_VERSION_COMPAT "5.46.0" // this refers to the driver ABI compatibility
|
#define MY_VERSION_COMPAT "5.46.0" // this refers to the driver ABI compatibility
|
||||||
|
|
||||||
// These #defines are used by either Resource Compiler, or by NSIC installer
|
// These #defines are used by either Resource Compiler, or by NSIC installer
|
||||||
|
|
|
@ -154,6 +154,10 @@ static void Com_Trace(
|
||||||
const WCHAR *TraceType, REFCLSID rclsid, REFIID riid,
|
const WCHAR *TraceType, REFCLSID rclsid, REFIID riid,
|
||||||
ULONG ProcNum, HRESULT hr);
|
ULONG ProcNum, HRESULT hr);
|
||||||
|
|
||||||
|
static void Com_Trace2(
|
||||||
|
const WCHAR* TraceType, REFCLSID rclsid, REFIID riid,
|
||||||
|
ULONG ProcNum, HRESULT hr, USHORT monflag);
|
||||||
|
|
||||||
static void Com_Monitor(REFCLSID rclsid, USHORT monflag);
|
static void Com_Monitor(REFCLSID rclsid, USHORT monflag);
|
||||||
|
|
||||||
#define HSTRING void*
|
#define HSTRING void*
|
||||||
|
@ -596,8 +600,8 @@ _FX HRESULT Com_CoGetClassObject(
|
||||||
}
|
}
|
||||||
|
|
||||||
if (clsctx & CLSCTX_LOCAL_SERVER) {
|
if (clsctx & CLSCTX_LOCAL_SERVER) {
|
||||||
Com_Trace(TraceType, rclsid, riid, 0, hr);
|
Com_Trace2(TraceType, rclsid, riid, 0, hr, monflag);
|
||||||
Com_Monitor(rclsid, monflag);
|
if(!Com_TraceFlag) Com_Monitor(rclsid, monflag);
|
||||||
}
|
}
|
||||||
|
|
||||||
return hr;
|
return hr;
|
||||||
|
@ -642,8 +646,8 @@ _FX HRESULT Com_CoGetObject(
|
||||||
else
|
else
|
||||||
monflag |= MONITOR_DENY;
|
monflag |= MONITOR_DENY;
|
||||||
|
|
||||||
Com_Trace(TraceType, &clsid, riid, 0, hr);
|
Com_Trace2(TraceType, &clsid, riid, 0, hr, monflag);
|
||||||
Com_Monitor(&clsid, monflag);
|
if (!Com_TraceFlag) Com_Monitor(&clsid, monflag);
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
|
|
||||||
|
@ -696,8 +700,8 @@ _FX HRESULT Com_CoCreateInstance(
|
||||||
}
|
}
|
||||||
|
|
||||||
if (clsctx & CLSCTX_LOCAL_SERVER) {
|
if (clsctx & CLSCTX_LOCAL_SERVER) {
|
||||||
Com_Trace(TraceType, rclsid, riid, 0, hr);
|
Com_Trace2(TraceType, rclsid, riid, 0, hr, monflag);
|
||||||
Com_Monitor(rclsid, monflag);
|
if (!Com_TraceFlag) Com_Monitor(rclsid, monflag);
|
||||||
}
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
|
@ -808,8 +812,8 @@ _FX HRESULT Com_CoCreateInstanceEx(
|
||||||
|
|
||||||
for (i = 0; i < cmq; ++i) {
|
for (i = 0; i < cmq; ++i) {
|
||||||
MULTI_QI *mqi = &pmqs[i];
|
MULTI_QI *mqi = &pmqs[i];
|
||||||
Com_Trace(TraceType, rclsid, mqi->pIID, 0, mqi->hr);
|
Com_Trace2(TraceType, rclsid, mqi->pIID, 0, mqi->hr, monflag);
|
||||||
Com_Monitor(rclsid, monflag);
|
if (!Com_TraceFlag) Com_Monitor(rclsid, monflag);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -3306,6 +3310,13 @@ _FX void Com_Trace_Guid(
|
||||||
_FX void Com_Trace(
|
_FX void Com_Trace(
|
||||||
const WCHAR* TraceType, REFCLSID rclsid, REFIID riid,
|
const WCHAR* TraceType, REFCLSID rclsid, REFIID riid,
|
||||||
ULONG ProcNum, HRESULT hr)
|
ULONG ProcNum, HRESULT hr)
|
||||||
|
{
|
||||||
|
Com_Trace2(TraceType, rclsid, riid, ProcNum, hr, MONITOR_TRACE);
|
||||||
|
}
|
||||||
|
|
||||||
|
_FX void Com_Trace2(
|
||||||
|
const WCHAR* TraceType, REFCLSID rclsid, REFIID riid,
|
||||||
|
ULONG ProcNum, HRESULT hr, USHORT monflag)
|
||||||
{
|
{
|
||||||
WCHAR *text;
|
WCHAR *text;
|
||||||
WCHAR *ptr;
|
WCHAR *ptr;
|
||||||
|
@ -3314,7 +3325,7 @@ _FX void Com_Trace(
|
||||||
return;
|
return;
|
||||||
|
|
||||||
text = Com_Alloc(1024 * sizeof(WCHAR));
|
text = Com_Alloc(1024 * sizeof(WCHAR));
|
||||||
ptr = text + Sbie_snwprintf(text, 1024, L"SBIE %s <%08X> ", TraceType, hr);
|
ptr = text + Sbie_snwprintf(text, 1024, L"COM %s <%08X> ", TraceType, hr);
|
||||||
|
|
||||||
if (rclsid) {
|
if (rclsid) {
|
||||||
Com_Trace_Guid(ptr, rclsid, L"CLSID");
|
Com_Trace_Guid(ptr, rclsid, L"CLSID");
|
||||||
|
@ -3341,7 +3352,7 @@ _FX void Com_Trace(
|
||||||
//ptr[1] = L'\0';
|
//ptr[1] = L'\0';
|
||||||
//OutputDebugString(text);
|
//OutputDebugString(text);
|
||||||
*ptr = L'\0';
|
*ptr = L'\0';
|
||||||
SbieApi_MonitorPut(MONITOR_COMCLASS | MONITOR_TRACE, text);
|
SbieApi_MonitorPut(MONITOR_COMCLASS | monflag, text);
|
||||||
|
|
||||||
Com_Free(text);
|
Com_Free(text);
|
||||||
}
|
}
|
||||||
|
|
|
@ -1558,3 +1558,27 @@ BOOLEAN SbieDll_MatchImage(const WCHAR* pat_str, const WCHAR* test_str, const WC
|
||||||
ULONG pat_len = wcslen(pat_str);
|
ULONG pat_len = wcslen(pat_str);
|
||||||
return SbieDll_MatchImage_Impl(pat_str, pat_len, test_str, BoxName, 1);
|
return SbieDll_MatchImage_Impl(pat_str, pat_len, test_str, BoxName, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
// CheckStringInList
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
BOOLEAN SbieDll_CheckStringInList(const WCHAR* string, const WCHAR* boxname, const WCHAR* setting)
|
||||||
|
{
|
||||||
|
WCHAR buf[66];
|
||||||
|
ULONG index = 0;
|
||||||
|
while (1) {
|
||||||
|
NTSTATUS status = SbieApi_QueryConfAsIs(boxname, setting, index, buf, 64 * sizeof(WCHAR));
|
||||||
|
++index;
|
||||||
|
if (NT_SUCCESS(status)) {
|
||||||
|
if (_wcsicmp(buf, string) == 0) {
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (status != STATUS_BUFFER_TOO_SMALL)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
|
@ -977,7 +977,10 @@ _FX BOOL Proc_UpdateProcThreadAttribute(
|
||||||
// fals with an access denided error, so we need to block this attribute form being set
|
// fals with an access denided error, so we need to block this attribute form being set
|
||||||
// if(Dll_ImageType == DLL_IMAGE_GOOGLE_CHROME)
|
// if(Dll_ImageType == DLL_IMAGE_GOOGLE_CHROME)
|
||||||
if (Attribute == 0x0002000d) //PROC_THREAD_ATTRIBUTE_JOB_LIST
|
if (Attribute == 0x0002000d) //PROC_THREAD_ATTRIBUTE_JOB_LIST
|
||||||
|
{
|
||||||
|
if (!SbieApi_QueryConfBool(NULL, L"NoAddProcessToJob", FALSE))
|
||||||
return TRUE;
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
// some mitigation flags break SbieDll.dll Injection, so we disable them
|
// some mitigation flags break SbieDll.dll Injection, so we disable them
|
||||||
if (Attribute == 0x00020007) //PROC_THREAD_ATTRIBUTE_MITIGATION_POLICY
|
if (Attribute == 0x00020007) //PROC_THREAD_ATTRIBUTE_MITIGATION_POLICY
|
||||||
|
@ -1380,11 +1383,13 @@ _FX BOOL Proc_AlternateCreateProcess(
|
||||||
void *lpCurrentDirectory, LPPROCESS_INFORMATION lpProcessInformation,
|
void *lpCurrentDirectory, LPPROCESS_INFORMATION lpProcessInformation,
|
||||||
BOOL *ReturnValue)
|
BOOL *ReturnValue)
|
||||||
{
|
{
|
||||||
|
if (SbieApi_QueryConfBool(NULL, L"BlockSoftwareUpdaters", TRUE))
|
||||||
if (Proc_IsSoftwareUpdateW(lpApplicationName)) {
|
if (Proc_IsSoftwareUpdateW(lpApplicationName)) {
|
||||||
|
|
||||||
SetLastError(ERROR_ACCESS_DENIED);
|
SetLastError(ERROR_ACCESS_DENIED);
|
||||||
*ReturnValue = FALSE;
|
*ReturnValue = FALSE;
|
||||||
|
|
||||||
|
SbieApi_MonitorPut(MONITOR_OTHER, L"Blocked start of an updater");
|
||||||
return TRUE; // exit CreateProcessInternal
|
return TRUE; // exit CreateProcessInternal
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1407,10 +1412,13 @@ _FX BOOL Proc_AlternateCreateProcess(
|
||||||
// don't start Kaspersky Anti Virus klwtblfs.exe component
|
// don't start Kaspersky Anti Virus klwtblfs.exe component
|
||||||
// because Kaspersky protects the process and we can't put
|
// because Kaspersky protects the process and we can't put
|
||||||
// it into a job or inject SbieLow and so on
|
// it into a job or inject SbieLow and so on
|
||||||
|
SbieApi_MonitorPut(MONITOR_OTHER, L"Blocked start of klwtblfs.exe");
|
||||||
return TRUE; // exit CreateProcessInternal
|
return TRUE; // exit CreateProcessInternal
|
||||||
}
|
}
|
||||||
if (Dll_ImageType == DLL_IMAGE_SANDBOXIE_DCOMLAUNCH && lpCommandLine
|
if (Dll_ImageType == DLL_IMAGE_SANDBOXIE_DCOMLAUNCH && lpCommandLine
|
||||||
&& wcsstr(lpCommandLine, L"smartscreen.exe")) {
|
&& wcsstr(lpCommandLine, L"smartscreen.exe")) {
|
||||||
|
|
||||||
|
SbieApi_MonitorPut(MONITOR_OTHER, L"Blocked start of smartscreen.exe");
|
||||||
return TRUE; // exit CreateProcessInternal
|
return TRUE; // exit CreateProcessInternal
|
||||||
}
|
}
|
||||||
return FALSE; // continue with CreateProcessInternal
|
return FALSE; // continue with CreateProcessInternal
|
||||||
|
|
|
@ -269,6 +269,19 @@ WCHAR* GetDynamicLpcPortName(ENUM_DYNAMIC_PORT_TYPE portType)
|
||||||
|
|
||||||
rpl = (EPMAPPER_GET_PORT_NAME_RPL*)SbieDll_CallServer(&req.h);
|
rpl = (EPMAPPER_GET_PORT_NAME_RPL*)SbieDll_CallServer(&req.h);
|
||||||
|
|
||||||
|
WCHAR wsTraceOptions[4];
|
||||||
|
if (SbieApi_QueryConf(NULL, L"IpcTrace", 0, wsTraceOptions, sizeof(wsTraceOptions)) == STATUS_SUCCESS && wsTraceOptions[0] != L'\0')
|
||||||
|
{
|
||||||
|
WCHAR text[130];
|
||||||
|
|
||||||
|
if (rpl && NT_SUCCESS(rpl->h.status))
|
||||||
|
Sbie_snwprintf(text, 130, L"Resolved dynamic port: %d; endpoint: %s", req.portType, rpl->wszPortName);
|
||||||
|
else
|
||||||
|
Sbie_snwprintf(text, 130, L"Failed to resolve dynamic port: %d; status: %08X", req.portType, rpl ? rpl->h.status : 0);
|
||||||
|
|
||||||
|
SbieApi_MonitorPut2(MONITOR_IPC | MONITOR_TRACE, text, FALSE);
|
||||||
|
}
|
||||||
|
|
||||||
if (rpl && NT_SUCCESS(rpl->h.status))
|
if (rpl && NT_SUCCESS(rpl->h.status))
|
||||||
{
|
{
|
||||||
wcsncpy(g_Ipc_DynamicPortNames[portType], rpl->wszPortName, DYNAMIC_PORT_NAME_CHARS);
|
wcsncpy(g_Ipc_DynamicPortNames[portType], rpl->wszPortName, DYNAMIC_PORT_NAME_CHARS);
|
||||||
|
@ -377,15 +390,16 @@ _FX ULONG RpcRt_RpcBindingFromStringBindingW(
|
||||||
status = __sys_RpcBindingFromStringBindingW(StringBinding, OutBinding);
|
status = __sys_RpcBindingFromStringBindingW(StringBinding, OutBinding);
|
||||||
// If there are any IpcTrace options set, then output this debug string
|
// If there are any IpcTrace options set, then output this debug string
|
||||||
WCHAR wsTraceOptions[4];
|
WCHAR wsTraceOptions[4];
|
||||||
if (SbieApi_QueryConf(NULL, L"IpcTrace", 0, wsTraceOptions, sizeof(wsTraceOptions)) == STATUS_SUCCESS && wsTraceOptions != L'\0')
|
if (SbieApi_QueryConf(NULL, L"IpcTrace", 0, wsTraceOptions, sizeof(wsTraceOptions)) == STATUS_SUCCESS && wsTraceOptions[0] != L'\0')
|
||||||
{
|
{
|
||||||
WCHAR msg[512];
|
WCHAR msg[512];
|
||||||
Sbie_snwprintf(msg, 512, L"SBIE p=%06d t=%06d RpcBindingFromStringBindingW StringBinding = '%s', BindingHandle = 0x%X, status = 0x%X\n", GetCurrentProcessId(), GetCurrentThreadId(),
|
|
||||||
StringBinding,
|
//Sbie_snwprintf(msg, 512, L"SBIE p=%06d t=%06d RpcBindingFromStringBindingW StringBinding = '%s', BindingHandle = 0x%X, status = 0x%X\n", GetCurrentProcessId(), GetCurrentThreadId(),
|
||||||
OutBinding,
|
Sbie_snwprintf(msg, 512, L"StringBinding = '%s', BindingHandle = 0x%X, status = 0x%08X",
|
||||||
status);
|
StringBinding, OutBinding, status);
|
||||||
|
|
||||||
//OutputDebugString(msg);
|
//OutputDebugString(msg);
|
||||||
SbieApi_MonitorPut(MONITOR_IPC | MONITOR_TRACE, msg);
|
SbieApi_MonitorPut2(MONITOR_IPC | MONITOR_TRACE, msg, FALSE);
|
||||||
}
|
}
|
||||||
__sys_RpcMgmtSetComTimeout(*OutBinding, RPC_C_BINDING_TIMEOUT);
|
__sys_RpcMgmtSetComTimeout(*OutBinding, RPC_C_BINDING_TIMEOUT);
|
||||||
return status;
|
return status;
|
||||||
|
@ -442,14 +456,14 @@ _FX RPC_STATUS RpcRt_RpcBindingCreateW(
|
||||||
RPC_CSTR StringUuid;
|
RPC_CSTR StringUuid;
|
||||||
|
|
||||||
__sys_UuidToStringW(&Template->ObjectUuid, &StringUuid);
|
__sys_UuidToStringW(&Template->ObjectUuid, &StringUuid);
|
||||||
Sbie_snwprintf(msg, 512, L"SBIE p=%06d t=%06d RpcBindingCreateW Endpoint = '%s', UUID = %s, status = 0x%X\n", GetCurrentProcessId(), GetCurrentThreadId(),
|
//Sbie_snwprintf(msg, 512, L"SBIE p=%06d t=%06d RpcBindingCreateW Endpoint = '%s', UUID = %s, status = 0x%X\n", GetCurrentProcessId(), GetCurrentThreadId(),
|
||||||
|
Sbie_snwprintf(msg, 512, L"Endpoint = '%s', UUID = %s, status = 0x%08X",
|
||||||
Template && Template->StringEndpoint ? Template->StringEndpoint : L"null",
|
Template && Template->StringEndpoint ? Template->StringEndpoint : L"null",
|
||||||
StringUuid,
|
StringUuid, status);
|
||||||
status);
|
|
||||||
__sys_RpcStringFreeW(&StringUuid);
|
__sys_RpcStringFreeW(&StringUuid);
|
||||||
|
|
||||||
//OutputDebugString(msg);
|
//OutputDebugString(msg);
|
||||||
SbieApi_MonitorPut(MONITOR_IPC | MONITOR_TRACE, msg);
|
SbieApi_MonitorPut2(MONITOR_IPC | MONITOR_TRACE, msg, FALSE);
|
||||||
}
|
}
|
||||||
__sys_RpcMgmtSetComTimeout(*Binding, RPC_C_BINDING_TIMEOUT);
|
__sys_RpcMgmtSetComTimeout(*Binding, RPC_C_BINDING_TIMEOUT);
|
||||||
return status;
|
return status;
|
||||||
|
|
|
@ -202,6 +202,9 @@ SBIEDLL_EXPORT ULONG SbieDll_InjectLow(HANDLE hProcess, BOOLEAN is_wow64, BOOLE
|
||||||
|
|
||||||
SBIEDLL_EXPORT BOOLEAN SbieDll_MatchImage(const WCHAR* pat_str, const WCHAR* test_str, const WCHAR* BoxName);
|
SBIEDLL_EXPORT BOOLEAN SbieDll_MatchImage(const WCHAR* pat_str, const WCHAR* test_str, const WCHAR* BoxName);
|
||||||
|
|
||||||
|
SBIEDLL_EXPORT BOOLEAN SbieDll_CheckStringInList(const WCHAR* string, const WCHAR* boxname, const WCHAR* setting);
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -888,6 +888,9 @@ _FX BOOLEAN Scm_IsBoxedService(const WCHAR *ServiceName)
|
||||||
|
|
||||||
Dll_Free(names);
|
Dll_Free(names);
|
||||||
|
|
||||||
|
if (SbieDll_CheckStringInList(ServiceName, NULL, L"SandboxService"))
|
||||||
|
found = TRUE;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
if (_wcsicmp(ServiceName, _eventsystem) == 0) {
|
if (_wcsicmp(ServiceName, _eventsystem) == 0) {
|
||||||
//
|
//
|
||||||
|
|
|
@ -123,8 +123,12 @@ _FX BOOLEAN SysInfo_Init(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
SBIEDLL_HOOK(SysInfo_, NtCreateJobObject);
|
SBIEDLL_HOOK(SysInfo_, NtCreateJobObject);
|
||||||
|
if (!SbieApi_QueryConfBool(NULL, L"NoAddProcessToJob", FALSE))
|
||||||
|
{
|
||||||
SBIEDLL_HOOK(SysInfo_, NtAssignProcessToJobObject);
|
SBIEDLL_HOOK(SysInfo_, NtAssignProcessToJobObject);
|
||||||
SBIEDLL_HOOK(SysInfo_, NtSetInformationJobObject);
|
SBIEDLL_HOOK(SysInfo_, NtSetInformationJobObject);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
SBIEDLL_HOOK(SysInfo_,SetLocaleInfoW);
|
SBIEDLL_HOOK(SysInfo_,SetLocaleInfoW);
|
||||||
SBIEDLL_HOOK(SysInfo_,SetLocaleInfoA);
|
SBIEDLL_HOOK(SysInfo_,SetLocaleInfoA);
|
||||||
|
@ -392,6 +396,7 @@ _FX NTSTATUS SysInfo_NtCreateJobObject(
|
||||||
// job object, and to not request some specific rights
|
// job object, and to not request some specific rights
|
||||||
//
|
//
|
||||||
|
|
||||||
|
if (!SbieApi_QueryConfBool(NULL, L"NoAddProcessToJob", FALSE))
|
||||||
DesiredAccess &= ~(JOB_OBJECT_ASSIGN_PROCESS | JOB_OBJECT_TERMINATE);
|
DesiredAccess &= ~(JOB_OBJECT_ASSIGN_PROCESS | JOB_OBJECT_TERMINATE);
|
||||||
|
|
||||||
jobname_len = Dll_BoxIpcPathLen + wcslen(Dll_ImageName) + 64;
|
jobname_len = Dll_BoxIpcPathLen + wcslen(Dll_ImageName) + 64;
|
||||||
|
|
|
@ -41,7 +41,7 @@
|
||||||
#define DUPLICATE_INHERIT 0x00040000
|
#define DUPLICATE_INHERIT 0x00040000
|
||||||
#define DUPLICATE_INTO_OTHER 0x00080000 // otherwise DUP_FROM_OTHER
|
#define DUPLICATE_INTO_OTHER 0x00080000 // otherwise DUP_FROM_OTHER
|
||||||
|
|
||||||
|
#define MONITOR_SYSCALL 0x000B
|
||||||
#define MONITOR_PIPE 0x011B
|
#define MONITOR_PIPE 0x011B
|
||||||
#define MONITOR_IPC 0x022B
|
#define MONITOR_IPC 0x022B
|
||||||
#define MONITOR_WINCLASS 0x033B
|
#define MONITOR_WINCLASS 0x033B
|
||||||
|
@ -49,10 +49,17 @@
|
||||||
#define MONITOR_COMCLASS 0x055B
|
#define MONITOR_COMCLASS 0x055B
|
||||||
#define MONITOR_IGNORE 0x066B
|
#define MONITOR_IGNORE 0x066B
|
||||||
#define MONITOR_IMAGE 0x077B
|
#define MONITOR_IMAGE 0x077B
|
||||||
#define MONITOR_FILE_OR_KEY 0x088B
|
#define MONITOR_FILE 0x088B
|
||||||
#define MONITOR_OTHER 0x099B
|
#define MONITOR_KEY 0x099B
|
||||||
|
#define MONITOR_OTHER 0x0AAB
|
||||||
|
//#define MONITOR_ 0x0BBB
|
||||||
|
//#define MONITOR_ 0x0CCB
|
||||||
|
//#define MONITOR_ 0x0DDB
|
||||||
|
//#define MONITOR_ 0x0EEB
|
||||||
|
//#define MONITOR_ 0x0FFB
|
||||||
#define MONITOR_OPEN 0x1000
|
#define MONITOR_OPEN 0x1000
|
||||||
#define MONITOR_DENY 0x2000
|
#define MONITOR_DENY 0x2000
|
||||||
|
//#define MONITOR_ 0x4000
|
||||||
#define MONITOR_TRACE 0x8000
|
#define MONITOR_TRACE 0x8000
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -994,7 +994,7 @@ _FX NTSTATUS File_Generic_MyParseProc(
|
||||||
if (proc->file_trace & TRACE_IGNORE)
|
if (proc->file_trace & TRACE_IGNORE)
|
||||||
Log_Debug_Msg(MONITOR_IGNORE, ignore_str, Driver_Empty);
|
Log_Debug_Msg(MONITOR_IGNORE, ignore_str, Driver_Empty);
|
||||||
|
|
||||||
if (Session_MonitorCount &&
|
else if (Session_MonitorCount &&
|
||||||
device_type != FILE_DEVICE_PHYSICAL_NETCARD)
|
device_type != FILE_DEVICE_PHYSICAL_NETCARD)
|
||||||
Session_MonitorPut(MONITOR_IGNORE, ignore_str + 4, proc->pid);
|
Session_MonitorPut(MONITOR_IGNORE, ignore_str + 4, proc->pid);
|
||||||
|
|
||||||
|
@ -1492,14 +1492,25 @@ skip_due_to_home_folder:
|
||||||
letter = 0;
|
letter = 0;
|
||||||
|
|
||||||
if (letter) {
|
if (letter) {
|
||||||
|
|
||||||
|
USHORT mon_type = IsPipeDevice ? MONITOR_PIPE : MONITOR_FILE;
|
||||||
|
if (!IsBoxedPath) {
|
||||||
|
if (ShouldMonitorAccess == TRUE)
|
||||||
|
mon_type |= MONITOR_DENY;
|
||||||
|
else
|
||||||
|
mon_type |= MONITOR_OPEN;
|
||||||
|
}
|
||||||
|
if(!IsPipeDevice && !ShouldMonitorAccess)
|
||||||
|
mon_type |= MONITOR_TRACE;
|
||||||
|
|
||||||
swprintf(access_str, L"(F%c) %08X.%02X.%08X",
|
swprintf(access_str, L"(F%c) %08X.%02X.%08X",
|
||||||
letter, DesiredAccess,
|
letter, DesiredAccess,
|
||||||
CreateDisposition & 0x0F, CreateOptions);
|
CreateDisposition & 0x0F, CreateOptions);
|
||||||
Log_Debug_Msg(IsPipeDevice ? MONITOR_PIPE : MONITOR_FILE_OR_KEY, access_str, Name->Name.Buffer);
|
Log_Debug_Msg(mon_type, access_str, Name->Name.Buffer);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (IsPipeDevice && Session_MonitorCount) {
|
else if (IsPipeDevice && Session_MonitorCount) {
|
||||||
|
|
||||||
USHORT mon_type = MONITOR_PIPE;
|
USHORT mon_type = MONITOR_PIPE;
|
||||||
WCHAR *mon_name = Name->Name.Buffer;
|
WCHAR *mon_name = Name->Name.Buffer;
|
||||||
|
@ -1515,9 +1526,12 @@ skip_due_to_home_folder:
|
||||||
|
|
||||||
} else if (ShouldMonitorAccess) {
|
} else if (ShouldMonitorAccess) {
|
||||||
|
|
||||||
Session_MonitorPut(MONITOR_FILE_OR_KEY | MONITOR_DENY, Name->Name.Buffer, proc->pid);
|
Session_MonitorPut(MONITOR_FILE | MONITOR_DENY, Name->Name.Buffer, proc->pid);
|
||||||
|
|
||||||
} else if (msg1313 && status == STATUS_ACCESS_DENIED
|
}
|
||||||
|
|
||||||
|
if (!ShouldMonitorAccess && msg1313
|
||||||
|
&& status == STATUS_ACCESS_DENIED
|
||||||
&& device_type == FILE_DEVICE_DISK
|
&& device_type == FILE_DEVICE_DISK
|
||||||
&& RemainingName && RemainingName->Length == 0) {
|
&& RemainingName && RemainingName->Length == 0) {
|
||||||
|
|
||||||
|
|
|
@ -1442,7 +1442,7 @@ _FX ULONG_PTR Gui_NtUserSendInput(
|
||||||
if (letter) {
|
if (letter) {
|
||||||
|
|
||||||
swprintf(access_str, L"(G%c) SendInput", letter);
|
swprintf(access_str, L"(G%c) SendInput", letter);
|
||||||
Log_Debug_Msg(MONITOR_WINCLASS, access_str, Driver_Empty);
|
Log_Debug_Msg(MONITOR_WINCLASS | MONITOR_TRACE, access_str, Driver_Empty);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1538,7 +1538,7 @@ _FX ULONG_PTR Gui_NtUserSetWindowsHookEx(
|
||||||
swprintf(access_str,
|
swprintf(access_str,
|
||||||
L"(G%c) WinHook %04d on tid=%06d pid=%06d",
|
L"(G%c) WinHook %04d on tid=%06d pid=%06d",
|
||||||
letter, HookType, idThread, idProcess);
|
letter, HookType, idThread, idProcess);
|
||||||
Log_Debug_Msg(MONITOR_WINCLASS, access_str, Driver_Empty);
|
Log_Debug_Msg(MONITOR_WINCLASS | MONITOR_TRACE, access_str, Driver_Empty);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1595,7 +1595,7 @@ _FX ULONG_PTR Gui_NtUserSetWinEventHook(
|
||||||
|
|
||||||
swprintf(access_str, L"(G%c) AccHook on tid=%06d pid=%06d",
|
swprintf(access_str, L"(G%c) AccHook on tid=%06d pid=%06d",
|
||||||
letter, idThread, idProcess);
|
letter, idThread, idProcess);
|
||||||
Log_Debug_Msg(MONITOR_WINCLASS, access_str, Driver_Empty);
|
Log_Debug_Msg(MONITOR_WINCLASS | MONITOR_TRACE, access_str, Driver_Empty);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -210,14 +210,13 @@ _FX BOOLEAN Ipc_Init(void)
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Note: those don't have a special treatment
|
if (Driver_OsVersion >= DRIVER_WINDOWS_10) {
|
||||||
//if (Driver_OsVersion >= DRIVER_WINDOWS_10) {
|
|
||||||
//
|
if(!Mem_GetLockResource(&Ipc_Dynamic_Ports[WPAD_PORT].pPortLock, TRUE)
|
||||||
// if(!Mem_GetLockResource(&Ipc_Dynamic_Ports[WPAD_PORT].pPortLock, TRUE)
|
|| !Mem_GetLockResource(&Ipc_Dynamic_Ports[GAME_CONFIG_STORE_PORT].pPortLock, TRUE)
|
||||||
// || !Mem_GetLockResource(&Ipc_Dynamic_Ports[GAME_CONFIG_STORE_PORT].pPortLock, TRUE)
|
|| !Mem_GetLockResource(&Ipc_Dynamic_Ports[SMART_CARD_PORT].pPortLock, TRUE)
|
||||||
// || !Mem_GetLockResource(&Ipc_Dynamic_Ports[SMART_CARD_PORT].pPortLock, TRUE)
|
) return FALSE;
|
||||||
// ) return FALSE;
|
}
|
||||||
//}
|
|
||||||
|
|
||||||
//
|
//
|
||||||
// finish
|
// finish
|
||||||
|
@ -521,6 +520,8 @@ _FX BOOLEAN Ipc_InitPaths(PROCESS *proc)
|
||||||
L"\\RPC Control\\LSARPC_ENDPOINT",
|
L"\\RPC Control\\LSARPC_ENDPOINT",
|
||||||
L"\\RPC Control\\umpo",
|
L"\\RPC Control\\umpo",
|
||||||
L"*\\BaseNamedObjects*\\FlipEx*",
|
L"*\\BaseNamedObjects*\\FlipEx*",
|
||||||
|
L"*\\BaseNamedObjects*\\FontCachePort",
|
||||||
|
L"*\\BaseNamedObjects*\\FntCache-*",
|
||||||
NULL
|
NULL
|
||||||
};
|
};
|
||||||
static const WCHAR *openpaths_windows8[] = {
|
static const WCHAR *openpaths_windows8[] = {
|
||||||
|
@ -542,6 +543,7 @@ _FX BOOLEAN Ipc_InitPaths(PROCESS *proc)
|
||||||
L"*\\BaseNamedObjects*\\CoreMessagingRegistrar",
|
L"*\\BaseNamedObjects*\\CoreMessagingRegistrar",
|
||||||
L"\\RPC Control\\webcache_*",
|
L"\\RPC Control\\webcache_*",
|
||||||
L"*\\BaseNamedObjects\\windows_webcache_counters_*",
|
L"*\\BaseNamedObjects\\windows_webcache_counters_*",
|
||||||
|
L"*\\BaseNamedObjects\\[CoreUI]-*",
|
||||||
NULL
|
NULL
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -872,34 +874,34 @@ _FX NTSTATUS Ipc_CheckGenericObject(
|
||||||
status = STATUS_ACCESS_DENIED;
|
status = STATUS_ACCESS_DENIED;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Note: since version 5.46 these are open only per process
|
|
||||||
//else if (!is_open && !is_closed)
|
else if (!is_open && !is_closed)
|
||||||
//{
|
{
|
||||||
// int i;
|
int i;
|
||||||
// for (i = 0; i < NUM_DYNAMIC_PORTS; i++)
|
for (i = 0; i < NUM_DYNAMIC_PORTS; i++)
|
||||||
// {
|
{
|
||||||
// if (Ipc_Dynamic_Ports[i].pPortLock)
|
if (Ipc_Dynamic_Ports[i].pPortLock)
|
||||||
// {
|
{
|
||||||
// KeEnterCriticalRegion();
|
KeEnterCriticalRegion();
|
||||||
// ExAcquireResourceSharedLite(Ipc_Dynamic_Ports[i].pPortLock, TRUE);
|
ExAcquireResourceSharedLite(Ipc_Dynamic_Ports[i].pPortLock, TRUE);
|
||||||
//
|
|
||||||
// if (*Ipc_Dynamic_Ports[i].wstrPortName
|
if (*Ipc_Dynamic_Ports[i].wstrPortName
|
||||||
// && (Name->Length >= 32 * sizeof(WCHAR))
|
&& (Name->Length >= 32 * sizeof(WCHAR))
|
||||||
// && _wcsicmp(Name->Buffer, Ipc_Dynamic_Ports[i].wstrPortName) == 0)
|
&& _wcsicmp(Name->Buffer, Ipc_Dynamic_Ports[i].wstrPortName) == 0)
|
||||||
// {
|
{
|
||||||
// // dynamic version of RPC ports, see also ipc_spl.c
|
// dynamic version of RPC ports, see also ipc_spl.c
|
||||||
// // and RpcBindingFromStringBindingW in core/dll/rpcrt.c
|
// and RpcBindingFromStringBindingW in core/dll/rpcrt.c
|
||||||
// is_open = TRUE;
|
is_open = TRUE;
|
||||||
// }
|
}
|
||||||
//
|
|
||||||
// ExReleaseResourceLite(Ipc_Dynamic_Ports[i].pPortLock);
|
ExReleaseResourceLite(Ipc_Dynamic_Ports[i].pPortLock);
|
||||||
// KeLeaveCriticalRegion();
|
KeLeaveCriticalRegion();
|
||||||
//
|
|
||||||
// if (is_open)
|
if (is_open)
|
||||||
// break;
|
break;
|
||||||
// }
|
}
|
||||||
// }
|
}
|
||||||
//}
|
}
|
||||||
|
|
||||||
if (is_closed || (! is_open))
|
if (is_closed || (! is_open))
|
||||||
status = STATUS_ACCESS_DENIED;
|
status = STATUS_ACCESS_DENIED;
|
||||||
|
@ -936,12 +938,21 @@ _FX NTSTATUS Ipc_CheckGenericObject(
|
||||||
}
|
}
|
||||||
|
|
||||||
if (letter) {
|
if (letter) {
|
||||||
|
|
||||||
|
USHORT mon_type = MONITOR_IPC;
|
||||||
|
if (!IsBoxedPath) {
|
||||||
|
if (NT_SUCCESS(status))
|
||||||
|
mon_type |= MONITOR_OPEN;
|
||||||
|
else
|
||||||
|
mon_type |= MONITOR_DENY;
|
||||||
|
}
|
||||||
|
|
||||||
swprintf(access_str, L"(I%c) %08X", letter, GrantedAccess);
|
swprintf(access_str, L"(I%c) %08X", letter, GrantedAccess);
|
||||||
Log_Debug_Msg(MONITOR_IPC, access_str, Name->Buffer);
|
Log_Debug_Msg(mon_type, access_str, Name->Buffer);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Session_MonitorCount) {
|
else if (Session_MonitorCount) {
|
||||||
|
|
||||||
USHORT mon_type = MONITOR_IPC;
|
USHORT mon_type = MONITOR_IPC;
|
||||||
WCHAR *mon_name = Name->Buffer;
|
WCHAR *mon_name = Name->Buffer;
|
||||||
|
@ -995,6 +1006,7 @@ _FX NTSTATUS Ipc_CheckJobObject(
|
||||||
// is inside the sandbox
|
// is inside the sandbox
|
||||||
//
|
//
|
||||||
|
|
||||||
|
if (!Conf_Get_Boolean(proc->box->name, L"NoAddProcessToJob", 0, FALSE))
|
||||||
if (GrantedAccess & (JOB_OBJECT_ASSIGN_PROCESS | JOB_OBJECT_TERMINATE))
|
if (GrantedAccess & (JOB_OBJECT_ASSIGN_PROCESS | JOB_OBJECT_TERMINATE))
|
||||||
return STATUS_ACCESS_DENIED;
|
return STATUS_ACCESS_DENIED;
|
||||||
|
|
||||||
|
|
|
@ -28,12 +28,220 @@
|
||||||
#include "session.h"
|
#include "session.h"
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
// Structures and Types
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
typedef struct _LSA_MESSAGE_XP {
|
||||||
|
|
||||||
|
PORT_MESSAGE port_msg;
|
||||||
|
ULONG api_code;
|
||||||
|
ULONG status;
|
||||||
|
ULONG auth_pkg_code;
|
||||||
|
ULONG* buf;
|
||||||
|
ULONG buf_len;
|
||||||
|
|
||||||
|
} LSA_MESSAGE_XP;
|
||||||
|
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
// Variables
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
#ifndef _WIN64
|
||||||
|
|
||||||
|
static ULONG Ipc_MSV10_AuthPackageNumber = 0;
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
// Functions
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
BOOLEAN Ipc_Filter_Lsa_Ep_Msg(PROCESS* proc, UCHAR uMsg);
|
||||||
|
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
// Ipc_CheckPortRequest_Lsa
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
_FX NTSTATUS Ipc_CheckPortRequest_Lsa(
|
||||||
|
PROCESS* proc, OBJECT_NAME_INFORMATION* Name, PORT_MESSAGE* msg)
|
||||||
|
{
|
||||||
|
NTSTATUS status;
|
||||||
|
|
||||||
|
if (!proc->ipc_block_password)
|
||||||
|
return STATUS_BAD_INITIAL_PC;
|
||||||
|
|
||||||
|
//
|
||||||
|
// check that it is \LsaAuthenticationPort
|
||||||
|
// or that it is \RPC Control\lsasspirpc (Windows 7 variant)
|
||||||
|
//
|
||||||
|
|
||||||
|
if (Name->Name.Length == 22 * sizeof(WCHAR)) {
|
||||||
|
|
||||||
|
if (_wcsicmp(Name->Name.Buffer, L"\\LsaAuthenticationPort") != 0)
|
||||||
|
return STATUS_BAD_INITIAL_PC;
|
||||||
|
|
||||||
|
}
|
||||||
|
else if (Name->Name.Length == 23 * sizeof(WCHAR)) {
|
||||||
|
|
||||||
|
if (_wcsicmp(Name->Name.Buffer, L"\\RPC Control\\lsasspirpc") != 0)
|
||||||
|
return STATUS_BAD_INITIAL_PC;
|
||||||
|
|
||||||
|
}
|
||||||
|
else
|
||||||
|
return STATUS_BAD_INITIAL_PC;
|
||||||
|
|
||||||
|
//
|
||||||
|
// examine message
|
||||||
|
//
|
||||||
|
|
||||||
|
status = STATUS_SUCCESS;
|
||||||
|
|
||||||
|
__try {
|
||||||
|
|
||||||
|
ProbeForRead(msg, sizeof(PORT_MESSAGE), sizeof(ULONG_PTR));
|
||||||
|
|
||||||
|
if (Driver_OsVersion >= DRIVER_WINDOWS_VISTA) {
|
||||||
|
|
||||||
|
//
|
||||||
|
// in Windows Vista and Windows 7, a password change request
|
||||||
|
// includes the WCHAR string Negotiate immediately followed
|
||||||
|
// by a non-zero WCHAR
|
||||||
|
//
|
||||||
|
|
||||||
|
WCHAR* ptr = (WCHAR*)((UCHAR*)msg + sizeof(PORT_MESSAGE));
|
||||||
|
ULONG len = msg->u1.s1.DataLength;
|
||||||
|
|
||||||
|
ProbeForRead(ptr, len, sizeof(WCHAR));
|
||||||
|
len /= sizeof(WCHAR);
|
||||||
|
|
||||||
|
while (len > 9 + 1) {
|
||||||
|
|
||||||
|
if (ptr[0] == L'N' && ptr[9] != 0
|
||||||
|
&& wmemcmp(ptr, L"Negotiate", 9) == 0) {
|
||||||
|
|
||||||
|
status = STATUS_ACCESS_DENIED;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
++ptr;
|
||||||
|
--len;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
#ifndef _WIN64
|
||||||
|
else { // xp support
|
||||||
|
|
||||||
|
//
|
||||||
|
// prior to Windows Vista, we have a 'call package' api
|
||||||
|
// call (value 2), which identifies the MSV10 auth package,
|
||||||
|
// and a change password sub code (value 5)
|
||||||
|
//
|
||||||
|
|
||||||
|
if (msg->u1.s1.TotalLength >= sizeof(LSA_MESSAGE_XP)) {
|
||||||
|
|
||||||
|
LSA_MESSAGE_XP* msg2 = (LSA_MESSAGE_XP*)msg;
|
||||||
|
|
||||||
|
ProbeForRead(
|
||||||
|
msg2, sizeof(LSA_MESSAGE_XP), sizeof(ULONG_PTR));
|
||||||
|
|
||||||
|
if (msg2->api_code == 2 && // LsaCallAuthenticationPackage
|
||||||
|
msg2->auth_pkg_code == Ipc_MSV10_AuthPackageNumber &&
|
||||||
|
msg2->buf_len >= sizeof(ULONG)) {
|
||||||
|
|
||||||
|
ULONG* buf = msg2->buf;
|
||||||
|
ProbeForRead(buf, sizeof(ULONG), sizeof(ULONG));
|
||||||
|
|
||||||
|
if (*buf == 5) { // change password
|
||||||
|
|
||||||
|
status = STATUS_ACCESS_DENIED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
}
|
||||||
|
__except (EXCEPTION_EXECUTE_HANDLER) {
|
||||||
|
status = GetExceptionCode();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (status == STATUS_ACCESS_DENIED)
|
||||||
|
Log_Msg_Process(MSG_PASSWORD_CHANGE_DENIED, NULL, NULL, -1, proc->pid);
|
||||||
|
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
// Ipc_CheckPortRequest_LsaEP
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
_FX NTSTATUS Ipc_CheckPortRequest_LsaEP(
|
||||||
|
PROCESS* proc, OBJECT_NAME_INFORMATION* Name, PORT_MESSAGE* msg)
|
||||||
|
{
|
||||||
|
NTSTATUS status;
|
||||||
|
|
||||||
|
if (proc->ipc_open_lsa_endpoint)
|
||||||
|
return STATUS_BAD_INITIAL_PC;
|
||||||
|
|
||||||
|
if (Name->Name.Length == 28 * sizeof(WCHAR)) {
|
||||||
|
|
||||||
|
if (_wcsicmp(Name->Name.Buffer, L"\\RPC Control\\LSARPC_ENDPOINT") != 0)
|
||||||
|
return STATUS_BAD_INITIAL_PC;
|
||||||
|
|
||||||
|
}
|
||||||
|
else
|
||||||
|
return STATUS_BAD_INITIAL_PC;
|
||||||
|
|
||||||
|
//
|
||||||
|
// examine message
|
||||||
|
//
|
||||||
|
|
||||||
|
status = STATUS_SUCCESS;
|
||||||
|
|
||||||
|
__try {
|
||||||
|
|
||||||
|
ProbeForRead(msg, sizeof(PORT_MESSAGE), sizeof(ULONG_PTR));
|
||||||
|
|
||||||
|
if (Driver_OsVersion >= DRIVER_WINDOWS_7) {
|
||||||
|
|
||||||
|
ULONG len = msg->u1.s1.DataLength;
|
||||||
|
UCHAR* ptr = (UCHAR*)((UCHAR*)msg + sizeof(PORT_MESSAGE));
|
||||||
|
int i = 0;
|
||||||
|
int rc = -2;
|
||||||
|
|
||||||
|
ProbeForRead(ptr, len, sizeof(WCHAR));
|
||||||
|
|
||||||
|
if (Ipc_Filter_Lsa_Ep_Msg(proc, ptr[20]))
|
||||||
|
status = STATUS_ACCESS_DENIED;
|
||||||
|
|
||||||
|
//DbgPrint("\\RPC Control\\LSARPC_ENDPOINT message ID: %d\n", (int)ptr[20]);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
__except (EXCEPTION_EXECUTE_HANDLER) {
|
||||||
|
status = GetExceptionCode();
|
||||||
|
}
|
||||||
|
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
// Ipc_Filter_Lsa_Ep_Msg
|
// Ipc_Filter_Lsa_Ep_Msg
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
_FX BOOLEAN Ipc_Filter_Lsa_Ep_Msg(UCHAR uMsg)
|
_FX BOOLEAN Ipc_Filter_Lsa_Ep_Msg(PROCESS* proc, UCHAR uMsg)
|
||||||
{
|
{
|
||||||
BOOLEAN filter = FALSE;
|
BOOLEAN filter = FALSE;
|
||||||
|
|
||||||
|
@ -120,14 +328,54 @@ _FX BOOLEAN Ipc_Filter_Lsa_Ep_Msg(UCHAR uMsg)
|
||||||
filter = TRUE;
|
filter = TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Session_MonitorCount) {
|
if (Session_MonitorCount && (proc->ipc_trace & (TRACE_ALLOW | TRACE_DENY))) {
|
||||||
|
|
||||||
WCHAR access_str[24];
|
USHORT mon_type = MONITOR_IPC;
|
||||||
swprintf(access_str, L" Msg: %02X", (ULONG)uMsg);
|
|
||||||
const WCHAR* strings[3] = { L"\\RPC Control\\LSARPC_ENDPOINT", access_str, NULL };
|
if (filter && (proc->ipc_trace & TRACE_DENY))
|
||||||
Session_MonitorPutEx(MONITOR_IPC | (filter ? MONITOR_DENY : MONITOR_OPEN), strings, PsGetCurrentProcessId());
|
mon_type |= MONITOR_DENY;
|
||||||
|
else if (!filter && (proc->ipc_trace & TRACE_ALLOW))
|
||||||
|
mon_type |= MONITOR_OPEN;
|
||||||
|
else
|
||||||
|
mon_type = 0;
|
||||||
|
|
||||||
|
if (mon_type) {
|
||||||
|
WCHAR msg_str[24];
|
||||||
|
swprintf(msg_str, L" Msg: %02X", (ULONG)uMsg);
|
||||||
|
const WCHAR* strings[3] = { L"\\RPC Control\\LSARPC_ENDPOINT", msg_str, NULL };
|
||||||
|
Session_MonitorPutEx(mon_type, strings, NULL, PsGetCurrentProcessId());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return filter;
|
return filter;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifndef _WIN64
|
||||||
|
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
// Ipc_Api_SetLsaAuthPkg
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
_FX NTSTATUS Ipc_Api_SetLsaAuthPkg(PROCESS* proc, ULONG64* parms) // xp support
|
||||||
|
{
|
||||||
|
//
|
||||||
|
// caller must be our service process
|
||||||
|
//
|
||||||
|
|
||||||
|
if (proc || (PsGetCurrentProcessId() != Api_ServiceProcessId))
|
||||||
|
return STATUS_ACCESS_DENIED;
|
||||||
|
|
||||||
|
//
|
||||||
|
// collect msv10 auth package number
|
||||||
|
//
|
||||||
|
|
||||||
|
if (Ipc_MSV10_AuthPackageNumber)
|
||||||
|
return STATUS_ACCESS_DENIED;
|
||||||
|
|
||||||
|
Ipc_MSV10_AuthPackageNumber = (ULONG)parms[1];
|
||||||
|
return STATUS_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
|
@ -82,18 +82,6 @@ typedef struct _WINAPI_MESSAGE {
|
||||||
|
|
||||||
} WINAPI_MESSAGE;
|
} WINAPI_MESSAGE;
|
||||||
|
|
||||||
|
|
||||||
typedef struct _LSA_MESSAGE_XP {
|
|
||||||
|
|
||||||
PORT_MESSAGE port_msg;
|
|
||||||
ULONG api_code;
|
|
||||||
ULONG status;
|
|
||||||
ULONG auth_pkg_code;
|
|
||||||
ULONG *buf;
|
|
||||||
ULONG buf_len;
|
|
||||||
|
|
||||||
} LSA_MESSAGE_XP;
|
|
||||||
|
|
||||||
typedef struct _POWER_API_MESSAGE
|
typedef struct _POWER_API_MESSAGE
|
||||||
{
|
{
|
||||||
PORT_MESSAGE port_msg;
|
PORT_MESSAGE port_msg;
|
||||||
|
@ -122,32 +110,37 @@ typedef struct _POWER_API_MESSAGE
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
static NTSTATUS Ipc_CheckPortRequest(
|
NTSTATUS Ipc_CheckPortRequest(
|
||||||
PROCESS *proc, HANDLE PortHandle, PORT_MESSAGE *msg);
|
PROCESS *proc, HANDLE PortHandle, PORT_MESSAGE *msg);
|
||||||
|
|
||||||
static NTSTATUS Ipc_CheckPortRequest_WinApi(
|
NTSTATUS Ipc_CheckPortRequest_WinApi(
|
||||||
PROCESS *proc, OBJECT_NAME_INFORMATION *Name, PORT_MESSAGE *msg);
|
PROCESS *proc, OBJECT_NAME_INFORMATION *Name, PORT_MESSAGE *msg);
|
||||||
|
|
||||||
static NTSTATUS Ipc_CheckPortRequest_Lsa(
|
NTSTATUS Ipc_CheckPortRequest_Lsa(
|
||||||
PROCESS *proc, OBJECT_NAME_INFORMATION *Name, PORT_MESSAGE *msg);
|
PROCESS *proc, OBJECT_NAME_INFORMATION *Name, PORT_MESSAGE *msg);
|
||||||
|
|
||||||
static NTSTATUS Ipc_CheckPortRequest_LsaEP(
|
NTSTATUS Ipc_CheckPortRequest_LsaEP(
|
||||||
PROCESS* proc, OBJECT_NAME_INFORMATION* Name, PORT_MESSAGE* msg);
|
PROCESS* proc, OBJECT_NAME_INFORMATION* Name, PORT_MESSAGE* msg);
|
||||||
|
|
||||||
static NTSTATUS Ipc_CheckPortRequest_PowerManagement(
|
NTSTATUS Ipc_CheckPortRequest_PowerManagement(
|
||||||
PROCESS *proc, OBJECT_NAME_INFORMATION *Name, PORT_MESSAGE *msg);
|
PROCESS *proc, OBJECT_NAME_INFORMATION *Name, PORT_MESSAGE *msg);
|
||||||
|
|
||||||
static NTSTATUS Ipc_CheckPortRequest_SpoolerPort(
|
NTSTATUS Ipc_CheckPortRequest_SpoolerPort(
|
||||||
PROCESS *proc, OBJECT_NAME_INFORMATION *Name, PORT_MESSAGE *msg);
|
PROCESS *proc, OBJECT_NAME_INFORMATION *Name, PORT_MESSAGE *msg);
|
||||||
|
|
||||||
|
|
||||||
|
static NTSTATUS Ipc_Api_GetRpcPortName_2(
|
||||||
|
PEPROCESS ProcessObject, WCHAR* pDstPortName);
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
// Variables
|
// Variables
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
static ULONG Ipc_MSV10_AuthPackageNumber = 0;
|
IPC_DYNAMIC_PORTS Ipc_Dynamic_Ports[NUM_DYNAMIC_PORTS];
|
||||||
|
|
||||||
|
static const WCHAR* _rpc_control = L"\\RPC Control";
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
@ -269,121 +262,6 @@ finish:
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
// Ipc_CheckPortRequest_SpoolerPort
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
|
|
||||||
// This routine is currently not used. We chose to block spooler CreateFile in the minifilter instead. But I (Curt) am keeping this code
|
|
||||||
// around because it demonstrates how to examine & filter RPC requests going to the spooler.
|
|
||||||
|
|
||||||
// todo: move this code to ipc_spl.c
|
|
||||||
|
|
||||||
BOOLEAN Ipc_Filter_Spooler_Msg(UCHAR uMsg);
|
|
||||||
|
|
||||||
_FX NTSTATUS Ipc_CheckPortRequest_SpoolerPort(
|
|
||||||
PROCESS *proc, OBJECT_NAME_INFORMATION *Name, PORT_MESSAGE *msg)
|
|
||||||
{
|
|
||||||
NTSTATUS status;
|
|
||||||
|
|
||||||
if (proc->ipc_openPrintSpooler) // see if we are not filtering spooler requests
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
|
|
||||||
//
|
|
||||||
// check that it is the spooler port
|
|
||||||
//
|
|
||||||
|
|
||||||
if (Driver_OsVersion >= DRIVER_WINDOWS_81) {
|
|
||||||
|
|
||||||
if (Name->Name.Length < 13 * sizeof(WCHAR))
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
|
|
||||||
BOOLEAN is_spooler = FALSE;
|
|
||||||
|
|
||||||
if (Ipc_Dynamic_Ports[SPOOLER_PORT].pPortLock)
|
|
||||||
{
|
|
||||||
KeEnterCriticalRegion();
|
|
||||||
ExAcquireResourceSharedLite(Ipc_Dynamic_Ports[SPOOLER_PORT].pPortLock, TRUE);
|
|
||||||
|
|
||||||
if (_wcsicmp(Name->Name.Buffer, Ipc_Dynamic_Ports[SPOOLER_PORT].wstrPortName) == 0)
|
|
||||||
{
|
|
||||||
// dynamic version of RPC ports, see also ipc_spl.c
|
|
||||||
// and RpcBindingFromStringBindingW in core/dll/rpcrt.c
|
|
||||||
is_spooler = TRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
ExReleaseResourceLite(Ipc_Dynamic_Ports[SPOOLER_PORT].pPortLock);
|
|
||||||
KeLeaveCriticalRegion();
|
|
||||||
}
|
|
||||||
|
|
||||||
if(!is_spooler)
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
}
|
|
||||||
else if (Driver_OsVersion >= DRIVER_WINDOWS_VISTA) {
|
|
||||||
|
|
||||||
if (_wcsicmp(Name->Name.Buffer, L"\\RPC Control\\spoolss") != 0)
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
|
|
||||||
} else
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
|
|
||||||
//
|
|
||||||
// examine message
|
|
||||||
//
|
|
||||||
|
|
||||||
status = STATUS_SUCCESS;
|
|
||||||
|
|
||||||
__try {
|
|
||||||
|
|
||||||
ProbeForRead(msg, sizeof(PORT_MESSAGE), sizeof(ULONG_PTR));
|
|
||||||
|
|
||||||
if (Driver_OsVersion >= DRIVER_WINDOWS_VISTA) {
|
|
||||||
|
|
||||||
//
|
|
||||||
//
|
|
||||||
|
|
||||||
ULONG len = msg->u1.s1.DataLength;
|
|
||||||
UCHAR *ptr = (UCHAR *)((UCHAR *)msg + sizeof(PORT_MESSAGE));
|
|
||||||
int i = 0;
|
|
||||||
int rc = -2;
|
|
||||||
|
|
||||||
ProbeForRead(ptr, len, sizeof(WCHAR));
|
|
||||||
|
|
||||||
/*if (ptr[20] == 17) { // RpcStartDocPrinter = Opnum 17
|
|
||||||
|
|
||||||
if (!proc->ipc_allowSpoolerPrintToFile)
|
|
||||||
{
|
|
||||||
status = STATUS_ACCESS_DENIED;
|
|
||||||
//for (i = 20; i < len - 12; i++)
|
|
||||||
//{
|
|
||||||
// rc = memcmp((void*)&(ptr[i]), "\4\0\0\0\0\0\0\0\4\0\0\0\0", 12); // search for marshaled "RAW" field length bytes
|
|
||||||
// if (rc == 0)
|
|
||||||
// {
|
|
||||||
// rc = _wcsnicmp((void*)&(ptr[i + 12]), L"raw", 3); // search for case insensitive "RAW"
|
|
||||||
// if (rc == 0)
|
|
||||||
// status = STATUS_ACCESS_DENIED;
|
|
||||||
// }
|
|
||||||
//}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (status == STATUS_ACCESS_DENIED)
|
|
||||||
Log_MsgP0(MSG_1319, proc->pid);
|
|
||||||
}
|
|
||||||
else*/
|
|
||||||
|
|
||||||
if (Ipc_Filter_Spooler_Msg(ptr[20]))
|
|
||||||
status = STATUS_ACCESS_DENIED;
|
|
||||||
|
|
||||||
//DbgPrint("Spooler IPC Port message ID: %d\n", (int)ptr[20]);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
} __except (EXCEPTION_EXECUTE_HANDLER) {
|
|
||||||
status = GetExceptionCode();
|
|
||||||
}
|
|
||||||
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
// Ipc_DisplayPowerMsg
|
// Ipc_DisplayPowerMsg
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
@ -543,6 +421,7 @@ _FX NTSTATUS Ipc_CheckPortRequest_PowerManagement(
|
||||||
return Status;
|
return Status;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
// Ipc_CheckPortRequest_WinApi
|
// Ipc_CheckPortRequest_WinApi
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
@ -625,174 +504,6 @@ _FX NTSTATUS Ipc_CheckPortRequest_WinApi(
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
// Ipc_CheckPortRequest_Lsa
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
|
|
||||||
|
|
||||||
_FX NTSTATUS Ipc_CheckPortRequest_Lsa(
|
|
||||||
PROCESS *proc, OBJECT_NAME_INFORMATION *Name, PORT_MESSAGE *msg)
|
|
||||||
{
|
|
||||||
NTSTATUS status;
|
|
||||||
|
|
||||||
if (! proc->ipc_block_password)
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
|
|
||||||
//
|
|
||||||
// check that it is \LsaAuthenticationPort
|
|
||||||
// or that it is \RPC Control\lsasspirpc (Windows 7 variant)
|
|
||||||
//
|
|
||||||
|
|
||||||
if (Name->Name.Length == 22 * sizeof(WCHAR)) {
|
|
||||||
|
|
||||||
if (_wcsicmp(Name->Name.Buffer, L"\\LsaAuthenticationPort") != 0)
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
|
|
||||||
} else if (Name->Name.Length == 23 * sizeof(WCHAR)) {
|
|
||||||
|
|
||||||
if (_wcsicmp(Name->Name.Buffer, L"\\RPC Control\\lsasspirpc") != 0)
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
|
|
||||||
} else
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
|
|
||||||
//
|
|
||||||
// examine message
|
|
||||||
//
|
|
||||||
|
|
||||||
status = STATUS_SUCCESS;
|
|
||||||
|
|
||||||
__try {
|
|
||||||
|
|
||||||
ProbeForRead(msg, sizeof(PORT_MESSAGE), sizeof(ULONG_PTR));
|
|
||||||
|
|
||||||
if (Driver_OsVersion >= DRIVER_WINDOWS_VISTA) {
|
|
||||||
|
|
||||||
//
|
|
||||||
// in Windows Vista and Windows 7, a password change request
|
|
||||||
// includes the WCHAR string Negotiate immediately followed
|
|
||||||
// by a non-zero WCHAR
|
|
||||||
//
|
|
||||||
|
|
||||||
WCHAR *ptr = (WCHAR *)((UCHAR *)msg + sizeof(PORT_MESSAGE));
|
|
||||||
ULONG len = msg->u1.s1.DataLength;
|
|
||||||
|
|
||||||
ProbeForRead(ptr, len, sizeof(WCHAR));
|
|
||||||
len /= sizeof(WCHAR);
|
|
||||||
|
|
||||||
while (len > 9 + 1) {
|
|
||||||
|
|
||||||
if (ptr[0] == L'N' && ptr[9] != 0
|
|
||||||
&& wmemcmp(ptr, L"Negotiate", 9) == 0) {
|
|
||||||
|
|
||||||
status = STATUS_ACCESS_DENIED;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
++ptr;
|
|
||||||
--len;
|
|
||||||
}
|
|
||||||
|
|
||||||
} else { // xp support
|
|
||||||
|
|
||||||
//
|
|
||||||
// prior to Windows Vista, we have a 'call package' api
|
|
||||||
// call (value 2), which identifies the MSV10 auth package,
|
|
||||||
// and a change password sub code (value 5)
|
|
||||||
//
|
|
||||||
|
|
||||||
if (msg->u1.s1.TotalLength >= sizeof(LSA_MESSAGE_XP)) {
|
|
||||||
|
|
||||||
LSA_MESSAGE_XP *msg2 = (LSA_MESSAGE_XP *)msg;
|
|
||||||
|
|
||||||
ProbeForRead(
|
|
||||||
msg2, sizeof(LSA_MESSAGE_XP), sizeof(ULONG_PTR));
|
|
||||||
|
|
||||||
if (msg2->api_code == 2 && // LsaCallAuthenticationPackage
|
|
||||||
msg2->auth_pkg_code == Ipc_MSV10_AuthPackageNumber &&
|
|
||||||
msg2->buf_len >= sizeof(ULONG)) {
|
|
||||||
|
|
||||||
ULONG *buf = msg2->buf;
|
|
||||||
ProbeForRead(buf, sizeof(ULONG), sizeof(ULONG));
|
|
||||||
|
|
||||||
if (*buf == 5) { // change password
|
|
||||||
|
|
||||||
status = STATUS_ACCESS_DENIED;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
} __except (EXCEPTION_EXECUTE_HANDLER) {
|
|
||||||
status = GetExceptionCode();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (status == STATUS_ACCESS_DENIED)
|
|
||||||
Log_Msg_Process(MSG_PASSWORD_CHANGE_DENIED, NULL, NULL, -1, proc->pid);
|
|
||||||
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
// Ipc_CheckPortRequest_LsaEP
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
|
|
||||||
// todo: move the lsa code to code to ipc_lsa.c
|
|
||||||
|
|
||||||
BOOLEAN Ipc_Filter_Lsa_Ep_Msg(UCHAR uMsg);
|
|
||||||
|
|
||||||
_FX NTSTATUS Ipc_CheckPortRequest_LsaEP(
|
|
||||||
PROCESS* proc, OBJECT_NAME_INFORMATION* Name, PORT_MESSAGE* msg)
|
|
||||||
{
|
|
||||||
NTSTATUS status;
|
|
||||||
|
|
||||||
if (proc->ipc_open_lsa_endpoint)
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
|
|
||||||
if (Name->Name.Length == 28 * sizeof(WCHAR)) {
|
|
||||||
|
|
||||||
if (_wcsicmp(Name->Name.Buffer, L"\\RPC Control\\LSARPC_ENDPOINT") != 0)
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
|
|
||||||
}
|
|
||||||
else
|
|
||||||
return STATUS_BAD_INITIAL_PC;
|
|
||||||
|
|
||||||
//
|
|
||||||
// examine message
|
|
||||||
//
|
|
||||||
|
|
||||||
status = STATUS_SUCCESS;
|
|
||||||
|
|
||||||
__try {
|
|
||||||
|
|
||||||
ProbeForRead(msg, sizeof(PORT_MESSAGE), sizeof(ULONG_PTR));
|
|
||||||
|
|
||||||
if (Driver_OsVersion >= DRIVER_WINDOWS_7) {
|
|
||||||
|
|
||||||
ULONG len = msg->u1.s1.DataLength;
|
|
||||||
UCHAR* ptr = (UCHAR*)((UCHAR*)msg + sizeof(PORT_MESSAGE));
|
|
||||||
int i = 0;
|
|
||||||
int rc = -2;
|
|
||||||
|
|
||||||
ProbeForRead(ptr, len, sizeof(WCHAR));
|
|
||||||
|
|
||||||
if (Ipc_Filter_Lsa_Ep_Msg(ptr[20]))
|
|
||||||
status = STATUS_ACCESS_DENIED;
|
|
||||||
|
|
||||||
//DbgPrint("\\RPC Control\\LSARPC_ENDPOINT message ID: %d\n", (int)ptr[20]);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
__except (EXCEPTION_EXECUTE_HANDLER) {
|
|
||||||
status = GetExceptionCode();
|
|
||||||
}
|
|
||||||
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
// Ipc_ImpersonatePort
|
// Ipc_ImpersonatePort
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
@ -856,6 +567,288 @@ _FX NTSTATUS Ipc_AlpcSendWaitReceivePort(
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
// Ipc_Api_OpenDynamicPort
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
// Param 1 is dynamic port name (e.g. "\RPC Control\LRPC-f760d5b40689a98168"), WCHAR[DYNAMIC_PORT_NAME_CHARS]
|
||||||
|
// Param 2 is the process PID for which to open the port, can be 0 when port is special
|
||||||
|
// Param 3 is the port type/identifier, can be -1 indicating non special port
|
||||||
|
|
||||||
|
_FX NTSTATUS Ipc_Api_OpenDynamicPort(PROCESS* proc, ULONG64* parms)
|
||||||
|
{
|
||||||
|
NTSTATUS status = STATUS_SUCCESS;
|
||||||
|
//KIRQL irql;
|
||||||
|
API_OPEN_DYNAMIC_PORT_ARGS* pArgs = (API_OPEN_DYNAMIC_PORT_ARGS*)parms;
|
||||||
|
WCHAR portName[DYNAMIC_PORT_NAME_CHARS];
|
||||||
|
|
||||||
|
if (proc) // is caller sandboxed?
|
||||||
|
return STATUS_ACCESS_DENIED;
|
||||||
|
|
||||||
|
//if (PsGetCurrentProcessId() != Api_ServiceProcessId)
|
||||||
|
// return STATUS_ACCESS_DENIED;
|
||||||
|
|
||||||
|
ENUM_DYNAMIC_PORT_TYPE ePortType = NUM_DYNAMIC_PORTS;
|
||||||
|
//if (pArgs->port_type.val == -1)
|
||||||
|
// ePortType = NUM_DYNAMIC_PORTS;
|
||||||
|
//else
|
||||||
|
if (pArgs->port_type.val <= NUM_DYNAMIC_PORTS)
|
||||||
|
ePortType = (ENUM_DYNAMIC_PORT_TYPE)pArgs->port_type.val;
|
||||||
|
//else
|
||||||
|
// return STATUS_INVALID_PARAMETER;
|
||||||
|
|
||||||
|
if (pArgs->port_name.val == NULL)
|
||||||
|
return STATUS_INVALID_PARAMETER;
|
||||||
|
try {
|
||||||
|
ProbeForRead(pArgs->port_name.val, sizeof(WCHAR) * DYNAMIC_PORT_NAME_CHARS, sizeof(WCHAR));
|
||||||
|
wmemcpy(portName, pArgs->port_name.val, DYNAMIC_PORT_NAME_CHARS - 1);
|
||||||
|
portName[DYNAMIC_PORT_NAME_CHARS - 1] = L'\0';
|
||||||
|
}
|
||||||
|
__except (EXCEPTION_EXECUTE_HANDLER) {
|
||||||
|
status = GetExceptionCode();
|
||||||
|
}
|
||||||
|
if (!NT_SUCCESS(status))
|
||||||
|
return status;
|
||||||
|
|
||||||
|
//
|
||||||
|
// When this is a special port save it our global Ipc_Dynamic_Ports structure
|
||||||
|
//
|
||||||
|
|
||||||
|
if (ePortType != NUM_DYNAMIC_PORTS && Ipc_Dynamic_Ports[ePortType].pPortLock)
|
||||||
|
{
|
||||||
|
KeEnterCriticalRegion();
|
||||||
|
ExAcquireResourceExclusiveLite(Ipc_Dynamic_Ports[ePortType].pPortLock, TRUE);
|
||||||
|
|
||||||
|
wmemcpy(Ipc_Dynamic_Ports[ePortType].wstrPortName, portName, DYNAMIC_PORT_NAME_CHARS);
|
||||||
|
|
||||||
|
ExReleaseResourceLite(Ipc_Dynamic_Ports[ePortType].pPortLock);
|
||||||
|
KeLeaveCriticalRegion();
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// Open the port for the selected process
|
||||||
|
//
|
||||||
|
|
||||||
|
if (pArgs->process_id.val != 0)
|
||||||
|
{
|
||||||
|
//proc = Process_Find(pArgs->process_id.val, &irql);
|
||||||
|
proc = Process_Find(pArgs->process_id.val, NULL);
|
||||||
|
if (proc && (proc != PROCESS_TERMINATED))
|
||||||
|
{
|
||||||
|
KIRQL irql2;
|
||||||
|
|
||||||
|
KeRaiseIrql(APC_LEVEL, &irql2);
|
||||||
|
ExAcquireResourceExclusiveLite(proc->ipc_lock, TRUE);
|
||||||
|
|
||||||
|
Process_AddPath(proc, &proc->open_ipc_paths, NULL, FALSE, portName, FALSE);
|
||||||
|
|
||||||
|
ExReleaseResourceLite(proc->ipc_lock);
|
||||||
|
KeLowerIrql(irql2);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
status = STATUS_NOT_FOUND;
|
||||||
|
//ExReleaseResourceLite(Process_ListLock);
|
||||||
|
//KeLowerIrql(irql);
|
||||||
|
}
|
||||||
|
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
// Ipc_Api_GetDynamicPortFromPid
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
// Param 1 is the service PID
|
||||||
|
// Param 2 will return the port name with "\RPC Control\" prepended
|
||||||
|
|
||||||
|
_FX NTSTATUS Ipc_Api_GetDynamicPortFromPid(PROCESS* proc, ULONG64* parms)
|
||||||
|
{
|
||||||
|
NTSTATUS status;
|
||||||
|
PEPROCESS ProcessObject;
|
||||||
|
//BOOLEAN done = FALSE;
|
||||||
|
API_GET_DYNAMIC_PORT_FROM_PID_ARGS* pArgs = (API_GET_DYNAMIC_PORT_FROM_PID_ARGS*)parms;
|
||||||
|
|
||||||
|
if (proc) // is caller sandboxed?
|
||||||
|
return STATUS_ACCESS_DENIED;
|
||||||
|
|
||||||
|
//
|
||||||
|
// this function determines the dynamic RPC endpoint that is used by a service/process
|
||||||
|
//
|
||||||
|
|
||||||
|
status = PsLookupProcessByProcessId(pArgs->process_id.val, &ProcessObject);
|
||||||
|
|
||||||
|
if (NT_SUCCESS(status)) {
|
||||||
|
|
||||||
|
//if (PsGetProcessSessionId(ProcessObject) == 0) {
|
||||||
|
//
|
||||||
|
// void *nbuf;
|
||||||
|
// ULONG nlen;
|
||||||
|
// WCHAR *nptr;
|
||||||
|
//
|
||||||
|
// Process_GetProcessName(
|
||||||
|
// Driver_Pool, (ULONG_PTR)pArgs->process_id.val, &nbuf, &nlen, &nptr);
|
||||||
|
//
|
||||||
|
// if (nbuf) {
|
||||||
|
//
|
||||||
|
// if (_wcsicmp(nptr, pArgs->exe_name.val) == 0
|
||||||
|
// && MyIsProcessRunningAsSystemAccount(pArgs->process_id.val)) {
|
||||||
|
|
||||||
|
status = Ipc_Api_GetRpcPortName_2(ProcessObject, pArgs->full_port_name.val);
|
||||||
|
|
||||||
|
// done = TRUE;
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// Mem_Free(nbuf, nlen);
|
||||||
|
// }
|
||||||
|
//}
|
||||||
|
|
||||||
|
ObDereferenceObject(ProcessObject);
|
||||||
|
}
|
||||||
|
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
// Ipc_Api_GetRpcPortName_2
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
_FX NTSTATUS Ipc_Api_GetRpcPortName_2(PEPROCESS ProcessObject, WCHAR* pDstPortName)
|
||||||
|
{
|
||||||
|
NTSTATUS status;
|
||||||
|
ULONG len, dummy_len;
|
||||||
|
ULONG context;
|
||||||
|
HANDLE handle;
|
||||||
|
OBJECT_DIRECTORY_INFORMATION* info;
|
||||||
|
void* buf, * PortObject;
|
||||||
|
UNICODE_STRING objname;
|
||||||
|
OBJECT_ATTRIBUTES objattrs;
|
||||||
|
WCHAR name[DYNAMIC_PORT_NAME_CHARS];
|
||||||
|
|
||||||
|
InitializeObjectAttributes(&objattrs,
|
||||||
|
&objname, OBJ_CASE_INSENSITIVE | OBJ_KERNEL_HANDLE, NULL, NULL);
|
||||||
|
|
||||||
|
RtlInitUnicodeString(&objname, _rpc_control);
|
||||||
|
|
||||||
|
status = ZwOpenDirectoryObject(&handle, 0, &objattrs);
|
||||||
|
|
||||||
|
if (!NT_SUCCESS(status))
|
||||||
|
return status;
|
||||||
|
|
||||||
|
//
|
||||||
|
// get a list of all objects in the system
|
||||||
|
//
|
||||||
|
|
||||||
|
len = 0;
|
||||||
|
while (1) {
|
||||||
|
|
||||||
|
len += PAGE_SIZE * 2;
|
||||||
|
buf = ExAllocatePoolWithTag(PagedPool, len, tzuk);
|
||||||
|
if (!buf) {
|
||||||
|
status = STATUS_INSUFFICIENT_RESOURCES;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
dummy_len = 0;
|
||||||
|
status = ZwQueryDirectoryObject(
|
||||||
|
handle, buf, len, FALSE, TRUE, &context, &dummy_len);
|
||||||
|
|
||||||
|
if (status == STATUS_MORE_ENTRIES || status == STATUS_INFO_LENGTH_MISMATCH)
|
||||||
|
{
|
||||||
|
ExFreePoolWithTag(buf, tzuk);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!NT_SUCCESS(status))
|
||||||
|
return status;
|
||||||
|
|
||||||
|
//
|
||||||
|
// go through list looking for LRPC-* objects of type ALPC Port
|
||||||
|
//
|
||||||
|
|
||||||
|
info = (OBJECT_DIRECTORY_INFORMATION*)buf;
|
||||||
|
while (1) {
|
||||||
|
|
||||||
|
UNICODE_STRING* ObjName = &info->ObjectName;
|
||||||
|
UNICODE_STRING* TypeName = &info->ObjectTypeName;
|
||||||
|
|
||||||
|
if ((!ObjName->Buffer) && (!TypeName->Buffer))
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (TypeName->Length == 9 * sizeof(WCHAR) && TypeName->Buffer
|
||||||
|
&& _wcsicmp(TypeName->Buffer, L"ALPC Port") == 0) {
|
||||||
|
|
||||||
|
if ((ObjName->Length > 5 * sizeof(WCHAR)) &&
|
||||||
|
(ObjName->Length < 64 * sizeof(WCHAR)) &&
|
||||||
|
_wcsnicmp(ObjName->Buffer, L"LRPC-", 5) == 0) {
|
||||||
|
|
||||||
|
swprintf(name, L"%s\\%s", _rpc_control, ObjName->Buffer);
|
||||||
|
|
||||||
|
RtlInitUnicodeString(&objname, name);
|
||||||
|
|
||||||
|
status = ObReferenceObjectByName(
|
||||||
|
&objname, OBJ_CASE_INSENSITIVE, NULL, 0,
|
||||||
|
*LpcPortObjectType, KernelMode, NULL,
|
||||||
|
&PortObject);
|
||||||
|
|
||||||
|
if (NT_SUCCESS(status)) {
|
||||||
|
|
||||||
|
//
|
||||||
|
// make sure the owner process for the LRPC-* port
|
||||||
|
// is the process that was specified as a parameter
|
||||||
|
//
|
||||||
|
|
||||||
|
struct {
|
||||||
|
LIST_ENTRY PortListEntry;
|
||||||
|
void* CommunicationInfo;
|
||||||
|
PEPROCESS OwnerProcess;
|
||||||
|
} *AlpcPortObject = PortObject;
|
||||||
|
|
||||||
|
if (AlpcPortObject->OwnerProcess == ProcessObject) {
|
||||||
|
|
||||||
|
__try {
|
||||||
|
|
||||||
|
if (pDstPortName)
|
||||||
|
{
|
||||||
|
ProbeForWrite(pDstPortName, sizeof(WCHAR) * DYNAMIC_PORT_NAME_CHARS, sizeof(WCHAR));
|
||||||
|
wmemcpy(pDstPortName, name, DYNAMIC_PORT_NAME_CHARS - 1);
|
||||||
|
pDstPortName[DYNAMIC_PORT_NAME_CHARS - 1] = L'\0';
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
__except (EXCEPTION_EXECUTE_HANDLER) {
|
||||||
|
status = GetExceptionCode();
|
||||||
|
}
|
||||||
|
|
||||||
|
ObDereferenceObject(PortObject);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
ObDereferenceObject(PortObject);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
++info;
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// release storage
|
||||||
|
//
|
||||||
|
|
||||||
|
ExFreePoolWithTag(buf, tzuk);
|
||||||
|
|
||||||
|
ZwClose(handle);
|
||||||
|
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
//
|
//
|
||||||
// 32-bit hooks for Windows XP
|
// 32-bit hooks for Windows XP
|
||||||
|
@ -871,32 +864,6 @@ _FX NTSTATUS Ipc_AlpcSendWaitReceivePort(
|
||||||
#ifndef _WIN64
|
#ifndef _WIN64
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
// Ipc_Api_SetLsaAuthPkg
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
|
|
||||||
|
|
||||||
_FX NTSTATUS Ipc_Api_SetLsaAuthPkg(PROCESS *proc, ULONG64 *parms)
|
|
||||||
{
|
|
||||||
//
|
|
||||||
// caller must be our service process
|
|
||||||
//
|
|
||||||
|
|
||||||
if (proc || (PsGetCurrentProcessId() != Api_ServiceProcessId))
|
|
||||||
return STATUS_ACCESS_DENIED;
|
|
||||||
|
|
||||||
//
|
|
||||||
// collect msv10 auth package number
|
|
||||||
//
|
|
||||||
|
|
||||||
if (Ipc_MSV10_AuthPackageNumber)
|
|
||||||
return STATUS_ACCESS_DENIED;
|
|
||||||
|
|
||||||
Ipc_MSV10_AuthPackageNumber = (ULONG)parms[1];
|
|
||||||
return STATUS_SUCCESS;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
// IPC_PORT_HEADER
|
// IPC_PORT_HEADER
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|
|
@ -33,17 +33,9 @@
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
static NTSTATUS Ipc_Api_GetRpcPortName_2(PEPROCESS ProcessObject, WCHAR *pDstPortName);
|
BOOLEAN Ipc_Filter_Spooler_Msg(PROCESS* proc, UCHAR uMsg);
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
// Variables
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
|
|
||||||
IPC_DYNAMIC_PORTS Ipc_Dynamic_Ports[NUM_DYNAMIC_PORTS];
|
|
||||||
|
|
||||||
static const WCHAR *_rpc_control = L"\\RPC Control";
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
// Ipc_Api_AllowSpoolerPrintToFile
|
// Ipc_Api_AllowSpoolerPrintToFile
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
@ -67,278 +59,112 @@ static const WCHAR *_rpc_control = L"\\RPC Control";
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
// Ipc_Api_OpenDynamicPort
|
// Ipc_CheckPortRequest_SpoolerPort
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
// Param 1 is dynamic port name (e.g. "\RPC Control\LRPC-f760d5b40689a98168"), WCHAR[DYNAMIC_PORT_NAME_CHARS]
|
|
||||||
// Param 2 is the process PID for which to open the port
|
|
||||||
// Param 3 is the port type/identifier, can be -1 indicating non special port
|
|
||||||
|
|
||||||
_FX NTSTATUS Ipc_Api_OpenDynamicPort(PROCESS* proc, ULONG64* parms)
|
_FX NTSTATUS Ipc_CheckPortRequest_SpoolerPort(
|
||||||
|
PROCESS* proc, OBJECT_NAME_INFORMATION* Name, PORT_MESSAGE* msg)
|
||||||
{
|
{
|
||||||
NTSTATUS status = STATUS_SUCCESS;
|
NTSTATUS status;
|
||||||
//KIRQL irql;
|
|
||||||
API_OPEN_DYNAMIC_PORT_ARGS* pArgs = (API_OPEN_DYNAMIC_PORT_ARGS*)parms;
|
|
||||||
WCHAR portName[DYNAMIC_PORT_NAME_CHARS];
|
|
||||||
|
|
||||||
if (proc) // is caller sandboxed?
|
if (proc->ipc_openPrintSpooler) // see if we are not filtering spooler requests
|
||||||
return STATUS_ACCESS_DENIED;
|
return STATUS_BAD_INITIAL_PC;
|
||||||
|
|
||||||
//if (PsGetCurrentProcessId() != Api_ServiceProcessId)
|
//
|
||||||
// return STATUS_ACCESS_DENIED;
|
// check that it is the spooler port
|
||||||
|
//
|
||||||
|
|
||||||
ENUM_DYNAMIC_PORT_TYPE ePortType = NUM_DYNAMIC_PORTS;
|
if (Driver_OsVersion >= DRIVER_WINDOWS_81) {
|
||||||
//if (pArgs->port_type.val == -1)
|
|
||||||
// ePortType = NUM_DYNAMIC_PORTS;
|
if (Name->Name.Length < 13 * sizeof(WCHAR))
|
||||||
//else
|
return STATUS_BAD_INITIAL_PC;
|
||||||
if (pArgs->port_type.val <= NUM_DYNAMIC_PORTS)
|
|
||||||
ePortType = (ENUM_DYNAMIC_PORT_TYPE)pArgs->port_type.val;
|
BOOLEAN is_spooler = FALSE;
|
||||||
//else
|
|
||||||
// return STATUS_INVALID_PARAMETER;
|
if (Ipc_Dynamic_Ports[SPOOLER_PORT].pPortLock)
|
||||||
|
{
|
||||||
|
KeEnterCriticalRegion();
|
||||||
|
ExAcquireResourceSharedLite(Ipc_Dynamic_Ports[SPOOLER_PORT].pPortLock, TRUE);
|
||||||
|
|
||||||
|
if (_wcsicmp(Name->Name.Buffer, Ipc_Dynamic_Ports[SPOOLER_PORT].wstrPortName) == 0)
|
||||||
|
{
|
||||||
|
// dynamic version of RPC ports, see also ipc_spl.c
|
||||||
|
// and RpcBindingFromStringBindingW in core/dll/rpcrt.c
|
||||||
|
is_spooler = TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
ExReleaseResourceLite(Ipc_Dynamic_Ports[SPOOLER_PORT].pPortLock);
|
||||||
|
KeLeaveCriticalRegion();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!is_spooler)
|
||||||
|
return STATUS_BAD_INITIAL_PC;
|
||||||
|
}
|
||||||
|
else if (Driver_OsVersion >= DRIVER_WINDOWS_VISTA) {
|
||||||
|
|
||||||
|
if (_wcsicmp(Name->Name.Buffer, L"\\RPC Control\\spoolss") != 0)
|
||||||
|
return STATUS_BAD_INITIAL_PC;
|
||||||
|
|
||||||
|
}
|
||||||
|
else
|
||||||
|
return STATUS_BAD_INITIAL_PC;
|
||||||
|
|
||||||
|
//
|
||||||
|
// examine message
|
||||||
|
//
|
||||||
|
|
||||||
|
status = STATUS_SUCCESS;
|
||||||
|
|
||||||
|
__try {
|
||||||
|
|
||||||
|
ProbeForRead(msg, sizeof(PORT_MESSAGE), sizeof(ULONG_PTR));
|
||||||
|
|
||||||
|
if (Driver_OsVersion >= DRIVER_WINDOWS_VISTA) {
|
||||||
|
|
||||||
|
//
|
||||||
|
//
|
||||||
|
|
||||||
|
ULONG len = msg->u1.s1.DataLength;
|
||||||
|
UCHAR* ptr = (UCHAR*)((UCHAR*)msg + sizeof(PORT_MESSAGE));
|
||||||
|
int i = 0;
|
||||||
|
int rc = -2;
|
||||||
|
|
||||||
|
ProbeForRead(ptr, len, sizeof(WCHAR));
|
||||||
|
|
||||||
|
/*if (ptr[20] == 17) { // RpcStartDocPrinter = Opnum 17
|
||||||
|
|
||||||
|
if (!proc->ipc_allowSpoolerPrintToFile)
|
||||||
|
{
|
||||||
|
status = STATUS_ACCESS_DENIED;
|
||||||
|
//for (i = 20; i < len - 12; i++)
|
||||||
|
//{
|
||||||
|
// rc = memcmp((void*)&(ptr[i]), "\4\0\0\0\0\0\0\0\4\0\0\0\0", 12); // search for marshaled "RAW" field length bytes
|
||||||
|
// if (rc == 0)
|
||||||
|
// {
|
||||||
|
// rc = _wcsnicmp((void*)&(ptr[i + 12]), L"raw", 3); // search for case insensitive "RAW"
|
||||||
|
// if (rc == 0)
|
||||||
|
// status = STATUS_ACCESS_DENIED;
|
||||||
|
// }
|
||||||
|
//}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (status == STATUS_ACCESS_DENIED)
|
||||||
|
Log_MsgP0(MSG_1319, proc->pid);
|
||||||
|
}
|
||||||
|
else*/
|
||||||
|
|
||||||
|
if (Ipc_Filter_Spooler_Msg(proc, ptr[20]))
|
||||||
|
status = STATUS_ACCESS_DENIED;
|
||||||
|
|
||||||
|
//DbgPrint("Spooler IPC Port message ID: %d\n", (int)ptr[20]);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
if(pArgs->port_name.val == NULL)
|
|
||||||
return STATUS_INVALID_PARAMETER;
|
|
||||||
try {
|
|
||||||
ProbeForRead(pArgs->port_name.val, sizeof(WCHAR) * DYNAMIC_PORT_NAME_CHARS, sizeof(WCHAR));
|
|
||||||
wmemcpy(portName, pArgs->port_name.val, DYNAMIC_PORT_NAME_CHARS - 1);
|
|
||||||
portName[DYNAMIC_PORT_NAME_CHARS - 1] = L'\0';
|
|
||||||
}
|
}
|
||||||
__except (EXCEPTION_EXECUTE_HANDLER) {
|
__except (EXCEPTION_EXECUTE_HANDLER) {
|
||||||
status = GetExceptionCode();
|
status = GetExceptionCode();
|
||||||
}
|
}
|
||||||
if (!NT_SUCCESS(status))
|
|
||||||
return status;
|
|
||||||
|
|
||||||
//proc = Process_Find(pArgs->process_id.val, &irql);
|
|
||||||
proc = Process_Find(pArgs->process_id.val, NULL);
|
|
||||||
if (proc && (proc != PROCESS_TERMINATED))
|
|
||||||
{
|
|
||||||
//
|
|
||||||
// When this is a special port save it our global Ipc_Dynamic_Ports structure
|
|
||||||
//
|
|
||||||
|
|
||||||
if (ePortType != NUM_DYNAMIC_PORTS && Ipc_Dynamic_Ports[ePortType].pPortLock)
|
|
||||||
{
|
|
||||||
KeEnterCriticalRegion();
|
|
||||||
ExAcquireResourceExclusiveLite(Ipc_Dynamic_Ports[ePortType].pPortLock, TRUE);
|
|
||||||
|
|
||||||
wmemcpy(Ipc_Dynamic_Ports[ePortType].wstrPortName, portName, DYNAMIC_PORT_NAME_CHARS);
|
|
||||||
|
|
||||||
ExReleaseResourceLite(Ipc_Dynamic_Ports[ePortType].pPortLock);
|
|
||||||
KeLeaveCriticalRegion();
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Open the port for the selected process
|
|
||||||
//
|
|
||||||
|
|
||||||
KIRQL irql2;
|
|
||||||
|
|
||||||
KeRaiseIrql(APC_LEVEL, &irql2);
|
|
||||||
ExAcquireResourceExclusiveLite(proc->ipc_lock, TRUE);
|
|
||||||
|
|
||||||
Process_AddPath(proc, &proc->open_ipc_paths, NULL, FALSE, portName, FALSE);
|
|
||||||
|
|
||||||
ExReleaseResourceLite(proc->ipc_lock);
|
|
||||||
KeLowerIrql(irql2);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
status = STATUS_NOT_FOUND;
|
|
||||||
//ExReleaseResourceLite(Process_ListLock);
|
|
||||||
//KeLowerIrql(irql);
|
|
||||||
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
// Ipc_Api_GetDynamicPortFromPid
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
|
|
||||||
// Param 1 is the service PID
|
|
||||||
// Param 2 will return the port name with "\RPC Control\" prepended
|
|
||||||
|
|
||||||
_FX NTSTATUS Ipc_Api_GetDynamicPortFromPid(PROCESS *proc, ULONG64 *parms)
|
|
||||||
{
|
|
||||||
NTSTATUS status;
|
|
||||||
PEPROCESS ProcessObject;
|
|
||||||
//BOOLEAN done = FALSE;
|
|
||||||
API_GET_DYNAMIC_PORT_FROM_PID_ARGS *pArgs = (API_GET_DYNAMIC_PORT_FROM_PID_ARGS *)parms;
|
|
||||||
|
|
||||||
if (proc) // is caller sandboxed?
|
|
||||||
return STATUS_ACCESS_DENIED;
|
|
||||||
|
|
||||||
//
|
|
||||||
// this function determines the dynamic RPC endpoint that is used by a service/process
|
|
||||||
//
|
|
||||||
|
|
||||||
status = PsLookupProcessByProcessId(pArgs->process_id.val, &ProcessObject);
|
|
||||||
|
|
||||||
if (NT_SUCCESS(status)) {
|
|
||||||
|
|
||||||
//if (PsGetProcessSessionId(ProcessObject) == 0) {
|
|
||||||
//
|
|
||||||
// void *nbuf;
|
|
||||||
// ULONG nlen;
|
|
||||||
// WCHAR *nptr;
|
|
||||||
//
|
|
||||||
// Process_GetProcessName(
|
|
||||||
// Driver_Pool, (ULONG_PTR)pArgs->process_id.val, &nbuf, &nlen, &nptr);
|
|
||||||
//
|
|
||||||
// if (nbuf) {
|
|
||||||
//
|
|
||||||
// if (_wcsicmp(nptr, pArgs->exe_name.val) == 0
|
|
||||||
// && MyIsProcessRunningAsSystemAccount(pArgs->process_id.val)) {
|
|
||||||
|
|
||||||
status = Ipc_Api_GetRpcPortName_2(ProcessObject, pArgs->full_port_name.val);
|
|
||||||
|
|
||||||
// done = TRUE;
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// Mem_Free(nbuf, nlen);
|
|
||||||
// }
|
|
||||||
//}
|
|
||||||
|
|
||||||
ObDereferenceObject(ProcessObject);
|
|
||||||
}
|
|
||||||
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
// Ipc_Api_GetRpcPortName_2
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
|
|
||||||
|
|
||||||
_FX NTSTATUS Ipc_Api_GetRpcPortName_2(PEPROCESS ProcessObject, WCHAR *pDstPortName)
|
|
||||||
{
|
|
||||||
NTSTATUS status;
|
|
||||||
ULONG len, dummy_len;
|
|
||||||
ULONG context;
|
|
||||||
HANDLE handle;
|
|
||||||
OBJECT_DIRECTORY_INFORMATION *info;
|
|
||||||
void *buf, *PortObject;
|
|
||||||
UNICODE_STRING objname;
|
|
||||||
OBJECT_ATTRIBUTES objattrs;
|
|
||||||
WCHAR name[DYNAMIC_PORT_NAME_CHARS];
|
|
||||||
|
|
||||||
InitializeObjectAttributes(&objattrs,
|
|
||||||
&objname, OBJ_CASE_INSENSITIVE | OBJ_KERNEL_HANDLE, NULL, NULL);
|
|
||||||
|
|
||||||
RtlInitUnicodeString(&objname, _rpc_control);
|
|
||||||
|
|
||||||
status = ZwOpenDirectoryObject(&handle, 0, &objattrs);
|
|
||||||
|
|
||||||
if (!NT_SUCCESS(status))
|
|
||||||
return status;
|
|
||||||
|
|
||||||
//
|
|
||||||
// get a list of all objects in the system
|
|
||||||
//
|
|
||||||
|
|
||||||
len = 0;
|
|
||||||
while (1) {
|
|
||||||
|
|
||||||
len += PAGE_SIZE * 2;
|
|
||||||
buf = ExAllocatePoolWithTag(PagedPool, len, tzuk);
|
|
||||||
if (!buf) {
|
|
||||||
status = STATUS_INSUFFICIENT_RESOURCES;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
dummy_len = 0;
|
|
||||||
status = ZwQueryDirectoryObject(
|
|
||||||
handle, buf, len, FALSE, TRUE, &context, &dummy_len);
|
|
||||||
|
|
||||||
if (status == STATUS_MORE_ENTRIES || status == STATUS_INFO_LENGTH_MISMATCH)
|
|
||||||
{
|
|
||||||
ExFreePoolWithTag(buf, tzuk);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!NT_SUCCESS(status))
|
|
||||||
return status;
|
|
||||||
|
|
||||||
//
|
|
||||||
// go through list looking for LRPC-* objects of type ALPC Port
|
|
||||||
//
|
|
||||||
|
|
||||||
info = (OBJECT_DIRECTORY_INFORMATION *)buf;
|
|
||||||
while (1) {
|
|
||||||
|
|
||||||
UNICODE_STRING *ObjName = &info->ObjectName;
|
|
||||||
UNICODE_STRING *TypeName = &info->ObjectTypeName;
|
|
||||||
|
|
||||||
if ((!ObjName->Buffer) && (!TypeName->Buffer))
|
|
||||||
break;
|
|
||||||
|
|
||||||
if (TypeName->Length == 9 * sizeof(WCHAR) && TypeName->Buffer
|
|
||||||
&& _wcsicmp(TypeName->Buffer, L"ALPC Port") == 0) {
|
|
||||||
|
|
||||||
if ((ObjName->Length > 5 * sizeof(WCHAR)) &&
|
|
||||||
(ObjName->Length < 64 * sizeof(WCHAR)) &&
|
|
||||||
_wcsnicmp(ObjName->Buffer, L"LRPC-", 5) == 0) {
|
|
||||||
|
|
||||||
swprintf(name, L"%s\\%s", _rpc_control, ObjName->Buffer);
|
|
||||||
|
|
||||||
RtlInitUnicodeString(&objname, name);
|
|
||||||
|
|
||||||
status = ObReferenceObjectByName(
|
|
||||||
&objname, OBJ_CASE_INSENSITIVE, NULL, 0,
|
|
||||||
*LpcPortObjectType, KernelMode, NULL,
|
|
||||||
&PortObject);
|
|
||||||
|
|
||||||
if (NT_SUCCESS(status)) {
|
|
||||||
|
|
||||||
//
|
|
||||||
// make sure the owner process for the LRPC-* port
|
|
||||||
// is the process that was specified as a parameter
|
|
||||||
//
|
|
||||||
|
|
||||||
struct {
|
|
||||||
LIST_ENTRY PortListEntry;
|
|
||||||
void *CommunicationInfo;
|
|
||||||
PEPROCESS OwnerProcess;
|
|
||||||
} *AlpcPortObject = PortObject;
|
|
||||||
|
|
||||||
if (AlpcPortObject->OwnerProcess == ProcessObject) {
|
|
||||||
|
|
||||||
__try {
|
|
||||||
|
|
||||||
if (pDstPortName)
|
|
||||||
{
|
|
||||||
ProbeForWrite(pDstPortName, sizeof(WCHAR) * DYNAMIC_PORT_NAME_CHARS, sizeof(WCHAR));
|
|
||||||
wmemcpy(pDstPortName, name, DYNAMIC_PORT_NAME_CHARS - 1);
|
|
||||||
pDstPortName[DYNAMIC_PORT_NAME_CHARS - 1] = L'\0';
|
|
||||||
}
|
|
||||||
|
|
||||||
} __except (EXCEPTION_EXECUTE_HANDLER) {
|
|
||||||
status = GetExceptionCode();
|
|
||||||
}
|
|
||||||
|
|
||||||
ObDereferenceObject(PortObject);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
ObDereferenceObject(PortObject);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
++info;
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// release storage
|
|
||||||
//
|
|
||||||
|
|
||||||
ExFreePoolWithTag(buf, tzuk);
|
|
||||||
|
|
||||||
ZwClose(handle);
|
|
||||||
|
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
@ -349,7 +175,7 @@ _FX NTSTATUS Ipc_Api_GetRpcPortName_2(PEPROCESS ProcessObject, WCHAR *pDstPortNa
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
_FX BOOLEAN Ipc_Filter_Spooler_Msg(UCHAR uMsg)
|
_FX BOOLEAN Ipc_Filter_Spooler_Msg(PROCESS* proc, UCHAR uMsg)
|
||||||
{
|
{
|
||||||
BOOLEAN filter = FALSE;
|
BOOLEAN filter = FALSE;
|
||||||
|
|
||||||
|
@ -471,12 +297,23 @@ _FX BOOLEAN Ipc_Filter_Spooler_Msg(UCHAR uMsg)
|
||||||
filter = TRUE;
|
filter = TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Session_MonitorCount) {
|
if (Session_MonitorCount && (proc->ipc_trace & (TRACE_ALLOW | TRACE_DENY))) {
|
||||||
|
|
||||||
WCHAR access_str[24];
|
USHORT mon_type = MONITOR_IPC;
|
||||||
swprintf(access_str, L" Msg: %02X", (ULONG)uMsg);
|
|
||||||
const WCHAR* strings[3] = { L"\\RPC Control\\spoolss", access_str, NULL };
|
if (filter && (proc->ipc_trace & TRACE_DENY))
|
||||||
Session_MonitorPutEx(MONITOR_IPC | (filter ? MONITOR_DENY : MONITOR_OPEN), strings, PsGetCurrentProcessId());
|
mon_type |= MONITOR_DENY;
|
||||||
|
else if (!filter && (proc->ipc_trace & TRACE_ALLOW))
|
||||||
|
mon_type |= MONITOR_OPEN;
|
||||||
|
else
|
||||||
|
mon_type = 0;
|
||||||
|
|
||||||
|
if (mon_type) {
|
||||||
|
WCHAR msg_str[24];
|
||||||
|
swprintf(msg_str, L" Msg: %02X", (ULONG)uMsg);
|
||||||
|
const WCHAR* strings[3] = { L"\\RPC Control\\spoolss", msg_str, NULL };
|
||||||
|
Session_MonitorPutEx(mon_type, strings, NULL, PsGetCurrentProcessId());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return filter;
|
return filter;
|
||||||
|
|
|
@ -463,15 +463,26 @@ _FX NTSTATUS Key_MyParseProc_2(OBJ_PARSE_PROC_ARGS_2)
|
||||||
letter = 0;
|
letter = 0;
|
||||||
|
|
||||||
if (letter) {
|
if (letter) {
|
||||||
|
|
||||||
|
USHORT mon_type = MONITOR_KEY;
|
||||||
|
if (!IsBoxedPath) {
|
||||||
|
if (ShouldMonitorAccess == TRUE)
|
||||||
|
mon_type |= MONITOR_DENY;
|
||||||
|
else
|
||||||
|
mon_type |= MONITOR_OPEN;
|
||||||
|
}
|
||||||
|
if (!ShouldMonitorAccess)
|
||||||
|
mon_type |= MONITOR_TRACE;
|
||||||
|
|
||||||
swprintf(access_str, L"(K%c) %08X",
|
swprintf(access_str, L"(K%c) %08X",
|
||||||
letter, AccessState->OriginalDesiredAccess);
|
letter, AccessState->OriginalDesiredAccess);
|
||||||
Log_Debug_Msg(MONITOR_FILE_OR_KEY, access_str, Name->Name.Buffer);
|
Log_Debug_Msg(mon_type, access_str, Name->Name.Buffer);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ShouldMonitorAccess) {
|
else if (ShouldMonitorAccess) {
|
||||||
|
|
||||||
Session_MonitorPut(MONITOR_FILE_OR_KEY | MONITOR_DENY, Name->Name.Buffer, proc->pid);
|
Session_MonitorPut(MONITOR_KEY | MONITOR_DENY, Name->Name.Buffer, proc->pid);
|
||||||
}
|
}
|
||||||
|
|
||||||
Mem_Free(Name, NameLength);
|
Mem_Free(Name, NameLength);
|
||||||
|
|
|
@ -174,13 +174,14 @@ _FX NTSTATUS Key_Callback(void *Context, void *Arg1, void *Arg2)
|
||||||
REG_SET_VALUE_KEY_INFORMATION *pSetInfo = (REG_SET_VALUE_KEY_INFORMATION*)Arg2;
|
REG_SET_VALUE_KEY_INFORMATION *pSetInfo = (REG_SET_VALUE_KEY_INFORMATION*)Arg2;
|
||||||
status = Key_StoreValue(proc, pSetInfo, spid);
|
status = Key_StoreValue(proc, pSetInfo, spid);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
// we only handle RegNtPreCreateKeyEx and RegNtPreOpenKeyEx events before windows 10 CU
|
// we only handle RegNtPreCreateKeyEx and RegNtPreOpenKeyEx events
|
||||||
//
|
//
|
||||||
|
|
||||||
if (NotifyEvent != RegNtPreCreateKeyEx &&
|
if (NotifyEvent != RegNtPreCreateKeyEx &&
|
||||||
NotifyEvent != RegNtPreOpenKeyEx) {
|
NotifyEvent != RegNtPreOpenKeyEx) {
|
||||||
return status;
|
return status;
|
||||||
|
@ -189,12 +190,11 @@ _FX NTSTATUS Key_Callback(void *Context, void *Arg1, void *Arg2)
|
||||||
//
|
//
|
||||||
// check if the caller is sandboxed before proceeding
|
// check if the caller is sandboxed before proceeding
|
||||||
//
|
//
|
||||||
if (Driver_OsBuild < DRIVER_BUILD_WINDOWS_10_CU)
|
|
||||||
{
|
|
||||||
proc = Process_Find(NULL, NULL);
|
proc = Process_Find(NULL, NULL);
|
||||||
if (proc == PROCESS_TERMINATED)
|
if (proc == PROCESS_TERMINATED)
|
||||||
return STATUS_PROCESS_IS_TERMINATING;
|
return STATUS_PROCESS_IS_TERMINATING;
|
||||||
}
|
|
||||||
Info = (REG_OPEN_CREATE_KEY_INFORMATION_VISTA *)Arg2;
|
Info = (REG_OPEN_CREATE_KEY_INFORMATION_VISTA *)Arg2;
|
||||||
|
|
||||||
// HACK ALERT! If you click a link in a Word doc, it will try to start an embedded IE, which cannot be forced into Sandboxie.
|
// HACK ALERT! If you click a link in a Word doc, it will try to start an embedded IE, which cannot be forced into Sandboxie.
|
||||||
|
|
|
@ -337,6 +337,6 @@ _FX void Log_Debug_Msg(USHORT type, const WCHAR *string1, const WCHAR *string2)
|
||||||
if (Session_MonitorCount) {
|
if (Session_MonitorCount) {
|
||||||
|
|
||||||
const WCHAR* strings[4] = { string1, L" ", string2, NULL };
|
const WCHAR* strings[4] = { string1, L" ", string2, NULL };
|
||||||
Session_MonitorPutEx(type | MONITOR_TRACE, strings, PsGetCurrentProcessId());
|
Session_MonitorPutEx(type, strings, NULL, PsGetCurrentProcessId());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -695,6 +695,7 @@ _FX PROCESS *Process_Create(
|
||||||
// initialize trace flags
|
// initialize trace flags
|
||||||
//
|
//
|
||||||
|
|
||||||
|
proc->call_trace = Process_GetTraceFlag(proc, L"CallTrace");
|
||||||
proc->file_trace = Process_GetTraceFlag(proc, L"FileTrace");
|
proc->file_trace = Process_GetTraceFlag(proc, L"FileTrace");
|
||||||
proc->pipe_trace = Process_GetTraceFlag(proc, L"PipeTrace");
|
proc->pipe_trace = Process_GetTraceFlag(proc, L"PipeTrace");
|
||||||
proc->key_trace = Process_GetTraceFlag(proc, L"KeyTrace");
|
proc->key_trace = Process_GetTraceFlag(proc, L"KeyTrace");
|
||||||
|
|
|
@ -121,6 +121,8 @@ struct _PROCESS {
|
||||||
|
|
||||||
UCHAR create_console_flag;
|
UCHAR create_console_flag;
|
||||||
|
|
||||||
|
ULONG call_trace;
|
||||||
|
|
||||||
// file-related
|
// file-related
|
||||||
|
|
||||||
PERESOURCE file_lock;
|
PERESOURCE file_lock;
|
||||||
|
|
|
@ -579,7 +579,7 @@ _FX BOOLEAN Session_IsForceDisabled(ULONG SessionId)
|
||||||
_FX void Session_MonitorPut(USHORT type, const WCHAR *name, HANDLE pid)
|
_FX void Session_MonitorPut(USHORT type, const WCHAR *name, HANDLE pid)
|
||||||
{
|
{
|
||||||
const WCHAR* strings[2] = { name, NULL };
|
const WCHAR* strings[2] = { name, NULL };
|
||||||
Session_MonitorPutEx(type, strings, pid);
|
Session_MonitorPutEx(type, strings, NULL, pid);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -588,7 +588,7 @@ _FX void Session_MonitorPut(USHORT type, const WCHAR *name, HANDLE pid)
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
_FX void Session_MonitorPutEx(USHORT type, const WCHAR** strings, HANDLE pid)
|
_FX void Session_MonitorPutEx(USHORT type, const WCHAR** strings, ULONG* lengths, HANDLE pid)
|
||||||
{
|
{
|
||||||
SESSION *session;
|
SESSION *session;
|
||||||
KIRQL irql;
|
KIRQL irql;
|
||||||
|
@ -601,8 +601,8 @@ _FX void Session_MonitorPutEx(USHORT type, const WCHAR** strings, HANDLE pid)
|
||||||
|
|
||||||
ULONG64 pid64 = (ULONG64)pid;
|
ULONG64 pid64 = (ULONG64)pid;
|
||||||
SIZE_T data_len = 0;
|
SIZE_T data_len = 0;
|
||||||
for(const WCHAR** string = strings; *string != NULL; string++)
|
for(int i=0; strings[i] != NULL; i++)
|
||||||
data_len += wcslen(*string) * sizeof(WCHAR);
|
data_len += (lengths ? lengths [i] : wcslen(strings[i])) * sizeof(WCHAR);
|
||||||
|
|
||||||
//[Type 2][PID 8][Data n*2]
|
//[Type 2][PID 8][Data n*2]
|
||||||
SIZE_T entry_size = 2 + 8 + data_len;
|
SIZE_T entry_size = 2 + 8 + data_len;
|
||||||
|
@ -613,8 +613,8 @@ _FX void Session_MonitorPutEx(USHORT type, const WCHAR** strings, HANDLE pid)
|
||||||
log_buffer_push_bytes((CHAR*)&pid64, 8, &write_ptr, session->monitor_log);
|
log_buffer_push_bytes((CHAR*)&pid64, 8, &write_ptr, session->monitor_log);
|
||||||
|
|
||||||
// join strings seamlessly
|
// join strings seamlessly
|
||||||
for (const WCHAR** string = strings; *string != NULL; string++)
|
for (int i = 0; strings[i] != NULL; i++)
|
||||||
log_buffer_push_bytes((CHAR*)*string, wcslen(*string) * sizeof(WCHAR), &write_ptr, session->monitor_log);
|
log_buffer_push_bytes((CHAR*)strings[i], (lengths ? lengths[i] : wcslen(strings[i])) * sizeof(WCHAR), &write_ptr, session->monitor_log);
|
||||||
}
|
}
|
||||||
else // this can only happen when the entire buffer is to small to hold this one entry
|
else // this can only happen when the entire buffer is to small to hold this one entry
|
||||||
Log_Msg0(MSG_MONITOR_OVERFLOW);
|
Log_Msg0(MSG_MONITOR_OVERFLOW);
|
||||||
|
@ -721,8 +721,6 @@ _FX NTSTATUS Session_Api_MonitorPut(PROCESS *proc, ULONG64 *parms)
|
||||||
_FX NTSTATUS Session_Api_MonitorPut2(PROCESS *proc, ULONG64 *parms)
|
_FX NTSTATUS Session_Api_MonitorPut2(PROCESS *proc, ULONG64 *parms)
|
||||||
{
|
{
|
||||||
API_MONITOR_PUT2_ARGS *args = (API_MONITOR_PUT2_ARGS *)parms;
|
API_MONITOR_PUT2_ARGS *args = (API_MONITOR_PUT2_ARGS *)parms;
|
||||||
UNICODE_STRING objname;
|
|
||||||
void *object;
|
|
||||||
USHORT *log_type;
|
USHORT *log_type;
|
||||||
WCHAR *log_data;
|
WCHAR *log_data;
|
||||||
WCHAR *name;
|
WCHAR *name;
|
||||||
|
@ -745,12 +743,12 @@ _FX NTSTATUS Session_Api_MonitorPut2(PROCESS *proc, ULONG64 *parms)
|
||||||
log_len = args->log_len.val / sizeof(WCHAR);
|
log_len = args->log_len.val / sizeof(WCHAR);
|
||||||
if (!log_len)
|
if (!log_len)
|
||||||
return STATUS_INVALID_PARAMETER;
|
return STATUS_INVALID_PARAMETER;
|
||||||
if (log_len > 256) // truncate as we only have 260 in buffer
|
if (log_len > 1024) // truncate as we only have 1028 in buffer
|
||||||
log_len = 256;
|
log_len = 1024;
|
||||||
log_data = args->log_ptr.val;
|
log_data = args->log_ptr.val;
|
||||||
ProbeForRead(log_data, log_len * sizeof(WCHAR), sizeof(WCHAR));
|
ProbeForRead(log_data, log_len * sizeof(WCHAR), sizeof(WCHAR));
|
||||||
|
|
||||||
name = Mem_Alloc(proc->pool, 260 * sizeof(WCHAR)); // todo: should we increase this ?
|
name = Mem_Alloc(proc->pool, 1028 * sizeof(WCHAR)); // todo: should we increase this ?
|
||||||
if (! name)
|
if (! name)
|
||||||
return STATUS_INSUFFICIENT_RESOURCES;
|
return STATUS_INSUFFICIENT_RESOURCES;
|
||||||
|
|
||||||
|
@ -765,7 +763,11 @@ _FX NTSTATUS Session_Api_MonitorPut2(PROCESS *proc, ULONG64 *parms)
|
||||||
name[log_len] = L'\0';
|
name[log_len] = L'\0';
|
||||||
|
|
||||||
status = STATUS_SUCCESS;
|
status = STATUS_SUCCESS;
|
||||||
object = NULL;
|
|
||||||
|
if (args->check_object_exists.val64 && ((type & MONITOR_TRACE) == 0)) { // do not check objects if this is a trace entry
|
||||||
|
|
||||||
|
UNICODE_STRING objname;
|
||||||
|
void* object = NULL;
|
||||||
|
|
||||||
//
|
//
|
||||||
// if type is MONITOR_IPC we try to open the object
|
// if type is MONITOR_IPC we try to open the object
|
||||||
|
@ -803,8 +805,6 @@ _FX NTSTATUS Session_Api_MonitorPut2(PROCESS *proc, ULONG64 *parms)
|
||||||
|
|
||||||
if ((type & 0xFFF) == MONITOR_PIPE) {
|
if ((type & 0xFFF) == MONITOR_PIPE) {
|
||||||
|
|
||||||
if (args->check_object_exists.val64)
|
|
||||||
{
|
|
||||||
OBJECT_ATTRIBUTES objattrs;
|
OBJECT_ATTRIBUTES objattrs;
|
||||||
IO_STATUS_BLOCK IoStatusBlock;
|
IO_STATUS_BLOCK IoStatusBlock;
|
||||||
HANDLE handle;
|
HANDLE handle;
|
||||||
|
@ -844,7 +844,6 @@ _FX NTSTATUS Session_Api_MonitorPut2(PROCESS *proc, ULONG64 *parms)
|
||||||
|
|
||||||
//DbgPrint("PIPE Status3 = %08X Object = %08X for Open <%S>\n", status, object, name);
|
//DbgPrint("PIPE Status3 = %08X Object = %08X for Open <%S>\n", status, object, name);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
//
|
//
|
||||||
// if we have an object, get its name from the kernel object
|
// if we have an object, get its name from the kernel object
|
||||||
|
@ -861,8 +860,8 @@ _FX NTSTATUS Session_Api_MonitorPut2(PROCESS *proc, ULONG64 *parms)
|
||||||
if (NT_SUCCESS(status)) {
|
if (NT_SUCCESS(status)) {
|
||||||
|
|
||||||
log_len = Name->Name.Length / sizeof(WCHAR);
|
log_len = Name->Name.Length / sizeof(WCHAR);
|
||||||
if (log_len > 256) // truncate as we only have 260 in buffer
|
if (log_len > 1024) // truncate as we only have 1028 in buffer
|
||||||
log_len = 256;
|
log_len = 1024;
|
||||||
wmemcpy(name, Name->Name.Buffer, log_len);
|
wmemcpy(name, Name->Name.Buffer, log_len);
|
||||||
name[log_len] = L'\0';
|
name[log_len] = L'\0';
|
||||||
|
|
||||||
|
@ -875,6 +874,8 @@ _FX NTSTATUS Session_Api_MonitorPut2(PROCESS *proc, ULONG64 *parms)
|
||||||
ObDereferenceObject(object);
|
ObDereferenceObject(object);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
} __except (EXCEPTION_EXECUTE_HANDLER) {
|
} __except (EXCEPTION_EXECUTE_HANDLER) {
|
||||||
status = GetExceptionCode();
|
status = GetExceptionCode();
|
||||||
}
|
}
|
||||||
|
|
|
@ -44,7 +44,7 @@ BOOLEAN Session_IsForceDisabled(ULONG SessionId);
|
||||||
|
|
||||||
void Session_MonitorPut(USHORT type, const WCHAR *name, HANDLE pid);
|
void Session_MonitorPut(USHORT type, const WCHAR *name, HANDLE pid);
|
||||||
|
|
||||||
void Session_MonitorPutEx(USHORT type, const WCHAR** strings, HANDLE pid);
|
void Session_MonitorPutEx(USHORT type, const WCHAR** strings, ULONG* lengths, HANDLE pid);
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|
|
@ -27,6 +27,7 @@
|
||||||
#include "obj.h"
|
#include "obj.h"
|
||||||
#include "api.h"
|
#include "api.h"
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
|
#include "session.h"
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -741,6 +742,7 @@ _FX NTSTATUS Syscall_Api_Invoke(PROCESS *proc, ULONG64 *parms)
|
||||||
|
|
||||||
__try {
|
__try {
|
||||||
|
|
||||||
|
BOOLEAN traced = FALSE;
|
||||||
const ULONG args_len = entry->param_count * sizeof(ULONG_PTR);
|
const ULONG args_len = entry->param_count * sizeof(ULONG_PTR);
|
||||||
#ifdef _WIN64
|
#ifdef _WIN64
|
||||||
ProbeForRead(user_args, args_len, sizeof(ULONG_PTR));
|
ProbeForRead(user_args, args_len, sizeof(ULONG_PTR));
|
||||||
|
@ -774,20 +776,20 @@ _FX NTSTATUS Syscall_Api_Invoke(PROCESS *proc, ULONG64 *parms)
|
||||||
ProbeForRead(user_args, args_len, sizeof(UCHAR));
|
ProbeForRead(user_args, args_len, sizeof(UCHAR));
|
||||||
#endif _WIN64
|
#endif _WIN64
|
||||||
|
|
||||||
/*
|
|
||||||
if (proc->ipc_trace & (TRACE_ALLOW | TRACE_DENY))
|
//if (proc->ipc_trace & (TRACE_ALLOW | TRACE_DENY))
|
||||||
{
|
//{
|
||||||
if (strcmp(entry->name, "AlpcSendWaitReceivePort") == 0)
|
// if (strcmp(entry->name, "AlpcSendWaitReceivePort") == 0)
|
||||||
{
|
// {
|
||||||
HANDLE hConnection;
|
// HANDLE hConnection;
|
||||||
hConnection = (HANDLE*)user_args[0];
|
// hConnection = (HANDLE*)user_args[0];
|
||||||
DbgPrintEx(DPFLTR_DEFAULT_ID, DPFLTR_ERROR_LEVEL, "SBIE [syscall] p=%06d t=%06d - %s, handle = %X >>>>>>\n",
|
// DbgPrintEx(DPFLTR_DEFAULT_ID, DPFLTR_ERROR_LEVEL, "SBIE [syscall] p=%06d t=%06d - %s, handle = %X >>>>>>\n",
|
||||||
PsGetCurrentProcessId(), PsGetCurrentThreadId(),
|
// PsGetCurrentProcessId(), PsGetCurrentThreadId(),
|
||||||
entry->name,
|
// entry->name,
|
||||||
hConnection);
|
// hConnection);
|
||||||
}
|
// }
|
||||||
}
|
//}
|
||||||
*/
|
|
||||||
|
|
||||||
if (entry->handler1_func) {
|
if (entry->handler1_func) {
|
||||||
|
|
||||||
|
@ -802,17 +804,20 @@ _FX NTSTATUS Syscall_Api_Invoke(PROCESS *proc, ULONG64 *parms)
|
||||||
|
|
||||||
if (proc->ipc_trace & (TRACE_ALLOW | TRACE_DENY))
|
if (proc->ipc_trace & (TRACE_ALLOW | TRACE_DENY))
|
||||||
{
|
{
|
||||||
|
HANDLE hConnection = NULL;
|
||||||
|
UNICODE_STRING* puStr = NULL;
|
||||||
|
|
||||||
if ((strcmp(entry->name, "ConnectPort") == 0) ||
|
if ((strcmp(entry->name, "ConnectPort") == 0) ||
|
||||||
(strcmp(entry->name, "AlpcConnectPort") == 0) )
|
(strcmp(entry->name, "AlpcConnectPort") == 0) )
|
||||||
{
|
{
|
||||||
HANDLE hConnection = *(HANDLE*)user_args[0];
|
hConnection = *(HANDLE*)user_args[0];
|
||||||
UNICODE_STRING *puStr = (UNICODE_STRING*)user_args[1];
|
puStr = (UNICODE_STRING*)user_args[1];
|
||||||
|
|
||||||
DbgPrintEx(DPFLTR_DEFAULT_ID, DPFLTR_INFO_LEVEL, "SBIE [syscall] p=%06d t=%06d - %s, '%.*S', status = 0x%X, handle = %X\n",
|
//DbgPrintEx(DPFLTR_DEFAULT_ID, DPFLTR_INFO_LEVEL, "SBIE [syscall] p=%06d t=%06d - %s, '%.*S', status = 0x%X, handle = %X\n",
|
||||||
PsGetCurrentProcessId(), PsGetCurrentThreadId(),
|
// PsGetCurrentProcessId(), PsGetCurrentThreadId(),
|
||||||
entry->name,
|
// entry->name,
|
||||||
(puStr->Length / 2), puStr->Buffer,
|
// (puStr->Length / 2), puStr->Buffer,
|
||||||
status, hConnection);
|
// status, hConnection);
|
||||||
//if (puStr && puStr->Buffer && wcsstr(puStr->Buffer, L"\\RPC Control\\LRPC-"))
|
//if (puStr && puStr->Buffer && wcsstr(puStr->Buffer, L"\\RPC Control\\LRPC-"))
|
||||||
//{
|
//{
|
||||||
//int i = 0; // place breakpoint here if you want to debug a particular port
|
//int i = 0; // place breakpoint here if you want to debug a particular port
|
||||||
|
@ -821,17 +826,16 @@ _FX NTSTATUS Syscall_Api_Invoke(PROCESS *proc, ULONG64 *parms)
|
||||||
else if ( (strcmp(entry->name, "AlpcCreatePort") == 0) ||
|
else if ( (strcmp(entry->name, "AlpcCreatePort") == 0) ||
|
||||||
(strcmp(entry->name, "AlpcConnectPortEx") == 0) )
|
(strcmp(entry->name, "AlpcConnectPortEx") == 0) )
|
||||||
{
|
{
|
||||||
HANDLE hConnection = *(HANDLE*)user_args[0];
|
hConnection = *(HANDLE*)user_args[0];
|
||||||
POBJECT_ATTRIBUTES pObjectAttributes = (POBJECT_ATTRIBUTES)user_args[1];
|
POBJECT_ATTRIBUTES pObjectAttributes = (POBJECT_ATTRIBUTES)user_args[1];
|
||||||
UNICODE_STRING *puStr = NULL;
|
|
||||||
if (pObjectAttributes)
|
if (pObjectAttributes)
|
||||||
puStr = (UNICODE_STRING*)pObjectAttributes->ObjectName;
|
puStr = (UNICODE_STRING*)pObjectAttributes->ObjectName;
|
||||||
|
|
||||||
DbgPrintEx(DPFLTR_DEFAULT_ID, DPFLTR_INFO_LEVEL, "SBIE [syscall] p=%06d t=%06d - %s, '%.*S', status = 0x%X, handle = %X\n",
|
//DbgPrintEx(DPFLTR_DEFAULT_ID, DPFLTR_INFO_LEVEL, "SBIE [syscall] p=%06d t=%06d - %s, '%.*S', status = 0x%X, handle = %X\n",
|
||||||
PsGetCurrentProcessId(), PsGetCurrentThreadId(),
|
// PsGetCurrentProcessId(), PsGetCurrentThreadId(),
|
||||||
entry->name,
|
// entry->name,
|
||||||
(puStr->Length / 2), puStr->Buffer,
|
// (puStr->Length / 2), puStr->Buffer,
|
||||||
status, hConnection);
|
// status, hConnection);
|
||||||
}
|
}
|
||||||
else if ((strcmp(entry->name, "ReplyWaitReceivePort") == 0) ||
|
else if ((strcmp(entry->name, "ReplyWaitReceivePort") == 0) ||
|
||||||
(strcmp(entry->name, "ReceiveMessagePort") == 0) ||
|
(strcmp(entry->name, "ReceiveMessagePort") == 0) ||
|
||||||
|
@ -841,12 +845,37 @@ _FX NTSTATUS Syscall_Api_Invoke(PROCESS *proc, ULONG64 *parms)
|
||||||
// these 2 APIs will generate a lot of output if we don't check status
|
// these 2 APIs will generate a lot of output if we don't check status
|
||||||
((status != STATUS_SUCCESS) && ((strcmp(entry->name, "AlpcSendWaitReceivePort") == 0) || (strcmp(entry->name, "RequestWaitReplyPort") == 0))) )
|
((status != STATUS_SUCCESS) && ((strcmp(entry->name, "AlpcSendWaitReceivePort") == 0) || (strcmp(entry->name, "RequestWaitReplyPort") == 0))) )
|
||||||
{
|
{
|
||||||
HANDLE hConnection = (HANDLE*)user_args[0];
|
hConnection = (HANDLE*)user_args[0];
|
||||||
DbgPrintEx(DPFLTR_DEFAULT_ID, DPFLTR_INFO_LEVEL, "SBIE [syscall] p=%06d t=%06d - %s, status = 0x%X, handle = %X\n",
|
|
||||||
PsGetCurrentProcessId(), PsGetCurrentThreadId(),
|
//DbgPrintEx(DPFLTR_DEFAULT_ID, DPFLTR_INFO_LEVEL, "SBIE [syscall] p=%06d t=%06d - %s, status = 0x%X, handle = %X\n",
|
||||||
entry->name,
|
// PsGetCurrentProcessId(), PsGetCurrentThreadId(),
|
||||||
status, hConnection);
|
// entry->name,
|
||||||
|
// status, hConnection);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (hConnection)
|
||||||
|
{
|
||||||
|
WCHAR trace_str[128];
|
||||||
|
swprintf(trace_str, L"[syscall] t=%06d - %.*S, status = 0x%X, handle = %X; ", //59 chars + entry->name
|
||||||
|
PsGetCurrentThreadId(),
|
||||||
|
max(strlen(entry->name), 64), entry->name,
|
||||||
|
status, hConnection);
|
||||||
|
const WCHAR* strings[3] = { trace_str, puStr ? puStr->Buffer : NULL, NULL };
|
||||||
|
ULONG lengths[3] = { wcslen(trace_str), puStr ? puStr->Length / 2 : 0, 0 };
|
||||||
|
Session_MonitorPutEx(MONITOR_IPC | MONITOR_TRACE, strings, lengths, PsGetCurrentProcessId());
|
||||||
|
traced = TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!traced && ((proc->call_trace & TRACE_ALLOW) || ((status != STATUS_SUCCESS) && (proc->call_trace & TRACE_DENY))))
|
||||||
|
{
|
||||||
|
WCHAR trace_str[128];
|
||||||
|
swprintf(trace_str, L"[syscall] t=%06d - %.*S, status = 0x%X", //59 chars + entry->name
|
||||||
|
PsGetCurrentThreadId(),
|
||||||
|
max(strlen(entry->name), 64), entry->name,
|
||||||
|
status);
|
||||||
|
const WCHAR* strings[2] = { trace_str, NULL };
|
||||||
|
Session_MonitorPutEx(MONITOR_SYSCALL | MONITOR_TRACE, strings, NULL, PsGetCurrentProcessId());
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef _WIN64
|
#ifdef _WIN64
|
||||||
|
|
|
@ -37,7 +37,7 @@ static HANDLE Syscall_RestoreTargetHandle(
|
||||||
|
|
||||||
static NTSTATUS Syscall_CheckObject(
|
static NTSTATUS Syscall_CheckObject(
|
||||||
PROCESS *proc, SYSCALL_ENTRY *syscall_entry,
|
PROCESS *proc, SYSCALL_ENTRY *syscall_entry,
|
||||||
void *OpenedObject, OBJECT_HANDLE_INFORMATION *HandleInfo);
|
void *OpenedObject, OBJECT_HANDLE_INFORMATION *HandleInfo, PUNICODE_STRING puName);
|
||||||
|
|
||||||
static NTSTATUS Syscall_DuplicateHandle_2(
|
static NTSTATUS Syscall_DuplicateHandle_2(
|
||||||
HANDLE TargetProcessHandle, HANDLE TargetHandle,
|
HANDLE TargetProcessHandle, HANDLE TargetHandle,
|
||||||
|
@ -178,7 +178,7 @@ _FX HANDLE Syscall_RestoreTargetHandle(
|
||||||
|
|
||||||
_FX NTSTATUS Syscall_CheckObject(
|
_FX NTSTATUS Syscall_CheckObject(
|
||||||
PROCESS *proc, SYSCALL_ENTRY *syscall_entry,
|
PROCESS *proc, SYSCALL_ENTRY *syscall_entry,
|
||||||
void *OpenedObject, OBJECT_HANDLE_INFORMATION *HandleInfo)
|
void *OpenedObject, OBJECT_HANDLE_INFORMATION *HandleInfo, PUNICODE_STRING puName)
|
||||||
{
|
{
|
||||||
OBJECT_NAME_INFORMATION *Name;
|
OBJECT_NAME_INFORMATION *Name;
|
||||||
ULONG NameLength;
|
ULONG NameLength;
|
||||||
|
@ -194,9 +194,12 @@ _FX NTSTATUS Syscall_CheckObject(
|
||||||
if ((status != STATUS_SUCCESS)
|
if ((status != STATUS_SUCCESS)
|
||||||
&& (status != STATUS_BAD_INITIAL_PC)) {
|
&& (status != STATUS_BAD_INITIAL_PC)) {
|
||||||
|
|
||||||
|
if (puName == NULL && Name != NULL && Name->Name.Length != 0)
|
||||||
|
puName = &Name->Name;
|
||||||
|
|
||||||
WCHAR msg[256];
|
WCHAR msg[256];
|
||||||
swprintf(msg, L"%S (%08X) access=%08X initialized=%d", syscall_entry->name, status, HandleInfo->GrantedAccess, proc->initialized);
|
swprintf(msg, L"%S (%08X) access=%08X initialized=%d", syscall_entry->name, status, HandleInfo->GrantedAccess, proc->initialized);
|
||||||
Log_Msg_Process(MSG_2101, msg, Name != NULL ? Name->Name.Buffer : L"Unnamed object", -1, proc->pid);
|
Log_Msg_Process(MSG_2101, msg, puName != NULL ? puName->Buffer : L"Unnamed object", -1, proc->pid);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Name != &Obj_Unnamed)
|
if (Name != &Obj_Unnamed)
|
||||||
|
@ -269,6 +272,10 @@ _FX NTSTATUS Syscall_OpenHandle(
|
||||||
|
|
||||||
if (! NewHandle) {
|
if (! NewHandle) {
|
||||||
|
|
||||||
|
//WCHAR trace_str[128];
|
||||||
|
//swprintf(trace_str, L"Syscall %.*S security violation terminating process", max(strlen(syscall_entry->name), 64), syscall_entry->name);
|
||||||
|
//Session_MonitorPut(MONITOR_OTHER, trace_str, PsGetCurrentProcessId());
|
||||||
|
|
||||||
Process_SetTerminated(proc, 6);
|
Process_SetTerminated(proc, 6);
|
||||||
status = STATUS_PROCESS_IS_TERMINATING;
|
status = STATUS_PROCESS_IS_TERMINATING;
|
||||||
}
|
}
|
||||||
|
@ -289,15 +296,26 @@ _FX NTSTATUS Syscall_OpenHandle(
|
||||||
|
|
||||||
if (NT_SUCCESS(status)) {
|
if (NT_SUCCESS(status)) {
|
||||||
|
|
||||||
|
PUNICODE_STRING puName = NULL;
|
||||||
|
|
||||||
|
if ((strcmp(syscall_entry->name, "ConnectPort") == 0) ||
|
||||||
|
(strcmp(syscall_entry->name, "AlpcConnectPort") == 0))
|
||||||
|
{
|
||||||
|
puName = (UNICODE_STRING*)user_args[1];
|
||||||
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
// check the access that was granted to the object
|
// check the access that was granted to the object
|
||||||
//
|
//
|
||||||
|
|
||||||
status = Syscall_CheckObject(
|
status = Syscall_CheckObject(
|
||||||
proc, syscall_entry, OpenedObject, &HandleInfo);
|
proc, syscall_entry, OpenedObject, &HandleInfo, puName);
|
||||||
|
|
||||||
ObDereferenceObject(OpenedObject);
|
ObDereferenceObject(OpenedObject);
|
||||||
|
|
||||||
|
if (!NT_SUCCESS(status))
|
||||||
|
NtClose(NewHandle);
|
||||||
|
|
||||||
if (status == STATUS_BAD_INITIAL_PC) {
|
if (status == STATUS_BAD_INITIAL_PC) {
|
||||||
|
|
||||||
//
|
//
|
||||||
|
@ -327,8 +345,14 @@ _FX NTSTATUS Syscall_OpenHandle(
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (! NT_SUCCESS(status))
|
if (!NT_SUCCESS(status)) {
|
||||||
|
|
||||||
|
//WCHAR trace_str[128];
|
||||||
|
//swprintf(trace_str, L"Syscall %.*S security violation, status = 0x%X, terminating process", max(strlen(syscall_entry->name), 64), syscall_entry->name, status);
|
||||||
|
//Session_MonitorPut(MONITOR_OTHER, trace_str, PsGetCurrentProcessId());
|
||||||
|
|
||||||
Process_SetTerminated(proc, 7);
|
Process_SetTerminated(proc, 7);
|
||||||
|
}
|
||||||
|
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
@ -447,6 +471,10 @@ _FX NTSTATUS Syscall_DuplicateHandle(
|
||||||
|
|
||||||
if (! NewHandle) {
|
if (! NewHandle) {
|
||||||
|
|
||||||
|
//WCHAR trace_str[128];
|
||||||
|
//swprintf(trace_str, L"Syscall %.*S security violation terminating process", max(strlen(syscall_entry->name), 64), syscall_entry->name);
|
||||||
|
//Session_MonitorPut(MONITOR_OTHER, trace_str, PsGetCurrentProcessId());
|
||||||
|
|
||||||
Process_SetTerminated(proc, 8);
|
Process_SetTerminated(proc, 8);
|
||||||
status = STATUS_PROCESS_IS_TERMINATING;
|
status = STATUS_PROCESS_IS_TERMINATING;
|
||||||
}
|
}
|
||||||
|
@ -506,6 +534,11 @@ _FX NTSTATUS Syscall_DuplicateHandle(
|
||||||
// if(!wcsicmp(proc->image_name,L"SandboxieBITS.exe") && status == STATUS_ACCESS_DENIED) {
|
// if(!wcsicmp(proc->image_name,L"SandboxieBITS.exe") && status == STATUS_ACCESS_DENIED) {
|
||||||
// return status;
|
// return status;
|
||||||
// }
|
// }
|
||||||
|
//
|
||||||
|
// //WCHAR trace_str[128];
|
||||||
|
// //swprintf(trace_str, L"Syscall %.*S security violation terminating process", max(strlen(syscall_entry->name), 64), syscall_entry->name);
|
||||||
|
// //Session_MonitorPut(MONITOR_OTHER, trace_str, PsGetCurrentProcessId());
|
||||||
|
//
|
||||||
// Process_SetTerminated(proc, 9);
|
// Process_SetTerminated(proc, 9);
|
||||||
//}
|
//}
|
||||||
|
|
||||||
|
@ -633,7 +666,7 @@ _FX NTSTATUS Syscall_DuplicateHandle_2(
|
||||||
//
|
//
|
||||||
|
|
||||||
status = Syscall_CheckObject(
|
status = Syscall_CheckObject(
|
||||||
proc, syscall_entry, OpenedObject, &HandleInfo);
|
proc, syscall_entry, OpenedObject, &HandleInfo, NULL);
|
||||||
|
|
||||||
} else if ( TypeLength == 5 * sizeof(WCHAR)
|
} else if ( TypeLength == 5 * sizeof(WCHAR)
|
||||||
&& wmemcmp(TypeBuffer, L"Token", 5) == 0) {
|
&& wmemcmp(TypeBuffer, L"Token", 5) == 0) {
|
||||||
|
|
|
@ -1060,7 +1060,7 @@ trace:
|
||||||
if (Letter2) {
|
if (Letter2) {
|
||||||
swprintf(str, L"(%c%c) %08X %06d",
|
swprintf(str, L"(%c%c) %08X %06d",
|
||||||
Letter1, Letter2, GrantedAccess, (int)pid);
|
Letter1, Letter2, GrantedAccess, (int)pid);
|
||||||
Log_Debug_Msg(MONITOR_IPC, str, Driver_Empty);
|
Log_Debug_Msg(MONITOR_IPC | MONITOR_TRACE, str, Driver_Empty);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -93,6 +93,7 @@ MSG_HEADER *EpMapperServer::EpmapperGetPortNameHandler(MSG_HEADER *msg)
|
||||||
return SHORT_REPLY(E_OUTOFMEMORY);
|
return SHORT_REPLY(E_OUTOFMEMORY);
|
||||||
|
|
||||||
rpl->h.status = STATUS_NOT_FOUND;
|
rpl->h.status = STATUS_NOT_FOUND;
|
||||||
|
rpl->wszPortName[0] = L'\0';
|
||||||
|
|
||||||
if (pwszServiceName != NULL) {
|
if (pwszServiceName != NULL) {
|
||||||
|
|
||||||
|
@ -170,12 +171,18 @@ MSG_HEADER *EpMapperServer::EpmapperGetPortNameHandler(MSG_HEADER *msg)
|
||||||
|
|
||||||
if (rpl->h.status == STATUS_SUCCESS)
|
if (rpl->h.status == STATUS_SUCCESS)
|
||||||
{
|
{
|
||||||
|
//
|
||||||
|
// Note: it seams that chrome.exe resolves GAME_CONFIG_STORE_PORT in one process and accesses from an other
|
||||||
|
// so since here we onlyonly a fre non critical ports we will use PID 0 to open it gloally
|
||||||
|
// instead of only for the one process. Todo: make it per sandbox instead
|
||||||
|
//
|
||||||
|
|
||||||
// Param 1 is dynamic port name (e.g. "LRPC-f760d5b40689a98168"), WCHAR[DYNAMIC_PORT_NAME_CHARS]
|
// Param 1 is dynamic port name (e.g. "LRPC-f760d5b40689a98168"), WCHAR[DYNAMIC_PORT_NAME_CHARS]
|
||||||
// Param 2 is the process PID for which to open the port
|
// Param 2 is the process PID for which to open the port, can be 0 when port is special
|
||||||
// Param 3 is the port type/identifier, can be -1 indicating non special port
|
// Param 3 is the port type/identifier, can be -1 indicating non special port
|
||||||
rpl->h.status = SbieApi_CallThree(API_OPEN_DYNAMIC_PORT,
|
rpl->h.status = SbieApi_CallThree(API_OPEN_DYNAMIC_PORT,
|
||||||
(ULONG_PTR)rpl->wszPortName,
|
(ULONG_PTR)rpl->wszPortName,
|
||||||
(ULONG_PTR)idProcess,
|
(ULONG_PTR)0,
|
||||||
(ULONG_PTR)req->portType);
|
(ULONG_PTR)req->portType);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -491,27 +491,3 @@ bool CheckDropRights(const WCHAR *BoxName)
|
||||||
return true;
|
return true;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
// CheckStringInList
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
|
|
||||||
|
|
||||||
bool CheckStringInList(const WCHAR* string, const WCHAR* boxname, const WCHAR* setting)
|
|
||||||
{
|
|
||||||
WCHAR buf[66];
|
|
||||||
ULONG index = 0;
|
|
||||||
while (1) {
|
|
||||||
NTSTATUS status = SbieApi_QueryConfAsIs(boxname, setting, index, buf, 64 * sizeof(WCHAR));
|
|
||||||
++index;
|
|
||||||
if (NT_SUCCESS(status)) {
|
|
||||||
if (_wcsicmp(buf, string) == 0) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (status != STATUS_BUFFER_TOO_SMALL)
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
|
@ -24,7 +24,6 @@ void LogEvent(ULONG msgid, ULONG level, ULONG detail);
|
||||||
void AbortServer(void);
|
void AbortServer(void);
|
||||||
bool RestrictToken(void);
|
bool RestrictToken(void);
|
||||||
bool CheckDropRights(const WCHAR *BoxName);
|
bool CheckDropRights(const WCHAR *BoxName);
|
||||||
bool CheckStringInList(const WCHAR* string, const WCHAR* boxname, const WCHAR* setting);
|
|
||||||
|
|
||||||
SECURITY_ATTRIBUTES *GetSecurityAttributes(ACCESS_MASK EveryoneAccess);
|
SECURITY_ATTRIBUTES *GetSecurityAttributes(ACCESS_MASK EveryoneAccess);
|
||||||
|
|
||||||
|
|
|
@ -1625,6 +1625,7 @@ MSG_HEADER *SbieIniServer::RunSbieCtrl(HANDLE idProcess, bool isSandboxed)
|
||||||
NTSTATUS status = STATUS_UNSUCCESSFUL;
|
NTSTATUS status = STATUS_UNSUCCESSFUL;
|
||||||
HANDLE hToken = NULL;
|
HANDLE hToken = NULL;
|
||||||
BOOL ok = TRUE;
|
BOOL ok = TRUE;
|
||||||
|
WCHAR ctrlName[64];
|
||||||
|
|
||||||
//
|
//
|
||||||
// get token from caller session or caller process. note that on
|
// get token from caller session or caller process. note that on
|
||||||
|
@ -1668,21 +1669,28 @@ MSG_HEADER *SbieIniServer::RunSbieCtrl(HANDLE idProcess, bool isSandboxed)
|
||||||
if (ok && isSandboxed) {
|
if (ok && isSandboxed) {
|
||||||
|
|
||||||
const WCHAR *_Setting = SBIECTRL_ L"EnableAutoStart";
|
const WCHAR *_Setting = SBIECTRL_ L"EnableAutoStart";
|
||||||
|
const WCHAR* _Setting2 = SBIECTRL_ L"AutoStartAgent";
|
||||||
WCHAR buf[10], ch = 0;
|
WCHAR buf[10], ch = 0;
|
||||||
bool ok2 = SetUserSettingsSectionName(hToken);
|
bool ok2 = SetUserSettingsSectionName(hToken);
|
||||||
if (ok2) {
|
if (ok2) {
|
||||||
SbieApi_QueryConfAsIs(
|
SbieApi_QueryConfAsIs(
|
||||||
m_sectionname, _Setting, 0, buf, 8 * sizeof(WCHAR));
|
m_sectionname, _Setting, 0, buf, sizeof(buf) - 2);
|
||||||
ch = towlower(buf[0]);
|
ch = towlower(buf[0]);
|
||||||
|
|
||||||
|
SbieApi_QueryConfAsIs(
|
||||||
|
m_sectionname, _Setting2, 0, ctrlName, sizeof(ctrlName) - 2);
|
||||||
}
|
}
|
||||||
if (! ch) {
|
if (! ch) {
|
||||||
wcscpy(m_sectionname + 13, L"Default"); // UserSettings_Default
|
wcscpy(m_sectionname + 13, L"Default"); // UserSettings_Default
|
||||||
SbieApi_QueryConfAsIs(
|
SbieApi_QueryConfAsIs(
|
||||||
m_sectionname, _Setting, 0, buf, 8 * sizeof(WCHAR));
|
m_sectionname, _Setting, 0, buf, 8 * sizeof(WCHAR));
|
||||||
ch = towlower(buf[0]);
|
ch = towlower(buf[0]);
|
||||||
|
|
||||||
|
SbieApi_QueryConfAsIs(
|
||||||
|
m_sectionname, _Setting2, 0, ctrlName, sizeof(ctrlName) - 2);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ch != L'y') {
|
if (ch == L'n') {
|
||||||
status = STATUS_LOGON_NOT_GRANTED;
|
status = STATUS_LOGON_NOT_GRANTED;
|
||||||
ok = FALSE;
|
ok = FALSE;
|
||||||
}
|
}
|
||||||
|
@ -1699,11 +1707,11 @@ MSG_HEADER *SbieIniServer::RunSbieCtrl(HANDLE idProcess, bool isSandboxed)
|
||||||
|
|
||||||
WCHAR *args;
|
WCHAR *args;
|
||||||
if (isSandboxed)
|
if (isSandboxed)
|
||||||
args = NULL;
|
args = L" -autorun";
|
||||||
else
|
else
|
||||||
args = L" /open /sync";
|
args = L" /open /sync";
|
||||||
|
|
||||||
if (SbieDll_RunFromHome(SBIECTRL_EXE, args, &si, NULL)) {
|
if (SbieDll_RunFromHome(*ctrlName ? ctrlName : SBIECTRL_EXE, args, &si, NULL)) {
|
||||||
|
|
||||||
WCHAR *CmdLine = (WCHAR *)si.lpReserved;
|
WCHAR *CmdLine = (WCHAR *)si.lpReserved;
|
||||||
|
|
||||||
|
|
|
@ -67,7 +67,7 @@ bool ServiceServer::CanCallerDoElevation(
|
||||||
// if this service is configured to be started on box initialization
|
// if this service is configured to be started on box initialization
|
||||||
// by SandboxieRpcSs.exe then allow it to be started
|
// by SandboxieRpcSs.exe then allow it to be started
|
||||||
//
|
//
|
||||||
if (CheckStringInList(ServiceName, boxname, L"StartService"))
|
if (SbieDll_CheckStringInList(ServiceName, boxname, L"StartService"))
|
||||||
DropRights = false;
|
DropRights = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -283,7 +283,7 @@ bool ServiceServer__RunServiceAsSystem(const WCHAR* svcname, const WCHAR* boxnam
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
// check exception list
|
// check exception list
|
||||||
return CheckStringInList(svcname, boxname, L"RunServiceAsSystem");
|
return SbieDll_CheckStringInList(svcname, boxname, L"RunServiceAsSystem");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
Binary file not shown.
Binary file not shown.
|
@ -158,6 +158,7 @@ public:
|
||||||
QStyle* pStyle = QStyleFactory::create("windows");
|
QStyle* pStyle = QStyleFactory::create("windows");
|
||||||
m_pTreeList->setStyle(pStyle);
|
m_pTreeList->setStyle(pStyle);
|
||||||
#endif
|
#endif
|
||||||
|
m_pTreeList->setExpandsOnDoubleClick(false);
|
||||||
m_pTreeList->setSortingEnabled(true);
|
m_pTreeList->setSortingEnabled(true);
|
||||||
|
|
||||||
m_pTreeList->setContextMenuPolicy(Qt::CustomContextMenu);
|
m_pTreeList->setContextMenuPolicy(Qt::CustomContextMenu);
|
||||||
|
|
|
@ -11,6 +11,8 @@ public:
|
||||||
{
|
{
|
||||||
m_bAlternate = bAlternate;
|
m_bAlternate = bAlternate;
|
||||||
m_bHighLight = false;
|
m_bHighLight = false;
|
||||||
|
|
||||||
|
this->setSortCaseSensitivity(Qt::CaseInsensitive);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool filterAcceptsRow(int source_row, const QModelIndex & source_parent) const
|
bool filterAcceptsRow(int source_row, const QModelIndex & source_parent) const
|
||||||
|
|
|
@ -0,0 +1,165 @@
|
||||||
|
GNU LESSER GENERAL PUBLIC LICENSE
|
||||||
|
Version 3, 29 June 2007
|
||||||
|
|
||||||
|
Copyright (C) 2007 Free Software Foundation, Inc. <https://fsf.org/>
|
||||||
|
Everyone is permitted to copy and distribute verbatim copies
|
||||||
|
of this license document, but changing it is not allowed.
|
||||||
|
|
||||||
|
|
||||||
|
This version of the GNU Lesser General Public License incorporates
|
||||||
|
the terms and conditions of version 3 of the GNU General Public
|
||||||
|
License, supplemented by the additional permissions listed below.
|
||||||
|
|
||||||
|
0. Additional Definitions.
|
||||||
|
|
||||||
|
As used herein, "this License" refers to version 3 of the GNU Lesser
|
||||||
|
General Public License, and the "GNU GPL" refers to version 3 of the GNU
|
||||||
|
General Public License.
|
||||||
|
|
||||||
|
"The Library" refers to a covered work governed by this License,
|
||||||
|
other than an Application or a Combined Work as defined below.
|
||||||
|
|
||||||
|
An "Application" is any work that makes use of an interface provided
|
||||||
|
by the Library, but which is not otherwise based on the Library.
|
||||||
|
Defining a subclass of a class defined by the Library is deemed a mode
|
||||||
|
of using an interface provided by the Library.
|
||||||
|
|
||||||
|
A "Combined Work" is a work produced by combining or linking an
|
||||||
|
Application with the Library. The particular version of the Library
|
||||||
|
with which the Combined Work was made is also called the "Linked
|
||||||
|
Version".
|
||||||
|
|
||||||
|
The "Minimal Corresponding Source" for a Combined Work means the
|
||||||
|
Corresponding Source for the Combined Work, excluding any source code
|
||||||
|
for portions of the Combined Work that, considered in isolation, are
|
||||||
|
based on the Application, and not on the Linked Version.
|
||||||
|
|
||||||
|
The "Corresponding Application Code" for a Combined Work means the
|
||||||
|
object code and/or source code for the Application, including any data
|
||||||
|
and utility programs needed for reproducing the Combined Work from the
|
||||||
|
Application, but excluding the System Libraries of the Combined Work.
|
||||||
|
|
||||||
|
1. Exception to Section 3 of the GNU GPL.
|
||||||
|
|
||||||
|
You may convey a covered work under sections 3 and 4 of this License
|
||||||
|
without being bound by section 3 of the GNU GPL.
|
||||||
|
|
||||||
|
2. Conveying Modified Versions.
|
||||||
|
|
||||||
|
If you modify a copy of the Library, and, in your modifications, a
|
||||||
|
facility refers to a function or data to be supplied by an Application
|
||||||
|
that uses the facility (other than as an argument passed when the
|
||||||
|
facility is invoked), then you may convey a copy of the modified
|
||||||
|
version:
|
||||||
|
|
||||||
|
a) under this License, provided that you make a good faith effort to
|
||||||
|
ensure that, in the event an Application does not supply the
|
||||||
|
function or data, the facility still operates, and performs
|
||||||
|
whatever part of its purpose remains meaningful, or
|
||||||
|
|
||||||
|
b) under the GNU GPL, with none of the additional permissions of
|
||||||
|
this License applicable to that copy.
|
||||||
|
|
||||||
|
3. Object Code Incorporating Material from Library Header Files.
|
||||||
|
|
||||||
|
The object code form of an Application may incorporate material from
|
||||||
|
a header file that is part of the Library. You may convey such object
|
||||||
|
code under terms of your choice, provided that, if the incorporated
|
||||||
|
material is not limited to numerical parameters, data structure
|
||||||
|
layouts and accessors, or small macros, inline functions and templates
|
||||||
|
(ten or fewer lines in length), you do both of the following:
|
||||||
|
|
||||||
|
a) Give prominent notice with each copy of the object code that the
|
||||||
|
Library is used in it and that the Library and its use are
|
||||||
|
covered by this License.
|
||||||
|
|
||||||
|
b) Accompany the object code with a copy of the GNU GPL and this license
|
||||||
|
document.
|
||||||
|
|
||||||
|
4. Combined Works.
|
||||||
|
|
||||||
|
You may convey a Combined Work under terms of your choice that,
|
||||||
|
taken together, effectively do not restrict modification of the
|
||||||
|
portions of the Library contained in the Combined Work and reverse
|
||||||
|
engineering for debugging such modifications, if you also do each of
|
||||||
|
the following:
|
||||||
|
|
||||||
|
a) Give prominent notice with each copy of the Combined Work that
|
||||||
|
the Library is used in it and that the Library and its use are
|
||||||
|
covered by this License.
|
||||||
|
|
||||||
|
b) Accompany the Combined Work with a copy of the GNU GPL and this license
|
||||||
|
document.
|
||||||
|
|
||||||
|
c) For a Combined Work that displays copyright notices during
|
||||||
|
execution, include the copyright notice for the Library among
|
||||||
|
these notices, as well as a reference directing the user to the
|
||||||
|
copies of the GNU GPL and this license document.
|
||||||
|
|
||||||
|
d) Do one of the following:
|
||||||
|
|
||||||
|
0) Convey the Minimal Corresponding Source under the terms of this
|
||||||
|
License, and the Corresponding Application Code in a form
|
||||||
|
suitable for, and under terms that permit, the user to
|
||||||
|
recombine or relink the Application with a modified version of
|
||||||
|
the Linked Version to produce a modified Combined Work, in the
|
||||||
|
manner specified by section 6 of the GNU GPL for conveying
|
||||||
|
Corresponding Source.
|
||||||
|
|
||||||
|
1) Use a suitable shared library mechanism for linking with the
|
||||||
|
Library. A suitable mechanism is one that (a) uses at run time
|
||||||
|
a copy of the Library already present on the user's computer
|
||||||
|
system, and (b) will operate properly with a modified version
|
||||||
|
of the Library that is interface-compatible with the Linked
|
||||||
|
Version.
|
||||||
|
|
||||||
|
e) Provide Installation Information, but only if you would otherwise
|
||||||
|
be required to provide such information under section 6 of the
|
||||||
|
GNU GPL, and only to the extent that such information is
|
||||||
|
necessary to install and execute a modified version of the
|
||||||
|
Combined Work produced by recombining or relinking the
|
||||||
|
Application with a modified version of the Linked Version. (If
|
||||||
|
you use option 4d0, the Installation Information must accompany
|
||||||
|
the Minimal Corresponding Source and Corresponding Application
|
||||||
|
Code. If you use option 4d1, you must provide the Installation
|
||||||
|
Information in the manner specified by section 6 of the GNU GPL
|
||||||
|
for conveying Corresponding Source.)
|
||||||
|
|
||||||
|
5. Combined Libraries.
|
||||||
|
|
||||||
|
You may place library facilities that are a work based on the
|
||||||
|
Library side by side in a single library together with other library
|
||||||
|
facilities that are not Applications and are not covered by this
|
||||||
|
License, and convey such a combined library under terms of your
|
||||||
|
choice, if you do both of the following:
|
||||||
|
|
||||||
|
a) Accompany the combined library with a copy of the same work based
|
||||||
|
on the Library, uncombined with any other library facilities,
|
||||||
|
conveyed under the terms of this License.
|
||||||
|
|
||||||
|
b) Give prominent notice with the combined library that part of it
|
||||||
|
is a work based on the Library, and explaining where to find the
|
||||||
|
accompanying uncombined form of the same work.
|
||||||
|
|
||||||
|
6. Revised Versions of the GNU Lesser General Public License.
|
||||||
|
|
||||||
|
The Free Software Foundation may publish revised and/or new versions
|
||||||
|
of the GNU Lesser General Public License from time to time. Such new
|
||||||
|
versions will be similar in spirit to the present version, but may
|
||||||
|
differ in detail to address new problems or concerns.
|
||||||
|
|
||||||
|
Each version is given a distinguishing version number. If the
|
||||||
|
Library as you received it specifies that a certain numbered version
|
||||||
|
of the GNU Lesser General Public License "or any later version"
|
||||||
|
applies to it, you have the option of following the terms and
|
||||||
|
conditions either of that published version or of any later version
|
||||||
|
published by the Free Software Foundation. If the Library as you
|
||||||
|
received it does not specify a version number of the GNU Lesser
|
||||||
|
General Public License, you may choose any version of the GNU Lesser
|
||||||
|
General Public License ever published by the Free Software Foundation.
|
||||||
|
|
||||||
|
If the Library as you received it specifies that a proxy can decide
|
||||||
|
whether future versions of the GNU Lesser General Public License shall
|
||||||
|
apply, that proxy's public statement of acceptance of any version is
|
||||||
|
permanent authorization for you to choose that version for the
|
||||||
|
Library.
|
|
@ -55,7 +55,6 @@ CSandBox::CSandBox(const QString& BoxName, class CSbieAPI* pAPI) : CSbieIni(BoxN
|
||||||
InsertText("Template", "LingerPrograms");
|
InsertText("Template", "LingerPrograms");
|
||||||
// templates L7
|
// templates L7
|
||||||
InsertText("Template", "BlockPorts");
|
InsertText("Template", "BlockPorts");
|
||||||
InsertText("Template", "WindowsFontCache");
|
|
||||||
InsertText("Template", "qWave");
|
InsertText("Template", "qWave");
|
||||||
|
|
||||||
// recovery
|
// recovery
|
||||||
|
@ -92,6 +91,11 @@ SB_STATUS CSandBox::TerminateAll()
|
||||||
return m_pAPI->TerminateAll(m_Name);
|
return m_pAPI->TerminateAll(m_Name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool CSandBox::IsEmpty()
|
||||||
|
{
|
||||||
|
return !QDir(m_FilePath).exists();
|
||||||
|
}
|
||||||
|
|
||||||
SB_PROGRESS CSandBox::CleanBox()
|
SB_PROGRESS CSandBox::CleanBox()
|
||||||
{
|
{
|
||||||
if (GetBool("NeverDelete", false))
|
if (GetBool("NeverDelete", false))
|
||||||
|
@ -149,10 +153,9 @@ void CSandBox::CleanBoxAsync(const CSbieProgressPtr& pProgress, const QStringLis
|
||||||
|
|
||||||
SB_STATUS CSandBox::RenameBox(const QString& NewName)
|
SB_STATUS CSandBox::RenameBox(const QString& NewName)
|
||||||
{
|
{
|
||||||
if (QDir(m_FilePath).exists())
|
if (!IsEmpty())
|
||||||
return SB_ERR(SB_RemNotEmpty);
|
return SB_ERR(SB_RemNotEmpty);
|
||||||
|
|
||||||
|
|
||||||
SB_STATUS Status = CSbieAPI::ValidateName(NewName);
|
SB_STATUS Status = CSbieAPI::ValidateName(NewName);
|
||||||
if (Status.IsError())
|
if (Status.IsError())
|
||||||
return Status;
|
return Status;
|
||||||
|
@ -162,7 +165,7 @@ SB_STATUS CSandBox::RenameBox(const QString& NewName)
|
||||||
|
|
||||||
SB_STATUS CSandBox::RemoveBox()
|
SB_STATUS CSandBox::RemoveBox()
|
||||||
{
|
{
|
||||||
if (QDir(m_FilePath).exists())
|
if (!IsEmpty())
|
||||||
return SB_ERR(SB_DelNotEmpty);
|
return SB_ERR(SB_DelNotEmpty);
|
||||||
|
|
||||||
return RemoveSection();
|
return RemoveSection();
|
||||||
|
@ -215,6 +218,9 @@ SB_PROGRESS CSandBox::TakeSnapshot(const QString& Name)
|
||||||
if (m_pAPI->HasProcesses(m_Name))
|
if (m_pAPI->HasProcesses(m_Name))
|
||||||
return SB_ERR(SB_SnapIsRunning, OP_CONFIRM);
|
return SB_ERR(SB_SnapIsRunning, OP_CONFIRM);
|
||||||
|
|
||||||
|
if (IsEmpty())
|
||||||
|
return SB_ERR(SB_SnapIsEmpty);
|
||||||
|
|
||||||
QStringList Snapshots = ini.childGroups();
|
QStringList Snapshots = ini.childGroups();
|
||||||
|
|
||||||
QString ID;
|
QString ID;
|
||||||
|
|
|
@ -56,6 +56,7 @@ public:
|
||||||
|
|
||||||
virtual void CloseBox() {}
|
virtual void CloseBox() {}
|
||||||
|
|
||||||
|
virtual bool IsEmpty();
|
||||||
virtual SB_PROGRESS CleanBox();
|
virtual SB_PROGRESS CleanBox();
|
||||||
virtual SB_STATUS RenameBox(const QString& NewName);
|
virtual SB_STATUS RenameBox(const QString& NewName);
|
||||||
virtual SB_STATUS RemoveBox();
|
virtual SB_STATUS RemoveBox();
|
||||||
|
|
|
@ -752,14 +752,13 @@ QString CSbieAPI::GetVersion()
|
||||||
|
|
||||||
SB_STATUS CSbieAPI::TakeOver()
|
SB_STATUS CSbieAPI::TakeOver()
|
||||||
{
|
{
|
||||||
__declspec(align(8)) ULONG64 ResultValue;
|
|
||||||
__declspec(align(8)) ULONG64 parms[API_NUM_ARGS];
|
__declspec(align(8)) ULONG64 parms[API_NUM_ARGS];
|
||||||
API_SESSION_LEADER_ARGS *args = (API_SESSION_LEADER_ARGS *)parms;
|
API_SESSION_LEADER_ARGS *args = (API_SESSION_LEADER_ARGS *)parms;
|
||||||
|
|
||||||
memset(parms, 0, sizeof(parms));
|
memset(parms, 0, sizeof(parms));
|
||||||
args->func_code = API_SESSION_LEADER;
|
args->func_code = API_SESSION_LEADER;
|
||||||
args->token_handle.val64 = 0;
|
args->token_handle.val64 = 0; // (ULONG64)(ULONG_PTR)GetCurrentProcessToken();
|
||||||
args->process_id.val64 = 0;
|
args->process_id.val64 = 0; // (ULONG64)(ULONG_PTR)&ResultValue;
|
||||||
|
|
||||||
NTSTATUS status = m->IoControl(parms);
|
NTSTATUS status = m->IoControl(parms);
|
||||||
if (!NT_SUCCESS(status))
|
if (!NT_SUCCESS(status))
|
||||||
|
@ -1008,7 +1007,7 @@ SB_STATUS CSbieAPI::SbieIniSet(const QString& Section, const QString& Setting, c
|
||||||
|
|
||||||
SB_STATUS Status = SbieIniSet(req, req->password, Section, Setting);
|
SB_STATUS Status = SbieIniSet(req, req->password, Section, Setting);
|
||||||
//if (!Status)
|
//if (!Status)
|
||||||
// emit LogSbieMessage(2203, QStringList() << "" << Status.GetText() << "", GetCurrentProcessId());
|
// emit LogSbieMessage(0xC1020000 | 2203, QStringList() << "" << Status.GetText() << "", GetCurrentProcessId());
|
||||||
free(req);
|
free(req);
|
||||||
return Status;
|
return Status;
|
||||||
}
|
}
|
||||||
|
@ -1062,6 +1061,9 @@ SB_STATUS CSbieAPI::CreateBox(const QString& BoxName)
|
||||||
if(Status.IsError())
|
if(Status.IsError())
|
||||||
return Status;
|
return Status;
|
||||||
|
|
||||||
|
if(m_SandBoxes.contains(BoxName.toLower()))
|
||||||
|
return SB_ERR(SB_NameExists);
|
||||||
|
|
||||||
Status = SbieIniSet(BoxName, "Enabled", "y");
|
Status = SbieIniSet(BoxName, "Enabled", "y");
|
||||||
if (Status.IsError())
|
if (Status.IsError())
|
||||||
return Status;
|
return Status;
|
||||||
|
@ -1334,7 +1336,7 @@ QString CSbieAPI::GetDeviceMap()
|
||||||
status = CSbieAPI__OpenDeviceMap(m, &handle);
|
status = CSbieAPI__OpenDeviceMap(m, &handle);
|
||||||
|
|
||||||
if (!NT_SUCCESS(status)) {
|
if (!NT_SUCCESS(status)) {
|
||||||
emit LogSbieMessage(2321, QStringList() << "" << QString("%1").arg(status, 8, 16) << "", GetCurrentProcessId());
|
emit LogSbieMessage(0xC1020000 | 2321, QStringList() << "" << QString("%1").arg(status, 8, 16) << "", GetCurrentProcessId());
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -1345,7 +1347,7 @@ QString CSbieAPI::GetDeviceMap()
|
||||||
NtClose(handle);
|
NtClose(handle);
|
||||||
|
|
||||||
if (!NT_SUCCESS(status)) {
|
if (!NT_SUCCESS(status)) {
|
||||||
emit LogSbieMessage(2321, QStringList() << "" << QString("%1").arg(status, 8, 16) << "", GetCurrentProcessId());
|
emit LogSbieMessage(0xC1020000 | 2321, QStringList() << "" << QString("%1").arg(status, 8, 16) << "", GetCurrentProcessId());
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -1544,6 +1546,36 @@ QString CSbieAPI::GetBoxedPath(const CSandBoxPtr& pBox, const QString& Path)
|
||||||
return BoxRoot + "\\drive\\" + Path.at(0) + Path.mid(2);
|
return BoxRoot + "\\drive\\" + Path.at(0) + Path.mid(2);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QString CSbieAPI::GetRealPath(const CSandBoxPtr& pBox, const QString& Path)
|
||||||
|
{
|
||||||
|
QString RealPath;
|
||||||
|
QString BoxRoot = pBox->m_FilePath;
|
||||||
|
if (BoxRoot.right(1) == "\\") BoxRoot.truncate(BoxRoot.length() - 1);
|
||||||
|
|
||||||
|
if (Path.length() < BoxRoot.length())
|
||||||
|
return RealPath;
|
||||||
|
|
||||||
|
RealPath = Path.mid(BoxRoot.length());
|
||||||
|
|
||||||
|
if (RealPath.left(6) == "\\share")
|
||||||
|
RealPath = "\\device\\mup" + RealPath.mid(6);
|
||||||
|
|
||||||
|
if (RealPath.left(5) == "\\user")
|
||||||
|
{
|
||||||
|
if (RealPath.mid(5, 8) == "\\current")
|
||||||
|
RealPath = m_UserDir + RealPath.mid(5 + 8);
|
||||||
|
else if (RealPath.mid(5, 4) == "\\all")
|
||||||
|
RealPath = m_ProgramDataDir + RealPath.mid(5 + 4);
|
||||||
|
else if (RealPath.mid(5, 7) == "\\public")
|
||||||
|
RealPath = m_PublicDir + RealPath.mid(5 + 7);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (RealPath.left(6) == "\\drive")
|
||||||
|
RealPath = RealPath.mid(7, 1) + ":" + RealPath.mid(8);
|
||||||
|
|
||||||
|
return RealPath;
|
||||||
|
}
|
||||||
|
|
||||||
///////////////////////////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
// Conf
|
// Conf
|
||||||
//
|
//
|
||||||
|
@ -1769,6 +1801,7 @@ CBoxedProcessPtr CSbieAPI::OnProcessBoxed(quint32 ProcessId, const QString& Path
|
||||||
pBox->m_ProcessList.insert(ProcessId, pProcess);
|
pBox->m_ProcessList.insert(ProcessId, pProcess);
|
||||||
m_BoxedProxesses.insert(ProcessId, pProcess);
|
m_BoxedProxesses.insert(ProcessId, pProcess);
|
||||||
|
|
||||||
|
UpdateProcessInfo(pProcess);
|
||||||
pProcess->InitProcessInfo();
|
pProcess->InitProcessInfo();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1853,7 +1886,7 @@ bool CSbieAPI::IsMonitoring()
|
||||||
|
|
||||||
bool CSbieAPI::GetMonitor()
|
bool CSbieAPI::GetMonitor()
|
||||||
{
|
{
|
||||||
const int max_len = 256; // versions prioir to 5.44.1 check for max_len <= 256 increase this later
|
const int max_len = 1024;
|
||||||
|
|
||||||
USHORT type;
|
USHORT type;
|
||||||
ULONG64 pid;
|
ULONG64 pid;
|
||||||
|
@ -1879,7 +1912,7 @@ bool CSbieAPI::GetMonitor()
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if (RecordNum != m->lastRecordNum + 1 && !m->clearingBuffers)
|
if (RecordNum != m->lastRecordNum + 1 && !m->clearingBuffers)
|
||||||
emit LogSbieMessage(1242, QStringList() << "" << "" << "", GetCurrentProcessId()); // Monitor buffer overflow
|
emit LogSbieMessage(0xC1020000 | 1242, QStringList() << "" << "" << "", GetCurrentProcessId()); // Monitor buffer overflow
|
||||||
m->lastRecordNum = RecordNum;
|
m->lastRecordNum = RecordNum;
|
||||||
|
|
||||||
if (m->clearingBuffers)
|
if (m->clearingBuffers)
|
||||||
|
@ -1926,6 +1959,22 @@ QString CSbieAPI::GetSbieMsgStr(quint32 code, quint32 Lang)
|
||||||
//
|
//
|
||||||
//
|
//
|
||||||
|
|
||||||
|
QString ErrorString(qint32 err)
|
||||||
|
{
|
||||||
|
QString Error;
|
||||||
|
HMODULE handle = NULL; //err < 0 ? GetModuleHandle(L"NTDLL.DLL") : NULL;
|
||||||
|
DWORD flags = 0; //err < 0 ? FORMAT_MESSAGE_FROM_HMODULE : 0;
|
||||||
|
LPTSTR s;
|
||||||
|
if (::FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | flags, handle, err, 0, (LPTSTR)&s, 0, NULL) > 0)
|
||||||
|
{
|
||||||
|
LPTSTR p = wcschr(s, L'\r');
|
||||||
|
if (p != NULL) *p = L'\0';
|
||||||
|
Error = QString::fromWCharArray(s);
|
||||||
|
::LocalFree(s);
|
||||||
|
}
|
||||||
|
return Error;
|
||||||
|
}
|
||||||
|
|
||||||
CResLogEntry::CResLogEntry(quint32 ProcessId, quint32 Type, const QString& Value)
|
CResLogEntry::CResLogEntry(quint32 ProcessId, quint32 Type, const QString& Value)
|
||||||
{
|
{
|
||||||
m_ProcessId = ProcessId;
|
m_ProcessId = ProcessId;
|
||||||
|
@ -1935,6 +1984,19 @@ CResLogEntry::CResLogEntry(quint32 ProcessId, quint32 Type, const QString& Value
|
||||||
m_TimeStamp = QDateTime::currentDateTime(); // ms resolution
|
m_TimeStamp = QDateTime::currentDateTime(); // ms resolution
|
||||||
m_Counter = 0;
|
m_Counter = 0;
|
||||||
|
|
||||||
|
// if this is a set error, then get the actual error string
|
||||||
|
if (m_Type.Type == MONITOR_OTHER && Value.indexOf("SetError:") == 0)
|
||||||
|
{
|
||||||
|
auto tmp = Value.split(":");
|
||||||
|
if (tmp.length() >= 2)
|
||||||
|
{
|
||||||
|
qint32 errCode = tmp[1].trimmed().toInt();
|
||||||
|
QString Error = ErrorString(errCode);
|
||||||
|
if(!Error.isEmpty())
|
||||||
|
m_Name += " (" + Error + ")";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static atomic<quint64> uid = 0;
|
static atomic<quint64> uid = 0;
|
||||||
m_uid = uid.fetch_add(1);
|
m_uid = uid.fetch_add(1);
|
||||||
}
|
}
|
||||||
|
@ -1943,6 +2005,7 @@ QString CResLogEntry::GetTypeStr() const
|
||||||
{
|
{
|
||||||
switch (m_Type.Type)
|
switch (m_Type.Type)
|
||||||
{
|
{
|
||||||
|
case MONITOR_SYSCALL: return "SysCall";
|
||||||
case MONITOR_PIPE: return "Pipe";
|
case MONITOR_PIPE: return "Pipe";
|
||||||
case MONITOR_IPC: return "Ipc";
|
case MONITOR_IPC: return "Ipc";
|
||||||
case MONITOR_WINCLASS: return "WinClass";
|
case MONITOR_WINCLASS: return "WinClass";
|
||||||
|
@ -1950,7 +2013,8 @@ QString CResLogEntry::GetTypeStr() const
|
||||||
case MONITOR_COMCLASS: return "ComClass";
|
case MONITOR_COMCLASS: return "ComClass";
|
||||||
case MONITOR_IGNORE: return "Ignore";
|
case MONITOR_IGNORE: return "Ignore";
|
||||||
case MONITOR_IMAGE: return "Image";
|
case MONITOR_IMAGE: return "Image";
|
||||||
case MONITOR_FILE_OR_KEY: return "File/Key";
|
case MONITOR_FILE: return "File";
|
||||||
|
case MONITOR_KEY: return "Key";
|
||||||
case MONITOR_OTHER: return "Debug";
|
case MONITOR_OTHER: return "Debug";
|
||||||
default: return "Unknown: " + QString::number(m_Type.Type);
|
default: return "Unknown: " + QString::number(m_Type.Type);
|
||||||
}
|
}
|
||||||
|
@ -1958,14 +2022,19 @@ QString CResLogEntry::GetTypeStr() const
|
||||||
|
|
||||||
QString CResLogEntry::GetStautsStr() const
|
QString CResLogEntry::GetStautsStr() const
|
||||||
{
|
{
|
||||||
if (m_Type.Trace)
|
QString Status;
|
||||||
return "Trace";
|
|
||||||
|
|
||||||
if (m_Type.Open)
|
if (m_Type.Open)
|
||||||
return "Open";
|
Status.append("Open ");
|
||||||
if (m_Type.Deny)
|
if (m_Type.Deny)
|
||||||
return "Closed";
|
Status.append("Closed ");
|
||||||
return "";
|
|
||||||
|
if (m_Type.Trace)
|
||||||
|
Status.append("Trace ");
|
||||||
|
|
||||||
|
if (m_Counter > 1)
|
||||||
|
Status.append(QString("(%1)").arg(m_Counter));
|
||||||
|
|
||||||
|
return Status;
|
||||||
}
|
}
|
||||||
|
|
||||||
///////////////////////////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
|
@ -123,6 +123,7 @@ public:
|
||||||
|
|
||||||
virtual QString GetBoxedPath(const QString& BoxName, const QString& Path);
|
virtual QString GetBoxedPath(const QString& BoxName, const QString& Path);
|
||||||
virtual QString GetBoxedPath(const CSandBoxPtr& pBox, const QString& Path);
|
virtual QString GetBoxedPath(const CSandBoxPtr& pBox, const QString& Path);
|
||||||
|
virtual QString GetRealPath(const CSandBoxPtr& pBox, const QString& Path);
|
||||||
|
|
||||||
enum ESetMode
|
enum ESetMode
|
||||||
{
|
{
|
||||||
|
|
|
@ -37,7 +37,8 @@ enum ESbieMsgCodes
|
||||||
SB_SnapDelRegFail,
|
SB_SnapDelRegFail,
|
||||||
SB_NotAuthorized,
|
SB_NotAuthorized,
|
||||||
SB_ConfigFailed,
|
SB_ConfigFailed,
|
||||||
|
SB_SnapIsEmpty,
|
||||||
|
SB_NameExists,
|
||||||
};
|
};
|
||||||
|
|
||||||
class CSbieStatus
|
class CSbieStatus
|
||||||
|
|
|
@ -45,7 +45,7 @@
|
||||||
<enum>QTabWidget::West</enum>
|
<enum>QTabWidget::West</enum>
|
||||||
</property>
|
</property>
|
||||||
<property name="currentIndex">
|
<property name="currentIndex">
|
||||||
<number>8</number>
|
<number>0</number>
|
||||||
</property>
|
</property>
|
||||||
<widget class="QWidget" name="tabGeneral">
|
<widget class="QWidget" name="tabGeneral">
|
||||||
<attribute name="title">
|
<attribute name="title">
|
||||||
|
@ -1770,8 +1770,8 @@ instead of "*".</string>
|
||||||
<rect>
|
<rect>
|
||||||
<x>0</x>
|
<x>0</x>
|
||||||
<y>0</y>
|
<y>0</y>
|
||||||
<width>98</width>
|
<width>530</width>
|
||||||
<height>28</height>
|
<height>312</height>
|
||||||
</rect>
|
</rect>
|
||||||
</property>
|
</property>
|
||||||
<layout class="QGridLayout" name="dbgLayout">
|
<layout class="QGridLayout" name="dbgLayout">
|
||||||
|
@ -1960,6 +1960,112 @@ instead of "*".</string>
|
||||||
</item>
|
</item>
|
||||||
</layout>
|
</layout>
|
||||||
</widget>
|
</widget>
|
||||||
|
<tabstops>
|
||||||
|
<tabstop>tabs</tabstop>
|
||||||
|
<tabstop>tabWidget</tabstop>
|
||||||
|
<tabstop>cmbBoxIndicator</tabstop>
|
||||||
|
<tabstop>cmbBoxBorder</tabstop>
|
||||||
|
<tabstop>btnBorderColor</tabstop>
|
||||||
|
<tabstop>spinBorderWidth</tabstop>
|
||||||
|
<tabstop>chkBlockNetShare</tabstop>
|
||||||
|
<tabstop>chkBlockNetParam</tabstop>
|
||||||
|
<tabstop>chkDropRights</tabstop>
|
||||||
|
<tabstop>chkBlockSpooler</tabstop>
|
||||||
|
<tabstop>chkOpenSpooler</tabstop>
|
||||||
|
<tabstop>chkPrintToFile</tabstop>
|
||||||
|
<tabstop>treeRun</tabstop>
|
||||||
|
<tabstop>btnAddCmd</tabstop>
|
||||||
|
<tabstop>btnDelCmd</tabstop>
|
||||||
|
<tabstop>chkCopyLimit</tabstop>
|
||||||
|
<tabstop>txtCopyLimit</tabstop>
|
||||||
|
<tabstop>chkNoCopyWarn</tabstop>
|
||||||
|
<tabstop>chkAutoEmpty</tabstop>
|
||||||
|
<tabstop>chkProtectBox</tabstop>
|
||||||
|
<tabstop>treeAutoStart</tabstop>
|
||||||
|
<tabstop>btnAddAutoExe</tabstop>
|
||||||
|
<tabstop>btnAddAutoSvc</tabstop>
|
||||||
|
<tabstop>btnDelAuto</tabstop>
|
||||||
|
<tabstop>treeGroups</tabstop>
|
||||||
|
<tabstop>btnAddGroup</tabstop>
|
||||||
|
<tabstop>btnAddProg</tabstop>
|
||||||
|
<tabstop>btnDelProg</tabstop>
|
||||||
|
<tabstop>treeForced</tabstop>
|
||||||
|
<tabstop>btnForceProg</tabstop>
|
||||||
|
<tabstop>btnForceDir</tabstop>
|
||||||
|
<tabstop>chkShowForceTmpl</tabstop>
|
||||||
|
<tabstop>btnDelForce</tabstop>
|
||||||
|
<tabstop>treeStop</tabstop>
|
||||||
|
<tabstop>btnAddLingering</tabstop>
|
||||||
|
<tabstop>btnAddLeader</tabstop>
|
||||||
|
<tabstop>chkShowStopTmpl</tabstop>
|
||||||
|
<tabstop>btnDelStopProg</tabstop>
|
||||||
|
<tabstop>radStartAll</tabstop>
|
||||||
|
<tabstop>radStartExcept</tabstop>
|
||||||
|
<tabstop>radStartSelected</tabstop>
|
||||||
|
<tabstop>treeStart</tabstop>
|
||||||
|
<tabstop>btnAddStartProg</tabstop>
|
||||||
|
<tabstop>btnDelStartProg</tabstop>
|
||||||
|
<tabstop>chkStartBlockMsg</tabstop>
|
||||||
|
<tabstop>chkBlockINet</tabstop>
|
||||||
|
<tabstop>chkINetBlockPrompt</tabstop>
|
||||||
|
<tabstop>treeINet</tabstop>
|
||||||
|
<tabstop>btnAddINetProg</tabstop>
|
||||||
|
<tabstop>btnDelINetProg</tabstop>
|
||||||
|
<tabstop>chkINetBlockMsg</tabstop>
|
||||||
|
<tabstop>treeAccess</tabstop>
|
||||||
|
<tabstop>btnAddFile</tabstop>
|
||||||
|
<tabstop>btnAddKey</tabstop>
|
||||||
|
<tabstop>btnAddIPC</tabstop>
|
||||||
|
<tabstop>btnAddWnd</tabstop>
|
||||||
|
<tabstop>btnAddCOM</tabstop>
|
||||||
|
<tabstop>btnMoveUp</tabstop>
|
||||||
|
<tabstop>btnMoveDown</tabstop>
|
||||||
|
<tabstop>chkShowAccessTmpl</tabstop>
|
||||||
|
<tabstop>btnDelAccess</tabstop>
|
||||||
|
<tabstop>chkAutoRecovery</tabstop>
|
||||||
|
<tabstop>treeRecovery</tabstop>
|
||||||
|
<tabstop>btnAddRecovery</tabstop>
|
||||||
|
<tabstop>btnAddRecIgnore</tabstop>
|
||||||
|
<tabstop>btnAddRecIgnoreExt</tabstop>
|
||||||
|
<tabstop>chkShowRecoveryTmpl</tabstop>
|
||||||
|
<tabstop>btnDelRecovery</tabstop>
|
||||||
|
<tabstop>tabsAdvanced</tabstop>
|
||||||
|
<tabstop>chkPreferExternalManifest</tabstop>
|
||||||
|
<tabstop>chkNoWindowRename</tabstop>
|
||||||
|
<tabstop>chkAddToJob</tabstop>
|
||||||
|
<tabstop>chkRestrictServices</tabstop>
|
||||||
|
<tabstop>chkProtectSCM</tabstop>
|
||||||
|
<tabstop>chkProtectSystem</tabstop>
|
||||||
|
<tabstop>chkOpenProtectedStorage</tabstop>
|
||||||
|
<tabstop>chkOpenCredentials</tabstop>
|
||||||
|
<tabstop>chkOpenSmartCard</tabstop>
|
||||||
|
<tabstop>lstAutoExec</tabstop>
|
||||||
|
<tabstop>btnAddAutoExec</tabstop>
|
||||||
|
<tabstop>btnDelAutoExec</tabstop>
|
||||||
|
<tabstop>chkHideOtherBoxes</tabstop>
|
||||||
|
<tabstop>lstProcesses</tabstop>
|
||||||
|
<tabstop>btnAddProcess</tabstop>
|
||||||
|
<tabstop>btnDelProcess</tabstop>
|
||||||
|
<tabstop>lstUsers</tabstop>
|
||||||
|
<tabstop>btnAddUser</tabstop>
|
||||||
|
<tabstop>btnDelUser</tabstop>
|
||||||
|
<tabstop>chkMonitorAdminOnly</tabstop>
|
||||||
|
<tabstop>chkFileTrace</tabstop>
|
||||||
|
<tabstop>chkPipeTrace</tabstop>
|
||||||
|
<tabstop>chkKeyTrace</tabstop>
|
||||||
|
<tabstop>chkIpcTrace</tabstop>
|
||||||
|
<tabstop>chkGuiTrace</tabstop>
|
||||||
|
<tabstop>chkComTrace</tabstop>
|
||||||
|
<tabstop>chkDbgTrace</tabstop>
|
||||||
|
<tabstop>scrollArea</tabstop>
|
||||||
|
<tabstop>treeTemplates</tabstop>
|
||||||
|
<tabstop>cmbCategories</tabstop>
|
||||||
|
<tabstop>txtTemplates</tabstop>
|
||||||
|
<tabstop>btnEditIni</tabstop>
|
||||||
|
<tabstop>txtIniSection</tabstop>
|
||||||
|
<tabstop>btnSaveIni</tabstop>
|
||||||
|
<tabstop>btnCancelEdit</tabstop>
|
||||||
|
</tabstops>
|
||||||
<resources/>
|
<resources/>
|
||||||
<connections/>
|
<connections/>
|
||||||
</ui>
|
</ui>
|
||||||
|
|
|
@ -36,53 +36,7 @@
|
||||||
<layout class="QVBoxLayout" name="verticalLayout">
|
<layout class="QVBoxLayout" name="verticalLayout">
|
||||||
<item>
|
<item>
|
||||||
<layout class="QGridLayout" name="gridLayout">
|
<layout class="QGridLayout" name="gridLayout">
|
||||||
<item row="0" column="0">
|
<item row="5" column="1">
|
||||||
<widget class="QTreeView" name="treeFiles"/>
|
|
||||||
</item>
|
|
||||||
<item row="3" column="0">
|
|
||||||
<layout class="QHBoxLayout" name="horizontalLayout">
|
|
||||||
<item>
|
|
||||||
<widget class="QPushButton" name="btnAddFolder">
|
|
||||||
<property name="text">
|
|
||||||
<string>Add Folder</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item>
|
|
||||||
<widget class="QPushButton" name="btnRefresh">
|
|
||||||
<property name="text">
|
|
||||||
<string>Refresh</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item>
|
|
||||||
<spacer name="horizontalSpacer">
|
|
||||||
<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>
|
|
||||||
<widget class="QPushButton" name="btnRecover">
|
|
||||||
<property name="text">
|
|
||||||
<string>Recover</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item>
|
|
||||||
<widget class="QPushButton" name="btnRecoverTo">
|
|
||||||
<property name="text">
|
|
||||||
<string>Recover to</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item>
|
|
||||||
<spacer name="horizontalSpacer_2">
|
<spacer name="horizontalSpacer_2">
|
||||||
<property name="orientation">
|
<property name="orientation">
|
||||||
<enum>Qt::Horizontal</enum>
|
<enum>Qt::Horizontal</enum>
|
||||||
|
@ -95,21 +49,77 @@
|
||||||
</property>
|
</property>
|
||||||
</spacer>
|
</spacer>
|
||||||
</item>
|
</item>
|
||||||
<item>
|
<item row="5" column="3">
|
||||||
<widget class="QPushButton" name="btnDeleteAll">
|
|
||||||
<property name="text">
|
|
||||||
<string>Delete all</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item>
|
|
||||||
<widget class="QPushButton" name="btnClose">
|
<widget class="QPushButton" name="btnClose">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Close</string>
|
<string>Close</string>
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
</layout>
|
<item row="1" column="0">
|
||||||
|
<widget class="QPushButton" name="btnRecoverTo">
|
||||||
|
<property name="text">
|
||||||
|
<string>Recover to</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="2" column="0">
|
||||||
|
<widget class="QPushButton" name="btnAddFolder">
|
||||||
|
<property name="text">
|
||||||
|
<string>Add Folder</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="0" column="0">
|
||||||
|
<widget class="QPushButton" name="btnRecover">
|
||||||
|
<property name="text">
|
||||||
|
<string>Recover</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="3" column="0">
|
||||||
|
<spacer name="verticalSpacer">
|
||||||
|
<property name="orientation">
|
||||||
|
<enum>Qt::Vertical</enum>
|
||||||
|
</property>
|
||||||
|
<property name="sizeHint" stdset="0">
|
||||||
|
<size>
|
||||||
|
<width>20</width>
|
||||||
|
<height>40</height>
|
||||||
|
</size>
|
||||||
|
</property>
|
||||||
|
</spacer>
|
||||||
|
</item>
|
||||||
|
<item row="5" column="0">
|
||||||
|
<widget class="QPushButton" name="btnRefresh">
|
||||||
|
<property name="text">
|
||||||
|
<string>Refresh</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="5" column="2">
|
||||||
|
<widget class="QPushButton" name="btnDeleteAll">
|
||||||
|
<property name="text">
|
||||||
|
<string>Delete all</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="4" column="0">
|
||||||
|
<widget class="QCheckBox" name="chkShowAll">
|
||||||
|
<property name="text">
|
||||||
|
<string>Show All Files</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="0" column="1" rowspan="4" colspan="3">
|
||||||
|
<widget class="QTreeView" name="treeFiles"/>
|
||||||
|
</item>
|
||||||
|
<item row="4" column="1" colspan="3">
|
||||||
|
<widget class="QLabel" name="lblInfo">
|
||||||
|
<property name="text">
|
||||||
|
<string>TextLabel</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
</layout>
|
</layout>
|
||||||
</item>
|
</item>
|
||||||
|
@ -117,6 +127,16 @@
|
||||||
</item>
|
</item>
|
||||||
</layout>
|
</layout>
|
||||||
</widget>
|
</widget>
|
||||||
|
<tabstops>
|
||||||
|
<tabstop>btnAddFolder</tabstop>
|
||||||
|
<tabstop>btnRecover</tabstop>
|
||||||
|
<tabstop>btnRecoverTo</tabstop>
|
||||||
|
<tabstop>treeFiles</tabstop>
|
||||||
|
<tabstop>chkShowAll</tabstop>
|
||||||
|
<tabstop>btnRefresh</tabstop>
|
||||||
|
<tabstop>btnDeleteAll</tabstop>
|
||||||
|
<tabstop>btnClose</tabstop>
|
||||||
|
</tabstops>
|
||||||
<resources/>
|
<resources/>
|
||||||
<connections/>
|
<connections/>
|
||||||
</ui>
|
</ui>
|
||||||
|
|
|
@ -6,7 +6,7 @@
|
||||||
<rect>
|
<rect>
|
||||||
<x>0</x>
|
<x>0</x>
|
||||||
<y>0</y>
|
<y>0</y>
|
||||||
<width>573</width>
|
<width>576</width>
|
||||||
<height>451</height>
|
<height>451</height>
|
||||||
</rect>
|
</rect>
|
||||||
</property>
|
</property>
|
||||||
|
@ -45,7 +45,7 @@
|
||||||
<enum>QTabWidget::North</enum>
|
<enum>QTabWidget::North</enum>
|
||||||
</property>
|
</property>
|
||||||
<property name="currentIndex">
|
<property name="currentIndex">
|
||||||
<number>1</number>
|
<number>0</number>
|
||||||
</property>
|
</property>
|
||||||
<widget class="QWidget" name="tabGeneral">
|
<widget class="QWidget" name="tabGeneral">
|
||||||
<attribute name="title">
|
<attribute name="title">
|
||||||
|
@ -54,20 +54,7 @@
|
||||||
<layout class="QGridLayout" name="gridLayout_9">
|
<layout class="QGridLayout" name="gridLayout_9">
|
||||||
<item row="0" column="0">
|
<item row="0" column="0">
|
||||||
<layout class="QGridLayout" name="gridLayout_8">
|
<layout class="QGridLayout" name="gridLayout_8">
|
||||||
<item row="5" column="1" colspan="2">
|
<item row="12" column="1">
|
||||||
<widget class="QCheckBox" name="chkNotifications">
|
|
||||||
<property name="text">
|
|
||||||
<string>Show Notifications for relevant log Messages</string>
|
|
||||||
</property>
|
|
||||||
<property name="checked">
|
|
||||||
<bool>false</bool>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item row="0" column="1">
|
|
||||||
<widget class="QComboBox" name="uiLang"/>
|
|
||||||
</item>
|
|
||||||
<item row="11" column="1">
|
|
||||||
<spacer name="verticalSpacer_4">
|
<spacer name="verticalSpacer_4">
|
||||||
<property name="orientation">
|
<property name="orientation">
|
||||||
<enum>Qt::Vertical</enum>
|
<enum>Qt::Vertical</enum>
|
||||||
|
@ -80,32 +67,18 @@
|
||||||
</property>
|
</property>
|
||||||
</spacer>
|
</spacer>
|
||||||
</item>
|
</item>
|
||||||
<item row="3" column="1" colspan="2">
|
<item row="6" column="1" colspan="2">
|
||||||
<widget class="QCheckBox" name="chkAutoUpdate">
|
<widget class="QCheckBox" name="chkNotifications">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Check periodically for updates of Sandboxie-Plus</string>
|
<string>Show Notifications for relevant log Messages</string>
|
||||||
|
</property>
|
||||||
|
<property name="checked">
|
||||||
|
<bool>false</bool>
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="10" column="0">
|
<item row="0" column="1">
|
||||||
<widget class="QLabel" name="label_18">
|
<widget class="QComboBox" name="uiLang"/>
|
||||||
<property name="text">
|
|
||||||
<string>On main window close:</string>
|
|
||||||
</property>
|
|
||||||
<property name="alignment">
|
|
||||||
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item row="2" column="1">
|
|
||||||
<widget class="QCheckBox" name="chkAutoStart">
|
|
||||||
<property name="text">
|
|
||||||
<string>Start with Windows</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item row="10" column="1">
|
|
||||||
<widget class="QComboBox" name="onClose"/>
|
|
||||||
</item>
|
</item>
|
||||||
<item row="1" column="1">
|
<item row="1" column="1">
|
||||||
<widget class="QCheckBox" name="chkDarkTheme">
|
<widget class="QCheckBox" name="chkDarkTheme">
|
||||||
|
@ -114,57 +87,31 @@
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="4" column="1" colspan="2">
|
<item row="10" column="1">
|
||||||
<widget class="QCheckBox" name="chkShellMenu">
|
|
||||||
<property name="text">
|
|
||||||
<string>Add 'Run Sandboxed' to the explorer context menu</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item row="9" column="1">
|
|
||||||
<widget class="QCheckBox" name="chkShowTray">
|
<widget class="QCheckBox" name="chkShowTray">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Show Sys-Tray</string>
|
<string>Show Sys-Tray</string>
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="11" column="2">
|
<item row="7" column="1" colspan="2">
|
||||||
<spacer name="horizontalSpacer_8">
|
<widget class="QCheckBox" name="chkSandboxUrls">
|
||||||
<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="8" column="0">
|
|
||||||
<widget class="QLabel" name="label_5">
|
|
||||||
<property name="font">
|
|
||||||
<font>
|
|
||||||
<weight>75</weight>
|
|
||||||
<bold>true</bold>
|
|
||||||
</font>
|
|
||||||
</property>
|
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Tray options</string>
|
<string>Open urls from this ui sandboxed</string>
|
||||||
|
</property>
|
||||||
|
<property name="tristate">
|
||||||
|
<bool>true</bool>
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="0" column="2">
|
<item row="4" column="1" colspan="2">
|
||||||
<widget class="QLabel" name="label">
|
<widget class="QCheckBox" name="chkAutoUpdate">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Restart required (!)</string>
|
<string>Check periodically for updates of Sandboxie-Plus</string>
|
||||||
</property>
|
|
||||||
<property name="alignment">
|
|
||||||
<set>Qt::AlignCenter</set>
|
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="11" column="0">
|
<item row="12" column="0">
|
||||||
<spacer name="horizontalSpacer_9">
|
<spacer name="horizontalSpacer_9">
|
||||||
<property name="orientation">
|
<property name="orientation">
|
||||||
<enum>Qt::Horizontal</enum>
|
<enum>Qt::Horizontal</enum>
|
||||||
|
@ -177,20 +124,80 @@
|
||||||
</property>
|
</property>
|
||||||
</spacer>
|
</spacer>
|
||||||
</item>
|
</item>
|
||||||
<item row="6" column="1" colspan="2">
|
<item row="0" column="2">
|
||||||
<widget class="QCheckBox" name="chkSandboxUrls">
|
<widget class="QLabel" name="label">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Open urls from this ui sandboxed</string>
|
<string>Restart required (!)</string>
|
||||||
</property>
|
</property>
|
||||||
<property name="tristate">
|
<property name="alignment">
|
||||||
<bool>true</bool>
|
<set>Qt::AlignCenter</set>
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="7" column="1">
|
<item row="11" column="1">
|
||||||
<widget class="QCheckBox" name="chkWatchConfig">
|
<widget class="QComboBox" name="onClose"/>
|
||||||
|
</item>
|
||||||
|
<item row="2" column="1">
|
||||||
|
<widget class="QCheckBox" name="chkAutoStart">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Watch Sandboxie.ini for changes</string>
|
<string>Start UI with Windows</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="5" column="1" colspan="2">
|
||||||
|
<widget class="QCheckBox" name="chkShellMenu">
|
||||||
|
<property name="text">
|
||||||
|
<string>Add 'Run Sandboxed' to the explorer context menu</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="11" column="0">
|
||||||
|
<widget class="QLabel" name="label_18">
|
||||||
|
<property name="text">
|
||||||
|
<string>On main window close:</string>
|
||||||
|
</property>
|
||||||
|
<property name="alignment">
|
||||||
|
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="12" column="2">
|
||||||
|
<spacer name="horizontalSpacer_8">
|
||||||
|
<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="9" column="0">
|
||||||
|
<widget class="QLabel" name="label_5">
|
||||||
|
<property name="font">
|
||||||
|
<font>
|
||||||
|
<weight>75</weight>
|
||||||
|
<bold>true</bold>
|
||||||
|
</font>
|
||||||
|
</property>
|
||||||
|
<property name="text">
|
||||||
|
<string>Tray options</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="3" column="1" colspan="2">
|
||||||
|
<widget class="QCheckBox" name="chkSvcStart">
|
||||||
|
<property name="text">
|
||||||
|
<string>Start UI when a sandboxed process is started</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="8" column="1" colspan="2">
|
||||||
|
<widget class="QCheckBox" name="chkShowRecovery">
|
||||||
|
<property name="text">
|
||||||
|
<string>Show first recovery window when emptying sandboxes</string>
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
|
@ -205,21 +212,10 @@
|
||||||
<layout class="QGridLayout" name="gridLayout_6">
|
<layout class="QGridLayout" name="gridLayout_6">
|
||||||
<item row="0" column="0">
|
<item row="0" column="0">
|
||||||
<layout class="QGridLayout" name="gridLayout_5">
|
<layout class="QGridLayout" name="gridLayout_5">
|
||||||
<item row="8" column="1" colspan="2">
|
<item row="1" column="2" colspan="4">
|
||||||
<widget class="QCheckBox" name="chkAdminOnlyFP">
|
<widget class="QLineEdit" name="fileRoot"/>
|
||||||
<property name="text">
|
|
||||||
<string>Only Administrator user accounts can use Disable Forced Programs command</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
</item>
|
||||||
<item row="6" column="1">
|
<item row="7" column="0" colspan="2">
|
||||||
<widget class="QCheckBox" name="chkAdminOnly">
|
|
||||||
<property name="text">
|
|
||||||
<string>Only Administrator user accounts can make changes</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item row="5" column="0">
|
|
||||||
<widget class="QLabel" name="label_44">
|
<widget class="QLabel" name="label_44">
|
||||||
<property name="font">
|
<property name="font">
|
||||||
<font>
|
<font>
|
||||||
|
@ -232,25 +228,87 @@
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="7" column="1">
|
<item row="4" column="0" colspan="2">
|
||||||
<widget class="QCheckBox" name="chkPassRequired">
|
<widget class="QLabel" name="label_17">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Password must be entered in order to make changes</string>
|
<string>Sandbox <a href="sbie://docs/ipcrootpath">ipc root</a>: </string>
|
||||||
|
</property>
|
||||||
|
<property name="alignment">
|
||||||
|
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
||||||
|
</property>
|
||||||
|
<property name="openExternalLinks">
|
||||||
|
<bool>true</bool>
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="7" column="2">
|
<item row="12" column="2">
|
||||||
<widget class="QPushButton" name="btnSetPassword">
|
<spacer name="verticalSpacer_2">
|
||||||
|
<property name="orientation">
|
||||||
|
<enum>Qt::Vertical</enum>
|
||||||
|
</property>
|
||||||
|
<property name="sizeHint" stdset="0">
|
||||||
|
<size>
|
||||||
|
<width>20</width>
|
||||||
|
<height>40</height>
|
||||||
|
</size>
|
||||||
|
</property>
|
||||||
|
</spacer>
|
||||||
|
</item>
|
||||||
|
<item row="3" column="2" colspan="4">
|
||||||
|
<widget class="QLineEdit" name="regRoot"/>
|
||||||
|
</item>
|
||||||
|
<item row="3" column="0" colspan="2">
|
||||||
|
<widget class="QLabel" name="label_16">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Change Password</string>
|
<string>Sandbox <a href="sbie://docs/keyrootpath">registry root</a>: </string>
|
||||||
|
</property>
|
||||||
|
<property name="alignment">
|
||||||
|
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
||||||
|
</property>
|
||||||
|
<property name="openExternalLinks">
|
||||||
|
<bool>true</bool>
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="1" column="1" colspan="2">
|
<item row="4" column="2" colspan="4">
|
||||||
<widget class="QLineEdit" name="fileRoot"/>
|
<widget class="QLineEdit" name="ipcRoot"/>
|
||||||
</item>
|
</item>
|
||||||
<item row="0" column="1">
|
<item row="11" column="1" colspan="5">
|
||||||
<spacer name="horizontalSpacer_2">
|
<widget class="QCheckBox" name="chkClearPass">
|
||||||
|
<property name="text">
|
||||||
|
<string>Clear password when main window becomes hidden</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="10" column="1" colspan="5">
|
||||||
|
<widget class="QCheckBox" name="chkAdminOnlyFP">
|
||||||
|
<property name="text">
|
||||||
|
<string>Only Administrator user accounts can use Disable Forced Programs command</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="1" column="0" colspan="2">
|
||||||
|
<widget class="QLabel" name="label_15">
|
||||||
|
<property name="text">
|
||||||
|
<string>Sandbox <a href="sbie://docs/filerootpath">file system root</a>: </string>
|
||||||
|
</property>
|
||||||
|
<property name="alignment">
|
||||||
|
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
||||||
|
</property>
|
||||||
|
<property name="openExternalLinks">
|
||||||
|
<bool>true</bool>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="2" column="2">
|
||||||
|
<widget class="QCheckBox" name="chkSeparateUserFolders">
|
||||||
|
<property name="text">
|
||||||
|
<string>Separate user folders</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="12" column="1">
|
||||||
|
<spacer name="horizontalSpacer_4">
|
||||||
<property name="orientation">
|
<property name="orientation">
|
||||||
<enum>Qt::Horizontal</enum>
|
<enum>Qt::Horizontal</enum>
|
||||||
</property>
|
</property>
|
||||||
|
@ -262,8 +320,72 @@
|
||||||
</property>
|
</property>
|
||||||
</spacer>
|
</spacer>
|
||||||
</item>
|
</item>
|
||||||
<item row="3" column="1" colspan="2">
|
<item row="8" column="1" colspan="5">
|
||||||
<widget class="QLineEdit" name="regRoot"/>
|
<widget class="QCheckBox" name="chkAdminOnly">
|
||||||
|
<property name="text">
|
||||||
|
<string>Only Administrator user accounts can make changes</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="9" column="1" colspan="4">
|
||||||
|
<widget class="QCheckBox" name="chkPassRequired">
|
||||||
|
<property name="text">
|
||||||
|
<string>Password must be entered in order to make changes</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="9" column="5">
|
||||||
|
<widget class="QPushButton" name="btnSetPassword">
|
||||||
|
<property name="text">
|
||||||
|
<string>Change Password</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="2" column="5">
|
||||||
|
<widget class="QCheckBox" name="chkAutoRoot">
|
||||||
|
<property name="text">
|
||||||
|
<string>Portable root folder</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="1" column="6">
|
||||||
|
<widget class="QPushButton" name="btnBrowse">
|
||||||
|
<property name="maximumSize">
|
||||||
|
<size>
|
||||||
|
<width>23</width>
|
||||||
|
<height>16777215</height>
|
||||||
|
</size>
|
||||||
|
</property>
|
||||||
|
<property name="text">
|
||||||
|
<string>...</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="12" column="3">
|
||||||
|
<spacer name="horizontalSpacer">
|
||||||
|
<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="12" column="4">
|
||||||
|
<spacer name="horizontalSpacer_5">
|
||||||
|
<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>
|
||||||
<item row="0" column="0">
|
<item row="0" column="0">
|
||||||
<widget class="QLabel" name="label_43">
|
<widget class="QLabel" name="label_43">
|
||||||
|
@ -278,105 +400,23 @@
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="10" column="0">
|
<item row="5" column="0" colspan="2">
|
||||||
<spacer name="horizontalSpacer">
|
<widget class="QLabel" name="label_45">
|
||||||
<property name="orientation">
|
<property name="font">
|
||||||
<enum>Qt::Horizontal</enum>
|
<font>
|
||||||
|
<weight>75</weight>
|
||||||
|
<bold>true</bold>
|
||||||
|
</font>
|
||||||
</property>
|
</property>
|
||||||
<property name="sizeHint" stdset="0">
|
|
||||||
<size>
|
|
||||||
<width>40</width>
|
|
||||||
<height>20</height>
|
|
||||||
</size>
|
|
||||||
</property>
|
|
||||||
</spacer>
|
|
||||||
</item>
|
|
||||||
<item row="10" column="2">
|
|
||||||
<spacer name="horizontalSpacer_5">
|
|
||||||
<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="1" column="0">
|
|
||||||
<widget class="QLabel" name="label_15">
|
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Sandbox <a href="sbie://docs/filerootpath">file system root</a>: </string>
|
<string>Other settings</string>
|
||||||
</property>
|
|
||||||
<property name="alignment">
|
|
||||||
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
|
||||||
</property>
|
|
||||||
<property name="openExternalLinks">
|
|
||||||
<bool>true</bool>
|
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="4" column="0">
|
<item row="6" column="1" colspan="5">
|
||||||
<widget class="QLabel" name="label_17">
|
<widget class="QCheckBox" name="chkWatchConfig">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Sandbox <a href="sbie://docs/ipcrootpath">ipc root</a>: </string>
|
<string>Watch Sandboxie.ini for changes</string>
|
||||||
</property>
|
|
||||||
<property name="alignment">
|
|
||||||
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
|
||||||
</property>
|
|
||||||
<property name="openExternalLinks">
|
|
||||||
<bool>true</bool>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item row="4" column="1" colspan="2">
|
|
||||||
<widget class="QLineEdit" name="ipcRoot"/>
|
|
||||||
</item>
|
|
||||||
<item row="3" column="0">
|
|
||||||
<widget class="QLabel" name="label_16">
|
|
||||||
<property name="text">
|
|
||||||
<string>Sandbox <a href="sbie://docs/keyrootpath">registry root</a>: </string>
|
|
||||||
</property>
|
|
||||||
<property name="alignment">
|
|
||||||
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
|
||||||
</property>
|
|
||||||
<property name="openExternalLinks">
|
|
||||||
<bool>true</bool>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item row="10" column="1">
|
|
||||||
<spacer name="verticalSpacer_2">
|
|
||||||
<property name="orientation">
|
|
||||||
<enum>Qt::Vertical</enum>
|
|
||||||
</property>
|
|
||||||
<property name="sizeHint" stdset="0">
|
|
||||||
<size>
|
|
||||||
<width>20</width>
|
|
||||||
<height>40</height>
|
|
||||||
</size>
|
|
||||||
</property>
|
|
||||||
</spacer>
|
|
||||||
</item>
|
|
||||||
<item row="9" column="1">
|
|
||||||
<widget class="QCheckBox" name="chkClearPass">
|
|
||||||
<property name="text">
|
|
||||||
<string>Clear password when main window becomes hidden</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item row="2" column="1">
|
|
||||||
<widget class="QCheckBox" name="chkSeparateUserFolders">
|
|
||||||
<property name="text">
|
|
||||||
<string>Separate user folders</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item row="2" column="2">
|
|
||||||
<widget class="QCheckBox" name="chkAutoRoot">
|
|
||||||
<property name="text">
|
|
||||||
<string>Portable root folder</string>
|
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
|
@ -544,6 +584,42 @@
|
||||||
</item>
|
</item>
|
||||||
</layout>
|
</layout>
|
||||||
</widget>
|
</widget>
|
||||||
|
<tabstops>
|
||||||
|
<tabstop>tabs</tabstop>
|
||||||
|
<tabstop>uiLang</tabstop>
|
||||||
|
<tabstop>chkDarkTheme</tabstop>
|
||||||
|
<tabstop>chkAutoStart</tabstop>
|
||||||
|
<tabstop>chkSvcStart</tabstop>
|
||||||
|
<tabstop>chkAutoUpdate</tabstop>
|
||||||
|
<tabstop>chkShellMenu</tabstop>
|
||||||
|
<tabstop>chkNotifications</tabstop>
|
||||||
|
<tabstop>chkSandboxUrls</tabstop>
|
||||||
|
<tabstop>chkShowRecovery</tabstop>
|
||||||
|
<tabstop>chkShowTray</tabstop>
|
||||||
|
<tabstop>onClose</tabstop>
|
||||||
|
<tabstop>fileRoot</tabstop>
|
||||||
|
<tabstop>btnBrowse</tabstop>
|
||||||
|
<tabstop>chkSeparateUserFolders</tabstop>
|
||||||
|
<tabstop>chkAutoRoot</tabstop>
|
||||||
|
<tabstop>regRoot</tabstop>
|
||||||
|
<tabstop>ipcRoot</tabstop>
|
||||||
|
<tabstop>chkWatchConfig</tabstop>
|
||||||
|
<tabstop>chkAdminOnly</tabstop>
|
||||||
|
<tabstop>chkPassRequired</tabstop>
|
||||||
|
<tabstop>btnSetPassword</tabstop>
|
||||||
|
<tabstop>chkAdminOnlyFP</tabstop>
|
||||||
|
<tabstop>chkClearPass</tabstop>
|
||||||
|
<tabstop>chkStartBlock</tabstop>
|
||||||
|
<tabstop>treeWarnProgs</tabstop>
|
||||||
|
<tabstop>btnAddWarnProg</tabstop>
|
||||||
|
<tabstop>btnAddWarnFolder</tabstop>
|
||||||
|
<tabstop>btnDelWarnProg</tabstop>
|
||||||
|
<tabstop>chkStartBlockMsg</tabstop>
|
||||||
|
<tabstop>treeCompat</tabstop>
|
||||||
|
<tabstop>btnAddCompat</tabstop>
|
||||||
|
<tabstop>btnDelCompat</tabstop>
|
||||||
|
<tabstop>chkNoCompat</tabstop>
|
||||||
|
</tabstops>
|
||||||
<resources/>
|
<resources/>
|
||||||
<connections/>
|
<connections/>
|
||||||
</ui>
|
</ui>
|
||||||
|
|
|
@ -38,8 +38,26 @@
|
||||||
<layout class="QGridLayout" name="gridLayout">
|
<layout class="QGridLayout" name="gridLayout">
|
||||||
<item row="1" column="0">
|
<item row="1" column="0">
|
||||||
<widget class="QGroupBox" name="groupBox">
|
<widget class="QGroupBox" name="groupBox">
|
||||||
|
<property name="sizePolicy">
|
||||||
|
<sizepolicy hsizetype="Preferred" vsizetype="Ignored">
|
||||||
|
<horstretch>0</horstretch>
|
||||||
|
<verstretch>0</verstretch>
|
||||||
|
</sizepolicy>
|
||||||
|
</property>
|
||||||
|
<property name="minimumSize">
|
||||||
|
<size>
|
||||||
|
<width>0</width>
|
||||||
|
<height>0</height>
|
||||||
|
</size>
|
||||||
|
</property>
|
||||||
|
<property name="maximumSize">
|
||||||
|
<size>
|
||||||
|
<width>16777215</width>
|
||||||
|
<height>16777215</height>
|
||||||
|
</size>
|
||||||
|
</property>
|
||||||
<property name="title">
|
<property name="title">
|
||||||
<string>Snapshot Details</string>
|
<string>Selected Snapshot Details</string>
|
||||||
</property>
|
</property>
|
||||||
<layout class="QGridLayout" name="gridLayout_3">
|
<layout class="QGridLayout" name="gridLayout_3">
|
||||||
<item row="0" column="0">
|
<item row="0" column="0">
|
||||||
|
@ -65,31 +83,59 @@
|
||||||
<item row="0" column="1">
|
<item row="0" column="1">
|
||||||
<widget class="QLineEdit" name="txtName"/>
|
<widget class="QLineEdit" name="txtName"/>
|
||||||
</item>
|
</item>
|
||||||
<item row="2" column="3">
|
</layout>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="1" column="1">
|
||||||
|
<widget class="QGroupBox" name="groupBox_2">
|
||||||
|
<property name="maximumSize">
|
||||||
|
<size>
|
||||||
|
<width>16777215</width>
|
||||||
|
<height>125</height>
|
||||||
|
</size>
|
||||||
|
</property>
|
||||||
|
<property name="title">
|
||||||
|
<string>Snapshot Actions</string>
|
||||||
|
</property>
|
||||||
|
<layout class="QGridLayout" name="gridLayout_2">
|
||||||
|
<item row="3" column="0">
|
||||||
<widget class="QPushButton" name="btnRemove">
|
<widget class="QPushButton" name="btnRemove">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Remove Snapshot</string>
|
<string>Remove Snapshot</string>
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="0" column="3">
|
<item row="2" column="0">
|
||||||
<widget class="QPushButton" name="btnTake">
|
|
||||||
<property name="text">
|
|
||||||
<string>Take Snapshot</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
<item row="1" column="3">
|
|
||||||
<widget class="QPushButton" name="btnSelect">
|
<widget class="QPushButton" name="btnSelect">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
<string>Go to Snapshot</string>
|
<string>Go to Snapshot</string>
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
|
<item row="0" column="0">
|
||||||
|
<widget class="QPushButton" name="btnTake">
|
||||||
|
<property name="text">
|
||||||
|
<string>Take Snapshot</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="1" column="0">
|
||||||
|
<spacer name="verticalSpacer">
|
||||||
|
<property name="orientation">
|
||||||
|
<enum>Qt::Vertical</enum>
|
||||||
|
</property>
|
||||||
|
<property name="sizeHint" stdset="0">
|
||||||
|
<size>
|
||||||
|
<width>20</width>
|
||||||
|
<height>40</height>
|
||||||
|
</size>
|
||||||
|
</property>
|
||||||
|
</spacer>
|
||||||
|
</item>
|
||||||
</layout>
|
</layout>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="0" column="0">
|
<item row="0" column="0" colspan="2">
|
||||||
<widget class="QTreeView" name="treeSnapshots"/>
|
<widget class="QTreeView" name="treeSnapshots"/>
|
||||||
</item>
|
</item>
|
||||||
</layout>
|
</layout>
|
||||||
|
@ -98,6 +144,14 @@
|
||||||
</item>
|
</item>
|
||||||
</layout>
|
</layout>
|
||||||
</widget>
|
</widget>
|
||||||
|
<tabstops>
|
||||||
|
<tabstop>btnTake</tabstop>
|
||||||
|
<tabstop>treeSnapshots</tabstop>
|
||||||
|
<tabstop>btnSelect</tabstop>
|
||||||
|
<tabstop>btnRemove</tabstop>
|
||||||
|
<tabstop>txtName</tabstop>
|
||||||
|
<tabstop>txtInfo</tabstop>
|
||||||
|
</tabstops>
|
||||||
<resources/>
|
<resources/>
|
||||||
<connections/>
|
<connections/>
|
||||||
</ui>
|
</ui>
|
||||||
|
|
|
@ -0,0 +1,8 @@
|
||||||
|
Copyright 2020 – 2021 David Xanatos (xanasoft.com)
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
|
||||||
|
INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
|
||||||
|
PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
||||||
|
HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
|
||||||
|
CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE
|
||||||
|
OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|
@ -113,6 +113,8 @@ CSandMan::CSandMan(QWidget *parent)
|
||||||
QString appTitle = tr("Sandboxie-Plus v%1").arg(GetVersion());
|
QString appTitle = tr("Sandboxie-Plus v%1").arg(GetVersion());
|
||||||
this->setWindowTitle(appTitle);
|
this->setWindowTitle(appTitle);
|
||||||
|
|
||||||
|
setAcceptDrops(true);
|
||||||
|
|
||||||
m_pBoxBorder = new CBoxBorder(theAPI, this);
|
m_pBoxBorder = new CBoxBorder(theAPI, this);
|
||||||
|
|
||||||
m_SbieTemplates = new CSbieTemplates(theAPI, this);
|
m_SbieTemplates = new CSbieTemplates(theAPI, this);
|
||||||
|
@ -250,6 +252,10 @@ CSandMan::CSandMan(QWidget *parent)
|
||||||
pAction->setChecked(pAction->data().toBool() == bAdvanced);
|
pAction->setChecked(pAction->data().toBool() == bAdvanced);
|
||||||
SetViewMode(bAdvanced);
|
SetViewMode(bAdvanced);
|
||||||
|
|
||||||
|
bool bAlwaysOnTop = theConf->GetBool("Options/AlwaysOnTop", false);
|
||||||
|
m_pWndTopMost->setChecked(bAlwaysOnTop);
|
||||||
|
this->setWindowFlag(Qt::WindowStaysOnTopHint, bAlwaysOnTop);
|
||||||
|
|
||||||
m_pKeepTerminated->setChecked(theConf->GetBool("Options/KeepTerminated"));
|
m_pKeepTerminated->setChecked(theConf->GetBool("Options/KeepTerminated"));
|
||||||
|
|
||||||
m_pProgressDialog = new CProgressDialog("", this);
|
m_pProgressDialog = new CProgressDialog("", this);
|
||||||
|
@ -372,6 +378,11 @@ void CSandMan::CreateMenus()
|
||||||
MakeAction(m_pViewMode, m_pMenuView, tr("Simple View"), false);
|
MakeAction(m_pViewMode, m_pMenuView, tr("Simple View"), false);
|
||||||
MakeAction(m_pViewMode, m_pMenuView, tr("Advanced View"), true);
|
MakeAction(m_pViewMode, m_pMenuView, tr("Advanced View"), true);
|
||||||
connect(m_pViewMode, SIGNAL(triggered(QAction*)), this, SLOT(OnViewMode(QAction*)));
|
connect(m_pViewMode, SIGNAL(triggered(QAction*)), this, SLOT(OnViewMode(QAction*)));
|
||||||
|
|
||||||
|
m_pMenuView->addSeparator();
|
||||||
|
m_pWndTopMost = m_pMenuView->addAction(tr("Always on Top"), this, SLOT(OnAlwaysTop()));
|
||||||
|
m_pWndTopMost->setCheckable(true);
|
||||||
|
|
||||||
m_iMenuViewPos = m_pMenuView->actions().count();
|
m_iMenuViewPos = m_pMenuView->actions().count();
|
||||||
m_pMenuView->addSeparator();
|
m_pMenuView->addSeparator();
|
||||||
|
|
||||||
|
@ -466,7 +477,7 @@ void CSandMan::OnExit()
|
||||||
|
|
||||||
void CSandMan::closeEvent(QCloseEvent *e)
|
void CSandMan::closeEvent(QCloseEvent *e)
|
||||||
{
|
{
|
||||||
if (!m_bExit)
|
if (!m_bExit)// && !theAPI->IsConnected())
|
||||||
{
|
{
|
||||||
QString OnClose = theConf->GetString("Options/OnClose", "ToTray");
|
QString OnClose = theConf->GetString("Options/OnClose", "ToTray");
|
||||||
if (m_pTrayIcon->isVisible() && OnClose.compare("ToTray", Qt::CaseInsensitive) == 0)
|
if (m_pTrayIcon->isVisible() && OnClose.compare("ToTray", Qt::CaseInsensitive) == 0)
|
||||||
|
@ -550,8 +561,12 @@ void CSandMan::OnMessage(const QString& Message)
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
OnLogMessage(tr("Maintenance operation Successful"));
|
OnLogMessage(tr("Maintenance operation Successful"));
|
||||||
if (m_bConnectPending)
|
if (m_bConnectPending) {
|
||||||
ConnectSbieImpl();
|
|
||||||
|
QTimer::singleShot(1000, [this]() {
|
||||||
|
this->ConnectSbieImpl();
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
m_pProgressDialog->hide();
|
m_pProgressDialog->hide();
|
||||||
m_bConnectPending = false;
|
m_bConnectPending = false;
|
||||||
|
@ -559,6 +574,29 @@ void CSandMan::OnMessage(const QString& Message)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void CSandMan::dragEnterEvent(QDragEnterEvent* e)
|
||||||
|
{
|
||||||
|
if (e->mimeData()->hasUrls()) {
|
||||||
|
e->acceptProposedAction();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void CSandMan::dropEvent(QDropEvent* e)
|
||||||
|
{
|
||||||
|
bool ok;
|
||||||
|
QString box = QInputDialog::getItem(this, "Sandboxie-Plus", tr("Select box:"), theAPI->GetAllBoxes().keys(), 0, false, &ok);
|
||||||
|
if (!ok || box.isEmpty())
|
||||||
|
return;
|
||||||
|
|
||||||
|
foreach(const QUrl & url, e->mimeData()->urls()) {
|
||||||
|
if (!url.isLocalFile())
|
||||||
|
continue;
|
||||||
|
QString FileName = url.toLocalFile().replace("/", "\\");
|
||||||
|
|
||||||
|
theAPI->RunStart(box, FileName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void CSandMan::timerEvent(QTimerEvent* pEvent)
|
void CSandMan::timerEvent(QTimerEvent* pEvent)
|
||||||
{
|
{
|
||||||
if (pEvent->timerId() != m_uTimerID)
|
if (pEvent->timerId() != m_uTimerID)
|
||||||
|
@ -566,7 +604,13 @@ void CSandMan::timerEvent(QTimerEvent* pEvent)
|
||||||
|
|
||||||
if (theAPI->IsConnected())
|
if (theAPI->IsConnected())
|
||||||
{
|
{
|
||||||
theAPI->ReloadBoxes();
|
SB_STATUS Status = theAPI->ReloadBoxes();
|
||||||
|
|
||||||
|
if (!Status.IsError() && theAPI->GetAllBoxes().count() == 0) {
|
||||||
|
OnLogMessage(tr("No sandboxes found; creating: %1").arg("DefaultBox"));
|
||||||
|
theAPI->CreateBox("DefaultBox");
|
||||||
|
}
|
||||||
|
|
||||||
theAPI->UpdateProcesses(m_pKeepTerminated->isChecked());
|
theAPI->UpdateProcesses(m_pKeepTerminated->isChecked());
|
||||||
|
|
||||||
m_pDisableForce->setChecked(theAPI->AreForceProcessDisabled());
|
m_pDisableForce->setChecked(theAPI->AreForceProcessDisabled());
|
||||||
|
@ -633,6 +677,41 @@ void CSandMan::timerEvent(QTimerEvent* pEvent)
|
||||||
m_RequestManager->AbortAll();
|
m_RequestManager->AbortAll();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!m_MissingTemplates.isEmpty())
|
||||||
|
{
|
||||||
|
if (m_MissingTemplates[0] == "") {
|
||||||
|
m_MissingTemplates.clear();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
int CleanupTemplates = theConf->GetInt("Options/AutoCleanupTemplates", -1);
|
||||||
|
if (CleanupTemplates == -1)
|
||||||
|
{
|
||||||
|
bool State = false;
|
||||||
|
CleanupTemplates = CCheckableMessageBox::question(this, "Sandboxie-Plus", tr("Some compatibility templates (%1) are missing, probably deleted, do you want to remove them from all boxes?")
|
||||||
|
.arg(m_MissingTemplates.join(", "))
|
||||||
|
, tr("Don't show this message again."), &State, QDialogButtonBox::Yes | QDialogButtonBox::No, QDialogButtonBox::Yes, QMessageBox::Information) == QDialogButtonBox::Yes ? 1 : 0;
|
||||||
|
|
||||||
|
if (State)
|
||||||
|
theConf->SetValue("Options/AutoCleanupTemplates", CleanupTemplates);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (CleanupTemplates)
|
||||||
|
{
|
||||||
|
foreach(const QString& Template, m_MissingTemplates)
|
||||||
|
{
|
||||||
|
theAPI->GetGlobalSettings()->DelValue("Template", Template);
|
||||||
|
foreach(const CSandBoxPtr& pBox, theAPI->GetAllBoxes())
|
||||||
|
pBox->DelValue("Template", Template);
|
||||||
|
}
|
||||||
|
|
||||||
|
OnLogMessage(tr("Cleaned up removed templates..."));
|
||||||
|
}
|
||||||
|
m_MissingTemplates.clear();
|
||||||
|
|
||||||
|
m_MissingTemplates.append("");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void CSandMan::OnBoxClosed(const QString& BoxName)
|
void CSandMan::OnBoxClosed(const QString& BoxName)
|
||||||
|
@ -641,7 +720,7 @@ void CSandMan::OnBoxClosed(const QString& BoxName)
|
||||||
if (!pBox)
|
if (!pBox)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (!pBox->GetBool("NeverDelete", false) && pBox->GetBool("AutoDelete", false))
|
if (!pBox->GetBool("NeverDelete", false) && pBox->GetBool("AutoDelete", false) && !pBox->IsEmpty())
|
||||||
{
|
{
|
||||||
CRecoveryWindow* pRecoveryWindow = new CRecoveryWindow(pBox, this);
|
CRecoveryWindow* pRecoveryWindow = new CRecoveryWindow(pBox, this);
|
||||||
if (pRecoveryWindow->FindFiles() == 0)
|
if (pRecoveryWindow->FindFiles() == 0)
|
||||||
|
@ -685,7 +764,8 @@ void CSandMan::OnStatusChanged()
|
||||||
QString appTitle = tr("Sandboxie-Plus v%1").arg(GetVersion());
|
QString appTitle = tr("Sandboxie-Plus v%1").arg(GetVersion());
|
||||||
if (isConnected)
|
if (isConnected)
|
||||||
{
|
{
|
||||||
OnLogMessage(tr("Sbie Directory: %1").arg(theAPI->GetSbiePath()));
|
QString SbiePath = theAPI->GetSbiePath();
|
||||||
|
OnLogMessage(tr("Sbie Directory: %1").arg(SbiePath));
|
||||||
OnLogMessage(tr("Loaded Config: %1").arg(theAPI->GetIniPath()));
|
OnLogMessage(tr("Loaded Config: %1").arg(theAPI->GetIniPath()));
|
||||||
|
|
||||||
statusBar()->showMessage(tr("Driver version: %1").arg(theAPI->GetVersion()));
|
statusBar()->showMessage(tr("Driver version: %1").arg(theAPI->GetVersion()));
|
||||||
|
@ -723,6 +803,12 @@ void CSandMan::OnStatusChanged()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (SbiePath.compare(QApplication::applicationDirPath().replace("/", "\\"), Qt::CaseInsensitive) == 0)
|
||||||
|
{
|
||||||
|
if (theAPI->GetUserSettings()->GetText("SbieCtrl_AutoStartAgent").isEmpty())
|
||||||
|
theAPI->GetUserSettings()->SetText("SbieCtrl_AutoStartAgent", "SandMan.exe");
|
||||||
|
}
|
||||||
|
|
||||||
m_pBoxView->Clear();
|
m_pBoxView->Clear();
|
||||||
|
|
||||||
OnIniReloaded();
|
OnIniReloaded();
|
||||||
|
@ -811,6 +897,12 @@ void CSandMan::OnLogSbieMessage(quint32 MsgCode, const QStringList& MsgData, qui
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ((MsgCode & 0xFFFF) == 1411) // removed/missing template
|
||||||
|
{
|
||||||
|
if(MsgData.size() >= 3 && !m_MissingTemplates.contains(MsgData[2]))
|
||||||
|
m_MissingTemplates.append(MsgData[2]);
|
||||||
|
}
|
||||||
|
|
||||||
QString Message = MsgCode != 0 ? theAPI->GetSbieMsgStr(MsgCode, m_LanguageId) : (MsgData.size() > 0 ? MsgData[0] : QString());
|
QString Message = MsgCode != 0 ? theAPI->GetSbieMsgStr(MsgCode, m_LanguageId) : (MsgData.size() > 0 ? MsgData[0] : QString());
|
||||||
|
|
||||||
for (int i = 1; i < MsgData.size(); i++)
|
for (int i = 1; i < MsgData.size(); i++)
|
||||||
|
@ -1030,17 +1122,9 @@ SB_STATUS CSandMan::ConnectSbieImpl()
|
||||||
if (Status && !CSbieAPI::IsSbieCtrlRunning()) // don't take over when SbieCtrl is up and running
|
if (Status && !CSbieAPI::IsSbieCtrlRunning()) // don't take over when SbieCtrl is up and running
|
||||||
Status = theAPI->TakeOver();
|
Status = theAPI->TakeOver();
|
||||||
|
|
||||||
if (Status)
|
|
||||||
Status = theAPI->ReloadBoxes();
|
|
||||||
|
|
||||||
if (!Status)
|
if (!Status)
|
||||||
return Status;
|
return Status;
|
||||||
|
|
||||||
if (theAPI->GetAllBoxes().count() == 0) {
|
|
||||||
OnLogMessage(tr("No sandboxes found; creating: %1").arg("DefaultBox"));
|
|
||||||
theAPI->CreateBox("DefaultBox");
|
|
||||||
}
|
|
||||||
|
|
||||||
bool bIsMonitoring = theAPI->IsMonitoring();
|
bool bIsMonitoring = theAPI->IsMonitoring();
|
||||||
m_pResourceLog->setEnabled(bIsMonitoring);
|
m_pResourceLog->setEnabled(bIsMonitoring);
|
||||||
m_pEnableMonitoring->setChecked(bIsMonitoring);
|
m_pEnableMonitoring->setChecked(bIsMonitoring);
|
||||||
|
@ -1118,6 +1202,14 @@ void CSandMan::OnViewMode(QAction* pAction)
|
||||||
SetViewMode(bAdvanced);
|
SetViewMode(bAdvanced);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void CSandMan::OnAlwaysTop()
|
||||||
|
{
|
||||||
|
bool bAlwaysOnTop = m_pWndTopMost->isChecked();
|
||||||
|
theConf->SetValue("Options/AlwaysOnTop", bAlwaysOnTop);
|
||||||
|
this->setWindowFlag(Qt::WindowStaysOnTopHint, bAlwaysOnTop);
|
||||||
|
this->show(); // why is this needed?
|
||||||
|
}
|
||||||
|
|
||||||
void CSandMan::SetViewMode(bool bAdvanced)
|
void CSandMan::SetViewMode(bool bAdvanced)
|
||||||
{
|
{
|
||||||
if (bAdvanced)
|
if (bAdvanced)
|
||||||
|
@ -1179,10 +1271,17 @@ void CSandMan::OnSetKeep()
|
||||||
|
|
||||||
void CSandMan::OnSettings()
|
void CSandMan::OnSettings()
|
||||||
{
|
{
|
||||||
CSettingsWindow* pSettingsWindow = new CSettingsWindow(this);
|
static CSettingsWindow* pSettingsWindow = NULL;
|
||||||
|
if (pSettingsWindow == NULL)
|
||||||
|
{
|
||||||
|
pSettingsWindow = new CSettingsWindow(this);
|
||||||
connect(pSettingsWindow, SIGNAL(OptionsChanged()), this, SLOT(UpdateSettings()));
|
connect(pSettingsWindow, SIGNAL(OptionsChanged()), this, SLOT(UpdateSettings()));
|
||||||
|
connect(pSettingsWindow, &CSettingsWindow::Closed, [this]() {
|
||||||
|
pSettingsWindow = NULL;
|
||||||
|
});
|
||||||
pSettingsWindow->show();
|
pSettingsWindow->show();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void CSandMan::UpdateSettings()
|
void CSandMan::UpdateSettings()
|
||||||
{
|
{
|
||||||
|
@ -1214,7 +1313,12 @@ void CSandMan::OnResetMsgs()
|
||||||
theConf->SetValue("Options/NoEditInfo", true);
|
theConf->SetValue("Options/NoEditInfo", true);
|
||||||
theConf->SetValue("Options/ApiLogInfo", true);
|
theConf->SetValue("Options/ApiLogInfo", true);
|
||||||
|
|
||||||
|
theConf->SetValue("Options/BoxedExplorerInfo", true);
|
||||||
|
theConf->SetValue("Options/ExplorerInfo", true);
|
||||||
|
|
||||||
theConf->SetValue("Options/OpenUrlsSandboxed", 2);
|
theConf->SetValue("Options/OpenUrlsSandboxed", 2);
|
||||||
|
|
||||||
|
theConf->SetValue("Options/AutoCleanupTemplates", -1);
|
||||||
}
|
}
|
||||||
|
|
||||||
theAPI->GetUserSettings()->UpdateTextList("SbieCtrl_HideMessage", QStringList(), true);
|
theAPI->GetUserSettings()->UpdateTextList("SbieCtrl_HideMessage", QStringList(), true);
|
||||||
|
@ -1410,7 +1514,8 @@ QString CSandMan::FormatError(const SB_STATUS& Error)
|
||||||
case SB_SnapDelRegFail: Message = tr("Failed to remove old RegHive"); break;
|
case SB_SnapDelRegFail: Message = tr("Failed to remove old RegHive"); break;
|
||||||
case SB_NotAuthorized: Message = tr("You are not authorized to update configuration in section '%1'"); break;
|
case SB_NotAuthorized: Message = tr("You are not authorized to update configuration in section '%1'"); break;
|
||||||
case SB_ConfigFailed: Message = tr("Failed to set configuration setting %1 in section %2: %3"); break;
|
case SB_ConfigFailed: Message = tr("Failed to set configuration setting %1 in section %2: %3"); break;
|
||||||
|
case SB_SnapIsEmpty: Message = tr("Can not create snapshot of an empty sandbox"); break;
|
||||||
|
case SB_NameExists: Message = tr("A sandbox with that name already exists"); break;
|
||||||
default: return tr("Unknown Error Status: %1").arg(Error.GetStatus());
|
default: return tr("Unknown Error Status: %1").arg(Error.GetStatus());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1796,6 +1901,10 @@ void CSandMan::SetDarkTheme(bool bDark)
|
||||||
palette.setColor(QPalette::Link, QColor(218, 130, 42));
|
palette.setColor(QPalette::Link, QColor(218, 130, 42));
|
||||||
palette.setColor(QPalette::Highlight, QColor(42, 130, 218));
|
palette.setColor(QPalette::Highlight, QColor(42, 130, 218));
|
||||||
palette.setColor(QPalette::HighlightedText, Qt::black);
|
palette.setColor(QPalette::HighlightedText, Qt::black);
|
||||||
|
palette.setColor(QPalette::Disabled, QPalette::WindowText, Qt::darkGray);
|
||||||
|
palette.setColor(QPalette::Disabled, QPalette::Text, Qt::darkGray);
|
||||||
|
palette.setColor(QPalette::Disabled, QPalette::Light, Qt::black);
|
||||||
|
palette.setColor(QPalette::Disabled, QPalette::ButtonText, Qt::darkGray);
|
||||||
QApplication::setPalette(palette);
|
QApplication::setPalette(palette);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
|
|
@ -14,8 +14,8 @@
|
||||||
|
|
||||||
#define VERSION_MJR 0
|
#define VERSION_MJR 0
|
||||||
#define VERSION_MIN 5
|
#define VERSION_MIN 5
|
||||||
#define VERSION_REV 4
|
#define VERSION_REV 5
|
||||||
#define VERSION_UPD 2
|
#define VERSION_UPD 0
|
||||||
|
|
||||||
|
|
||||||
//#include "../QSbieAPI/SbieAPI.h"
|
//#include "../QSbieAPI/SbieAPI.h"
|
||||||
|
@ -57,6 +57,10 @@ protected:
|
||||||
static void RecoverFilesAsync(const CSbieProgressPtr& pProgress, const QList<QPair<QString, QString>>& FileList, int Action = 0);
|
static void RecoverFilesAsync(const CSbieProgressPtr& pProgress, const QList<QPair<QString, QString>>& FileList, int Action = 0);
|
||||||
|
|
||||||
void closeEvent(QCloseEvent* e);
|
void closeEvent(QCloseEvent* e);
|
||||||
|
|
||||||
|
void dragEnterEvent(QDragEnterEvent* e);
|
||||||
|
void dropEvent(QDropEvent* e);
|
||||||
|
|
||||||
void timerEvent(QTimerEvent* pEvent);
|
void timerEvent(QTimerEvent* pEvent);
|
||||||
int m_uTimerID;
|
int m_uTimerID;
|
||||||
bool m_bConnectPending;
|
bool m_bConnectPending;
|
||||||
|
@ -71,6 +75,8 @@ protected:
|
||||||
CNetworkAccessManager* m_RequestManager;
|
CNetworkAccessManager* m_RequestManager;
|
||||||
CSbieProgressPtr m_pUpdateProgress;
|
CSbieProgressPtr m_pUpdateProgress;
|
||||||
|
|
||||||
|
QStringList m_MissingTemplates;
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
void OnMessage(const QString&);
|
void OnMessage(const QString&);
|
||||||
|
|
||||||
|
@ -114,6 +120,7 @@ private slots:
|
||||||
void OnMaintenance();
|
void OnMaintenance();
|
||||||
|
|
||||||
void OnViewMode(QAction* action);
|
void OnViewMode(QAction* action);
|
||||||
|
void OnAlwaysTop();
|
||||||
void OnCleanUp();
|
void OnCleanUp();
|
||||||
void OnSetKeep();
|
void OnSetKeep();
|
||||||
|
|
||||||
|
@ -187,6 +194,7 @@ private:
|
||||||
|
|
||||||
QMenu* m_pMenuView;
|
QMenu* m_pMenuView;
|
||||||
QActionGroup* m_pViewMode;
|
QActionGroup* m_pViewMode;
|
||||||
|
QAction* m_pWndTopMost;
|
||||||
int m_iMenuViewPos;
|
int m_iMenuViewPos;
|
||||||
QMenu* m_pCleanUpMenu;
|
QMenu* m_pCleanUpMenu;
|
||||||
QAction* m_pCleanUpProcesses;
|
QAction* m_pCleanUpProcesses;
|
||||||
|
|
|
@ -9,6 +9,8 @@
|
||||||
#include "../Windows/OptionsWindow.h"
|
#include "../Windows/OptionsWindow.h"
|
||||||
#include "../Windows/SnapshotsWindow.h"
|
#include "../Windows/SnapshotsWindow.h"
|
||||||
#include <QFileIconProvider>
|
#include <QFileIconProvider>
|
||||||
|
#include "../../MiscHelpers/Common/CheckableMessageBox.h"
|
||||||
|
#include "../Windows/RecoveryWindow.h"
|
||||||
|
|
||||||
#include "qt_windows.h"
|
#include "qt_windows.h"
|
||||||
#include "qwindowdefs_win.h"
|
#include "qwindowdefs_win.h"
|
||||||
|
@ -32,6 +34,7 @@ CSbieView::CSbieView(QWidget* parent) : CPanelView(parent)
|
||||||
|
|
||||||
// SbieTree
|
// SbieTree
|
||||||
m_pSbieTree = new QTreeViewEx();
|
m_pSbieTree = new QTreeViewEx();
|
||||||
|
m_pSbieTree->setExpandsOnDoubleClick(false);
|
||||||
//m_pSbieTree->setItemDelegate(theGUI->GetItemDelegate());
|
//m_pSbieTree->setItemDelegate(theGUI->GetItemDelegate());
|
||||||
|
|
||||||
m_pSbieTree->setModel(m_pSortProxy);
|
m_pSbieTree->setModel(m_pSortProxy);
|
||||||
|
@ -122,7 +125,13 @@ CSbieView::CSbieView(QWidget* parent) : CPanelView(parent)
|
||||||
|
|
||||||
QByteArray Columns = theConf->GetBlob("MainWindow/BoxTree_Columns");
|
QByteArray Columns = theConf->GetBlob("MainWindow/BoxTree_Columns");
|
||||||
if (Columns.isEmpty())
|
if (Columns.isEmpty())
|
||||||
|
{
|
||||||
m_pSbieTree->OnResetColumns();
|
m_pSbieTree->OnResetColumns();
|
||||||
|
m_pSbieTree->setColumnWidth(0, 300);
|
||||||
|
m_pSbieTree->setColumnWidth(1, 70);
|
||||||
|
m_pSbieTree->setColumnWidth(2, 70);
|
||||||
|
m_pSbieTree->setColumnWidth(3, 70);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
m_pSbieTree->restoreState(Columns);
|
m_pSbieTree->restoreState(Columns);
|
||||||
|
|
||||||
|
@ -380,7 +389,7 @@ void CSbieView::OnGroupAction()
|
||||||
}
|
}
|
||||||
else if (Action == m_pDelGroupe)
|
else if (Action == m_pDelGroupe)
|
||||||
{
|
{
|
||||||
if (QMessageBox("Sandboxie-Plus", tr("Do you really want to remove the selected group(s)?"), QMessageBox::Warning, QMessageBox::Yes, QMessageBox::No | QMessageBox::Default | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
if (QMessageBox("Sandboxie-Plus", tr("Do you really want to remove the selected group(s)?"), QMessageBox::Question, QMessageBox::Yes, QMessageBox::No | QMessageBox::Default | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
foreach(const QModelIndex& Index, m_pSbieTree->selectedRows())
|
foreach(const QModelIndex& Index, m_pSbieTree->selectedRows())
|
||||||
|
@ -459,7 +468,20 @@ void CSbieView::OnSandBoxAction()
|
||||||
else if (Action == m_pMenuRunMailer)
|
else if (Action == m_pMenuRunMailer)
|
||||||
Results.append(SandBoxes.first()->RunStart("mail_agent"));
|
Results.append(SandBoxes.first()->RunStart("mail_agent"));
|
||||||
else if (Action == m_pMenuRunExplorer)
|
else if (Action == m_pMenuRunExplorer)
|
||||||
|
{
|
||||||
|
if (theConf->GetBool("Options/AdvancedView", true) == false && theConf->GetBool("Options/BoxedExplorerInfo", true))
|
||||||
|
{
|
||||||
|
bool State = false;
|
||||||
|
CCheckableMessageBox::question(this, "Sandboxie-Plus",
|
||||||
|
theAPI->GetSbieMsgStr(0x00000DCDL, theGUI->m_LanguageId) // MSG_3533
|
||||||
|
, tr("Don't show this message again."), &State, QDialogButtonBox::Ok, QDialogButtonBox::Ok, QMessageBox::Information);
|
||||||
|
|
||||||
|
if (State)
|
||||||
|
theConf->SetValue("Options/BoxedExplorerInfo", false);
|
||||||
|
}
|
||||||
|
|
||||||
Results.append(SandBoxes.first()->RunStart("explorer.exe /e,::{20D04FE0-3AEA-1069-A2D8-08002B30309D}"));
|
Results.append(SandBoxes.first()->RunStart("explorer.exe /e,::{20D04FE0-3AEA-1069-A2D8-08002B30309D}"));
|
||||||
|
}
|
||||||
else if (Action == m_pMenuRunCmd)
|
else if (Action == m_pMenuRunCmd)
|
||||||
Results.append(SandBoxes.first()->RunStart("cmd.exe"));
|
Results.append(SandBoxes.first()->RunStart("cmd.exe"));
|
||||||
else if (Action == m_pMenuPresetsLogApi)
|
else if (Action == m_pMenuPresetsLogApi)
|
||||||
|
@ -472,13 +494,22 @@ void CSbieView::OnSandBoxAction()
|
||||||
SandBoxes.first().objectCast<CSandBoxPlus>()->SetDropRights(m_pMenuPresetsNoAdmin->isChecked());
|
SandBoxes.first().objectCast<CSandBoxPlus>()->SetDropRights(m_pMenuPresetsNoAdmin->isChecked());
|
||||||
else if (Action == m_pMenuOptions)
|
else if (Action == m_pMenuOptions)
|
||||||
{
|
{
|
||||||
COptionsWindow* pOptionsWindow = new COptionsWindow(SandBoxes.first(), SandBoxes.first()->GetName(), this);
|
OnDoubleClicked(m_pSbieTree->selectedRows().first());
|
||||||
pOptionsWindow->show();
|
|
||||||
}
|
}
|
||||||
else if (Action == m_pMenuExplore)
|
else if (Action == m_pMenuExplore)
|
||||||
{
|
{
|
||||||
|
if (theConf->GetBool("Options/AdvancedView", true) == false && theConf->GetBool("Options/ExplorerInfo", true))
|
||||||
|
{
|
||||||
|
bool State = false;
|
||||||
|
CCheckableMessageBox::question(this, "Sandboxie-Plus",
|
||||||
|
theAPI->GetSbieMsgStr(0x00000DCEL, theGUI->m_LanguageId) // MSG_3534
|
||||||
|
, tr("Don't show this message again."), &State, QDialogButtonBox::Ok, QDialogButtonBox::Ok, QMessageBox::Information);
|
||||||
|
|
||||||
|
if (State)
|
||||||
|
theConf->SetValue("Options/ExplorerInfo", false);
|
||||||
|
}
|
||||||
|
|
||||||
::ShellExecute(NULL, NULL, SandBoxes.first()->GetFileRoot().toStdWString().c_str(), NULL, NULL, SW_SHOWNORMAL);
|
::ShellExecute(NULL, NULL, SandBoxes.first()->GetFileRoot().toStdWString().c_str(), NULL, NULL, SW_SHOWNORMAL);
|
||||||
// if (ret <= 32) error
|
|
||||||
}
|
}
|
||||||
else if (Action == m_pMenuSnapshots)
|
else if (Action == m_pMenuSnapshots)
|
||||||
{
|
{
|
||||||
|
@ -507,7 +538,24 @@ void CSbieView::OnSandBoxAction()
|
||||||
}
|
}
|
||||||
else if (Action == m_pMenuCleanUp)
|
else if (Action == m_pMenuCleanUp)
|
||||||
{
|
{
|
||||||
if (QMessageBox("Sandboxie-Plus", tr("Do you really want to delete the content of the selected sandbox(es)?"), QMessageBox::Warning, QMessageBox::Yes, QMessageBox::No | QMessageBox::Default | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
if (SandBoxes.count() == 1)
|
||||||
|
{
|
||||||
|
if (SandBoxes.first()->IsEmpty()) {
|
||||||
|
QMessageBox("Sandboxie-Plus", tr("This Sandbox is already empty."), QMessageBox::Information, QMessageBox::Ok, QMessageBox::NoButton, QMessageBox::NoButton).exec();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (theConf->GetBool("Options/ShowRecovery", false))
|
||||||
|
{
|
||||||
|
CRecoveryWindow* pRecoveryWindow = new CRecoveryWindow(SandBoxes.first(), this);
|
||||||
|
pRecoveryWindow->FindFiles();
|
||||||
|
if (pRecoveryWindow->exec() != 1)
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
else if(QMessageBox("Sandboxie-Plus", tr("Do you want to delete the content of the selected sandbox?"), QMessageBox::Question, QMessageBox::Yes, QMessageBox::No | QMessageBox::Default | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
else if (QMessageBox("Sandboxie-Plus", tr("Do you really want to delete the content of multiple sandboxes?"), QMessageBox::Warning, QMessageBox::Yes, QMessageBox::No | QMessageBox::Default | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
foreach(const CSandBoxPtr & pBox, SandBoxes)
|
foreach(const CSandBoxPtr & pBox, SandBoxes)
|
||||||
|
@ -638,7 +686,7 @@ void CSbieView::OnProcessAction()
|
||||||
{
|
{
|
||||||
if (!pProcess.objectCast<CSbieProcess>()->GetBox()->IsINetBlocked())
|
if (!pProcess.objectCast<CSbieProcess>()->GetBox()->IsINetBlocked())
|
||||||
{
|
{
|
||||||
if (QMessageBox("Sandboxie-Plus", tr("This box does not have Internet restrictions in place, do you want to enable them?"), QMessageBox::Warning, QMessageBox::Yes, QMessageBox::No | QMessageBox::Default | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
if (QMessageBox("Sandboxie-Plus", tr("This box does not have Internet restrictions in place, do you want to enable them?"), QMessageBox::Question, QMessageBox::Yes, QMessageBox::No | QMessageBox::Default | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
||||||
return;
|
return;
|
||||||
pProcess.objectCast<CSbieProcess>()->GetBox()->SetINetBlock(true);
|
pProcess.objectCast<CSbieProcess>()->GetBox()->SetINetBlock(true);
|
||||||
}
|
}
|
||||||
|
@ -666,9 +714,17 @@ void CSbieView::OnDoubleClicked(const QModelIndex& index)
|
||||||
if (pBox.isNull())
|
if (pBox.isNull())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
static QMap<void*, COptionsWindow*> OptionsWindows;
|
||||||
|
if (!OptionsWindows.contains(pBox.data()))
|
||||||
|
{
|
||||||
COptionsWindow* pOptionsWindow = new COptionsWindow(pBox, pBox->GetName(), this);
|
COptionsWindow* pOptionsWindow = new COptionsWindow(pBox, pBox->GetName(), this);
|
||||||
|
OptionsWindows.insert(pBox.data(), pOptionsWindow);
|
||||||
|
connect(pOptionsWindow, &COptionsWindow::Closed, [this, pBox]() {
|
||||||
|
OptionsWindows.remove(pBox.data());
|
||||||
|
});
|
||||||
pOptionsWindow->show();
|
pOptionsWindow->show();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void CSbieView::ProcessSelection(const QItemSelection& selected, const QItemSelection& deselected)
|
void CSbieView::ProcessSelection(const QItemSelection& selected, const QItemSelection& deselected)
|
||||||
{
|
{
|
||||||
|
|
|
@ -42,7 +42,7 @@ public:
|
||||||
|
|
||||||
|
|
||||||
COptionsWindow::COptionsWindow(const QSharedPointer<CSbieIni>& pBox, const QString& Name, QWidget *parent)
|
COptionsWindow::COptionsWindow(const QSharedPointer<CSbieIni>& pBox, const QString& Name, QWidget *parent)
|
||||||
: QMainWindow(parent)
|
: QDialog(parent)
|
||||||
{
|
{
|
||||||
m_pBox = pBox;
|
m_pBox = pBox;
|
||||||
|
|
||||||
|
@ -53,9 +53,7 @@ COptionsWindow::COptionsWindow(const QSharedPointer<CSbieIni>& pBox, const QStri
|
||||||
if (!pBoxPlus.isNull())
|
if (!pBoxPlus.isNull())
|
||||||
m_Programs = pBoxPlus->GetRecentPrograms();
|
m_Programs = pBoxPlus->GetRecentPrograms();
|
||||||
|
|
||||||
QWidget* centralWidget = new QWidget();
|
ui.setupUi(this);
|
||||||
ui.setupUi(centralWidget);
|
|
||||||
this->setCentralWidget(centralWidget);
|
|
||||||
this->setWindowTitle(tr("Sandboxie Plus - '%1' Options").arg(Name));
|
this->setWindowTitle(tr("Sandboxie Plus - '%1' Options").arg(Name));
|
||||||
|
|
||||||
ui.tabs->setTabPosition(QTabWidget::West);
|
ui.tabs->setTabPosition(QTabWidget::West);
|
||||||
|
@ -294,9 +292,9 @@ COptionsWindow::COptionsWindow(const QSharedPointer<CSbieIni>& pBox, const QStri
|
||||||
connect(ui.btnCancelEdit, SIGNAL(pressed()), this, SLOT(OnCancelEdit()));
|
connect(ui.btnCancelEdit, SIGNAL(pressed()), this, SLOT(OnCancelEdit()));
|
||||||
//
|
//
|
||||||
|
|
||||||
connect(ui.buttonBox->button(QDialogButtonBox::Ok), SIGNAL(pressed()), this, SLOT(accept()));
|
connect(ui.buttonBox->button(QDialogButtonBox::Ok), SIGNAL(pressed()), this, SLOT(ok()));
|
||||||
connect(ui.buttonBox->button(QDialogButtonBox::Apply), SIGNAL(pressed()), this, SLOT(apply()));
|
connect(ui.buttonBox->button(QDialogButtonBox::Apply), SIGNAL(pressed()), this, SLOT(apply()));
|
||||||
connect(ui.buttonBox, SIGNAL(rejected()), this, SLOT(reject()));
|
connect(ui.buttonBox, SIGNAL(rejected()), this, SLOT(close()));
|
||||||
|
|
||||||
if (ReadOnly) {
|
if (ReadOnly) {
|
||||||
ui.btnEditIni->setEnabled(false);
|
ui.btnEditIni->setEnabled(false);
|
||||||
|
@ -351,6 +349,7 @@ COptionsWindow::~COptionsWindow()
|
||||||
|
|
||||||
void COptionsWindow::closeEvent(QCloseEvent *e)
|
void COptionsWindow::closeEvent(QCloseEvent *e)
|
||||||
{
|
{
|
||||||
|
emit Closed();
|
||||||
this->deleteLater();
|
this->deleteLater();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -358,9 +357,11 @@ bool COptionsWindow::eventFilter(QObject *source, QEvent *event)
|
||||||
{
|
{
|
||||||
if (event->type() == QEvent::KeyPress && ((QKeyEvent*)event)->key() == Qt::Key_Escape && ((QKeyEvent*)event)->modifiers() == Qt::NoModifier)
|
if (event->type() == QEvent::KeyPress && ((QKeyEvent*)event)->key() == Qt::Key_Escape && ((QKeyEvent*)event)->modifiers() == Qt::NoModifier)
|
||||||
CloseAccessEdit(false);
|
CloseAccessEdit(false);
|
||||||
if (source == ui.treeAccess->viewport() && event->type() == QEvent::MouseButtonPress)
|
else if (source == ui.treeAccess->viewport() && event->type() == QEvent::MouseButtonPress)
|
||||||
CloseAccessEdit();
|
CloseAccessEdit();
|
||||||
return QMainWindow::eventFilter(source, event);
|
else
|
||||||
|
return QDialog::eventFilter(source, event);
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
//void COptionsWindow::OnWithTemplates()
|
//void COptionsWindow::OnWithTemplates()
|
||||||
|
@ -682,6 +683,11 @@ void COptionsWindow::SaveConfig()
|
||||||
|
|
||||||
void COptionsWindow::apply()
|
void COptionsWindow::apply()
|
||||||
{
|
{
|
||||||
|
if (m_pBox->GetText("Enabled").isEmpty()) {
|
||||||
|
QMessageBox::critical(this, "Sandboxie-Plus", tr("This sandbox has been deleted hence configuration can not be saved."));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (!ui.btnEditIni->isEnabled())
|
if (!ui.btnEditIni->isEnabled())
|
||||||
SaveIniSection();
|
SaveIniSection();
|
||||||
else
|
else
|
||||||
|
@ -692,7 +698,7 @@ void COptionsWindow::apply()
|
||||||
emit OptionsChanged();
|
emit OptionsChanged();
|
||||||
}
|
}
|
||||||
|
|
||||||
void COptionsWindow::accept()
|
void COptionsWindow::ok()
|
||||||
{
|
{
|
||||||
apply();
|
apply();
|
||||||
|
|
||||||
|
@ -701,6 +707,23 @@ void COptionsWindow::accept()
|
||||||
|
|
||||||
void COptionsWindow::reject()
|
void COptionsWindow::reject()
|
||||||
{
|
{
|
||||||
|
if (m_GeneralChanged
|
||||||
|
|| m_GroupsChanged
|
||||||
|
|| m_ForcedChanged
|
||||||
|
|| m_StopChanged
|
||||||
|
|| m_StartChanged
|
||||||
|
// || m_RestrictionChanged
|
||||||
|
|| m_INetBlockChanged
|
||||||
|
|| m_AccessChanged
|
||||||
|
|| m_TemplatesChanged
|
||||||
|
|| m_RecoveryChanged
|
||||||
|
|| m_AdvancedChanged)
|
||||||
|
{
|
||||||
|
if (QMessageBox("Sandboxie-Plus", tr("Some changes haven't been saved yet, do you really want to close this options window?")
|
||||||
|
, QMessageBox::Warning, QMessageBox::Yes | QMessageBox::Default, QMessageBox::No | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
this->close();
|
this->close();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -741,7 +764,7 @@ void COptionsWindow::OnAddAutoCmd()
|
||||||
|
|
||||||
void COptionsWindow::OnAddAutoExe()
|
void COptionsWindow::OnAddAutoExe()
|
||||||
{
|
{
|
||||||
QString Value = QFileDialog::getOpenFileName(this, tr("Select Program"), "", tr("Executables (*.exe|*.cmd)")).replace("/", "\\");;
|
QString Value = QFileDialog::getOpenFileName(this, tr("Select Program"), "", tr("Executables (*.exe *.cmd);;All files (*.*)")).replace("/", "\\");;
|
||||||
if (Value.isEmpty())
|
if (Value.isEmpty())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
|
|
@ -4,7 +4,7 @@
|
||||||
#include "ui_OptionsWindow.h"
|
#include "ui_OptionsWindow.h"
|
||||||
#include "SbiePlusAPI.h"
|
#include "SbiePlusAPI.h"
|
||||||
|
|
||||||
class COptionsWindow : public QMainWindow
|
class COptionsWindow : public QDialog
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
|
@ -12,13 +12,16 @@ public:
|
||||||
COptionsWindow(const QSharedPointer<CSbieIni>& pBox, const QString& Name, QWidget *parent = Q_NULLPTR);
|
COptionsWindow(const QSharedPointer<CSbieIni>& pBox, const QString& Name, QWidget *parent = Q_NULLPTR);
|
||||||
~COptionsWindow();
|
~COptionsWindow();
|
||||||
|
|
||||||
|
virtual void accept() {}
|
||||||
|
virtual void reject();
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
void OptionsChanged();
|
void OptionsChanged();
|
||||||
|
void Closed();
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
|
void ok();
|
||||||
void apply();
|
void apply();
|
||||||
void accept();
|
|
||||||
void reject();
|
|
||||||
|
|
||||||
private slots:
|
private slots:
|
||||||
|
|
||||||
|
|
|
@ -11,6 +11,15 @@ bool CPopUpWindow__DarkMode = false;
|
||||||
|
|
||||||
CPopUpWindow::CPopUpWindow(QWidget* parent) : QMainWindow(parent)
|
CPopUpWindow::CPopUpWindow(QWidget* parent) : QMainWindow(parent)
|
||||||
{
|
{
|
||||||
|
Qt::WindowFlags flags = windowFlags();
|
||||||
|
flags |= Qt::CustomizeWindowHint;
|
||||||
|
//flags &= ~Qt::WindowContextHelpButtonHint;
|
||||||
|
//flags &= ~Qt::WindowSystemMenuHint;
|
||||||
|
flags &= ~Qt::WindowMinMaxButtonsHint;
|
||||||
|
//flags &= ~Qt::WindowMinimizeButtonHint;
|
||||||
|
//flags &= ~Qt::WindowCloseButtonHint;
|
||||||
|
setWindowFlags(flags);
|
||||||
|
|
||||||
this->setWindowTitle(tr("Sandboxie-Plus Notifications"));
|
this->setWindowTitle(tr("Sandboxie-Plus Notifications"));
|
||||||
|
|
||||||
QWidget* centralWidget = new QWidget();
|
QWidget* centralWidget = new QWidget();
|
||||||
|
@ -232,7 +241,10 @@ void CPopUpWindow::AddUserPrompt(quint32 RequestId, const QVariantMap& Data, qui
|
||||||
CPopUpPrompt* pEntry = new CPopUpPrompt(Message, RequestId, Result, pProcess, this);
|
CPopUpPrompt* pEntry = new CPopUpPrompt(Message, RequestId, Result, pProcess, this);
|
||||||
switch (pEntry->m_Result["id"].toInt())
|
switch (pEntry->m_Result["id"].toInt())
|
||||||
{
|
{
|
||||||
case CSbieAPI::eInetBlockade: pEntry->m_pRemember->setChecked(true); break;
|
case CSbieAPI::eInetBlockade:
|
||||||
|
pEntry->AddAddToList();
|
||||||
|
pEntry->m_pRemember->setChecked(true);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
connect(pEntry, SIGNAL(PromptResult(int)), this, SLOT(OnPromptResult(int)));
|
connect(pEntry, SIGNAL(PromptResult(int)), this, SLOT(OnPromptResult(int)));
|
||||||
AddEntry(pEntry);
|
AddEntry(pEntry);
|
||||||
|
@ -254,8 +266,14 @@ void CPopUpWindow::SendPromptResult(CPopUpPrompt* pEntry, int retval)
|
||||||
{
|
{
|
||||||
switch (pEntry->m_Result["id"].toInt())
|
switch (pEntry->m_Result["id"].toInt())
|
||||||
{
|
{
|
||||||
case CSbieAPI::ePrintSpooler: theAPI->SetProcessExemption(pEntry->m_pProcess->GetProcessId(), 'splr', true); break;
|
case CSbieAPI::ePrintSpooler:
|
||||||
case CSbieAPI::eInetBlockade: theAPI->SetProcessExemption(pEntry->m_pProcess->GetProcessId(), 'inet', true); break;
|
theAPI->SetProcessExemption(pEntry->m_pProcess->GetProcessId(), 'splr', true);
|
||||||
|
break;
|
||||||
|
case CSbieAPI::eInetBlockade:
|
||||||
|
if (pEntry->m_bAddToList)
|
||||||
|
pEntry->m_pProcess.objectCast<CSbieProcess>()->SetInternetAccess(true);
|
||||||
|
theAPI->SetProcessExemption(pEntry->m_pProcess->GetProcessId(), 'inet', true);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -89,6 +89,7 @@ public:
|
||||||
m_RequestId = RequestId;
|
m_RequestId = RequestId;
|
||||||
m_Result = Result;
|
m_Result = Result;
|
||||||
m_pProcess = pProcess;
|
m_pProcess = pProcess;
|
||||||
|
m_bAddToList = false;
|
||||||
|
|
||||||
m_pLabel = new QLabel(Message);
|
m_pLabel = new QLabel(Message);
|
||||||
m_pLabel->setToolTip(Message);
|
m_pLabel->setToolTip(Message);
|
||||||
|
@ -132,10 +133,19 @@ public:
|
||||||
killTimer(m_uTimerID);
|
killTimer(m_uTimerID);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void AddAddToList()
|
||||||
|
{
|
||||||
|
m_pYes->setPopupMode(QToolButton::MenuButtonPopup);
|
||||||
|
QMenu* pMenu = new QMenu();
|
||||||
|
pMenu->addAction(tr("Yes and add to allowed programs"), this, SLOT(OnAcceptedAlways()));
|
||||||
|
m_pYes->setMenu(pMenu);
|
||||||
|
}
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
void PromptResult(int retval);
|
void PromptResult(int retval);
|
||||||
|
|
||||||
private slots:
|
private slots:
|
||||||
|
void OnAcceptedAlways() { m_bAddToList = true; emit PromptResult(1); }
|
||||||
void OnAccepted() { emit PromptResult(1); }
|
void OnAccepted() { emit PromptResult(1); }
|
||||||
void OnRejected() { emit PromptResult(0); }
|
void OnRejected() { emit PromptResult(0); }
|
||||||
void OnTerminate() { emit PromptResult(-1); }
|
void OnTerminate() { emit PromptResult(-1); }
|
||||||
|
@ -190,6 +200,7 @@ protected:
|
||||||
quint32 m_RequestId;
|
quint32 m_RequestId;
|
||||||
QVariantMap m_Result;
|
QVariantMap m_Result;
|
||||||
CBoxedProcessPtr m_pProcess;
|
CBoxedProcessPtr m_pProcess;
|
||||||
|
bool m_bAddToList;
|
||||||
|
|
||||||
QLabel* m_pLabel;
|
QLabel* m_pLabel;
|
||||||
QCheckBox* m_pRemember;
|
QCheckBox* m_pRemember;
|
||||||
|
|
|
@ -15,10 +15,13 @@ CRecoveryWindow::CRecoveryWindow(const CSandBoxPtr& pBox, QWidget *parent)
|
||||||
|
|
||||||
m_pBox = pBox;
|
m_pBox = pBox;
|
||||||
|
|
||||||
|
m_pCounter = NULL;
|
||||||
|
|
||||||
#ifdef WIN32
|
#ifdef WIN32
|
||||||
QStyle* pStyle = QStyleFactory::create("windows");
|
QStyle* pStyle = QStyleFactory::create("windows");
|
||||||
ui.treeFiles->setStyle(pStyle);
|
ui.treeFiles->setStyle(pStyle);
|
||||||
#endif
|
#endif
|
||||||
|
ui.treeFiles->setExpandsOnDoubleClick(false);
|
||||||
|
|
||||||
ui.btnDeleteAll->setVisible(false);
|
ui.btnDeleteAll->setVisible(false);
|
||||||
|
|
||||||
|
@ -44,6 +47,7 @@ CRecoveryWindow::CRecoveryWindow(const CSandBoxPtr& pBox, QWidget *parent)
|
||||||
//connect(ui.treeFiles, SIGNAL(doubleClicked(const QModelIndex&)), this, SLOT(OnSelectSnapshot()));
|
//connect(ui.treeFiles, SIGNAL(doubleClicked(const QModelIndex&)), this, SLOT(OnSelectSnapshot()));
|
||||||
|
|
||||||
connect(ui.btnAddFolder, SIGNAL(pressed()), this, SLOT(OnAddFolder()));
|
connect(ui.btnAddFolder, SIGNAL(pressed()), this, SLOT(OnAddFolder()));
|
||||||
|
connect(ui.chkShowAll, SIGNAL(clicked(bool)), this, SLOT(FindFiles()));
|
||||||
connect(ui.btnRefresh, SIGNAL(pressed()), this, SLOT(FindFiles()));
|
connect(ui.btnRefresh, SIGNAL(pressed()), this, SLOT(FindFiles()));
|
||||||
connect(ui.btnRecover, SIGNAL(pressed()), this, SLOT(OnRecover()));
|
connect(ui.btnRecover, SIGNAL(pressed()), this, SLOT(OnRecover()));
|
||||||
connect(ui.btnRecoverTo, SIGNAL(pressed()), this, SLOT(OnRecoverTo()));
|
connect(ui.btnRecoverTo, SIGNAL(pressed()), this, SLOT(OnRecoverTo()));
|
||||||
|
@ -63,7 +67,7 @@ CRecoveryWindow::CRecoveryWindow(const CSandBoxPtr& pBox, QWidget *parent)
|
||||||
foreach(const QString& NtFolder, m_pBox->GetTextList("RecoverFolder", true, true))
|
foreach(const QString& NtFolder, m_pBox->GetTextList("RecoverFolder", true, true))
|
||||||
{
|
{
|
||||||
QString Folder = theAPI->Nt2DosPath(NtFolder);
|
QString Folder = theAPI->Nt2DosPath(NtFolder);
|
||||||
m_RecoveryFolders.insert(theAPI->GetBoxedPath(m_pBox, Folder), Folder);
|
m_RecoveryFolders.append(Folder);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -94,10 +98,10 @@ void CRecoveryWindow::OnAddFolder()
|
||||||
if (m_RecoveryFolders.contains(Folder))
|
if (m_RecoveryFolders.contains(Folder))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
m_RecoveryFolders.insert(theAPI->GetBoxedPath(m_pBox, Folder), Folder);
|
m_RecoveryFolders.append(Folder);
|
||||||
m_pBox->AppendText("RecoverFolder", Folder);
|
m_pBox->AppendText("RecoverFolder", Folder);
|
||||||
|
|
||||||
FindFiles(theAPI->GetBoxedPath(m_pBox, Folder));
|
FindFiles(Folder);
|
||||||
|
|
||||||
m_pFileModel->Sync(m_FileMap);
|
m_pFileModel->Sync(m_FileMap);
|
||||||
ui.treeFiles->expandAll();
|
ui.treeFiles->expandAll();
|
||||||
|
@ -111,10 +115,30 @@ void CRecoveryWindow::OnDeleteAll()
|
||||||
|
|
||||||
int CRecoveryWindow::FindFiles()
|
int CRecoveryWindow::FindFiles()
|
||||||
{
|
{
|
||||||
|
if (m_pCounter == NULL) {
|
||||||
|
m_pCounter = new CRecoveryCounter(m_pBox->GetFileRoot(), this);
|
||||||
|
connect(m_pCounter, SIGNAL(Count(quint32, quint32, quint64)), this, SLOT(OnCount(quint32, quint32, quint64)));
|
||||||
|
}
|
||||||
|
|
||||||
m_FileMap.clear();
|
m_FileMap.clear();
|
||||||
int Count = 0;
|
int Count = 0;
|
||||||
foreach(const QString& Folder, m_RecoveryFolders.keys())
|
|
||||||
|
if (ui.chkShowAll->isChecked())
|
||||||
|
{
|
||||||
|
for(char drive = 'A'; drive <= 'Z'; drive++)
|
||||||
|
Count += FindBoxFiles("\\drive\\" + QString(drive));
|
||||||
|
if (m_pBox->GetBool("SeparateUserFolders", true)) {
|
||||||
|
Count += FindBoxFiles("\\user\\current");
|
||||||
|
Count += FindBoxFiles("\\user\\all");
|
||||||
|
Count += FindBoxFiles("\\user\\public");
|
||||||
|
}
|
||||||
|
Count += FindBoxFiles("\\share");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
foreach(const QString & Folder, m_RecoveryFolders)
|
||||||
Count += FindFiles(Folder);
|
Count += FindFiles(Folder);
|
||||||
|
}
|
||||||
|
|
||||||
m_pFileModel->Sync(m_FileMap);
|
m_pFileModel->Sync(m_FileMap);
|
||||||
ui.treeFiles->expandAll();
|
ui.treeFiles->expandAll();
|
||||||
|
@ -122,16 +146,24 @@ int CRecoveryWindow::FindFiles()
|
||||||
}
|
}
|
||||||
|
|
||||||
int CRecoveryWindow::FindFiles(const QString& Folder)
|
int CRecoveryWindow::FindFiles(const QString& Folder)
|
||||||
|
{
|
||||||
|
return FindFiles(Folder, theAPI->GetBoxedPath(m_pBox, Folder), Folder);
|
||||||
|
}
|
||||||
|
|
||||||
|
int CRecoveryWindow::FindBoxFiles(const QString& Folder)
|
||||||
|
{
|
||||||
|
return FindFiles(Folder, m_pBox->GetFileRoot() + Folder, theAPI->GetRealPath(m_pBox, m_pBox->GetFileRoot() + Folder));
|
||||||
|
}
|
||||||
|
|
||||||
|
int CRecoveryWindow::FindFiles(const QString& RecParent, const QString& BoxedFolder, const QString& RealFolder)
|
||||||
{
|
{
|
||||||
QFileIconProvider IconProvider;
|
QFileIconProvider IconProvider;
|
||||||
|
|
||||||
int Count = 0;
|
int Count = 0;
|
||||||
quint64 TotalSize = 0;
|
quint64 TotalSize = 0;
|
||||||
|
|
||||||
QString RecParent = m_RecoveryFolders.value(Folder);
|
|
||||||
|
|
||||||
QStringList Folders;
|
QStringList Folders;
|
||||||
Folders.append(Folder);
|
Folders.append(BoxedFolder);
|
||||||
do {
|
do {
|
||||||
QDir Dir(Folders.takeFirst());
|
QDir Dir(Folders.takeFirst());
|
||||||
foreach(const QFileInfo& Info, Dir.entryInfoList(QDir::AllEntries))
|
foreach(const QFileInfo& Info, Dir.entryInfoList(QDir::AllEntries))
|
||||||
|
@ -145,7 +177,7 @@ int CRecoveryWindow::FindFiles(const QString& Folder)
|
||||||
Count++;
|
Count++;
|
||||||
TotalSize += Info.size();
|
TotalSize += Info.size();
|
||||||
|
|
||||||
QString RealPath = RecParent + Path.mid(Folder.length());
|
QString RealPath = RealFolder + Path.mid(BoxedFolder.length());
|
||||||
|
|
||||||
QVariantMap RecFile;
|
QVariantMap RecFile;
|
||||||
RecFile["ID"] = RealPath;
|
RecFile["ID"] = RealPath;
|
||||||
|
@ -181,13 +213,7 @@ int CRecoveryWindow::FindFiles(const QString& Folder)
|
||||||
|
|
||||||
void CRecoveryWindow::RecoverFiles(bool bBrowse)
|
void CRecoveryWindow::RecoverFiles(bool bBrowse)
|
||||||
{
|
{
|
||||||
QString RecoveryFolder;
|
bool HasShare = false;
|
||||||
if (bBrowse)
|
|
||||||
{
|
|
||||||
RecoveryFolder = QFileDialog::getExistingDirectory(this, tr("Select Directory")).replace("/", "\\");
|
|
||||||
if (RecoveryFolder.isEmpty())
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
QMap<QString, QString> FileMap;
|
QMap<QString, QString> FileMap;
|
||||||
foreach(const QModelIndex& Index, ui.treeFiles->selectionModel()->selectedIndexes())
|
foreach(const QModelIndex& Index, ui.treeFiles->selectionModel()->selectedIndexes())
|
||||||
|
@ -201,7 +227,11 @@ void CRecoveryWindow::RecoverFiles(bool bBrowse)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if (!File["ParentID"].isNull())
|
if (!File["ParentID"].isNull())
|
||||||
|
{
|
||||||
|
if (File["DiskPath"].toString().indexOf("\\device\\mup") == 0)
|
||||||
|
HasShare = true;
|
||||||
FileMap[File["BoxPath"].toString()] = File["DiskPath"].toString();
|
FileMap[File["BoxPath"].toString()] = File["DiskPath"].toString();
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
for (int i = 0; i < m_pFileModel->rowCount(Index); i++)
|
for (int i = 0; i < m_pFileModel->rowCount(Index); i++)
|
||||||
|
@ -213,11 +243,23 @@ void CRecoveryWindow::RecoverFiles(bool bBrowse)
|
||||||
if (File.isEmpty())
|
if (File.isEmpty())
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
if (File["DiskPath"].toString().indexOf("\\device\\mup") == 0)
|
||||||
|
HasShare = true;
|
||||||
FileMap[File["BoxPath"].toString()] = File["DiskPath"].toString();
|
FileMap[File["BoxPath"].toString()] = File["DiskPath"].toString();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QString RecoveryFolder;
|
||||||
|
if (HasShare && !bBrowse)
|
||||||
|
{
|
||||||
|
if (!bBrowse)
|
||||||
|
QMessageBox::warning(this, "Sandboxie-Plus", tr("One or more selected files are located on a network share, and must be recovered to a local drive, please select a folder to recover all selected files to."));
|
||||||
|
|
||||||
|
RecoveryFolder = QFileDialog::getExistingDirectory(this, tr("Select Directory")).replace("/", "\\");
|
||||||
|
if (RecoveryFolder.isEmpty())
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
QList<QPair<QString, QString>> FileList;
|
QList<QPair<QString, QString>> FileList;
|
||||||
for(QMap<QString, QString>::const_iterator I = FileMap.begin(); I != FileMap.end(); ++I)
|
for(QMap<QString, QString>::const_iterator I = FileMap.begin(); I != FileMap.end(); ++I)
|
||||||
|
@ -240,3 +282,46 @@ void CRecoveryWindow::RecoverFiles(bool bBrowse)
|
||||||
theGUI->AddAsyncOp(Status.GetValue());
|
theGUI->AddAsyncOp(Status.GetValue());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void CRecoveryWindow::OnCount(quint32 fileCount, quint32 folderCount, quint64 totalSize)
|
||||||
|
{
|
||||||
|
ui.lblInfo->setText(tr("There are %1 files and %2 folders in the sandbox, occupying %3 bytes of disk space.").arg(fileCount).arg(folderCount).arg(FormatSize(totalSize)));
|
||||||
|
}
|
||||||
|
|
||||||
|
void CRecoveryCounter::run()
|
||||||
|
{
|
||||||
|
quint32 fileCount = 0;
|
||||||
|
quint32 folderCount = 0;
|
||||||
|
quint64 totalSize = 0;
|
||||||
|
|
||||||
|
QStringList Folders;
|
||||||
|
Folders.append(m_BoxPath);
|
||||||
|
do {
|
||||||
|
if (!m_run) break;
|
||||||
|
|
||||||
|
QDir Dir(Folders.takeFirst());
|
||||||
|
foreach(const QFileInfo & Info, Dir.entryInfoList(QDir::AllEntries))
|
||||||
|
{
|
||||||
|
if (!m_run) break;
|
||||||
|
|
||||||
|
QString Name = Info.fileName();
|
||||||
|
if (Name == "." || Name == "..")
|
||||||
|
continue;
|
||||||
|
QString Path = Info.filePath().replace("/", "\\");
|
||||||
|
if (Info.isFile())
|
||||||
|
{
|
||||||
|
fileCount++;
|
||||||
|
totalSize += Info.size();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Folders.append(Path);
|
||||||
|
|
||||||
|
folderCount++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
emit Count(fileCount, folderCount, totalSize);
|
||||||
|
|
||||||
|
} while (!Folders.isEmpty());
|
||||||
|
}
|
|
@ -5,6 +5,31 @@
|
||||||
#include "SbiePlusAPI.h"
|
#include "SbiePlusAPI.h"
|
||||||
class CSimpleTreeModel;
|
class CSimpleTreeModel;
|
||||||
|
|
||||||
|
class CRecoveryCounter : public QThread
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
public:
|
||||||
|
CRecoveryCounter(const QString& BoxPath, QWidget* parent = Q_NULLPTR) : QThread(parent) {
|
||||||
|
m_BoxPath = BoxPath;
|
||||||
|
m_run = true;
|
||||||
|
start(QThread::LowPriority);
|
||||||
|
}
|
||||||
|
~CRecoveryCounter() {
|
||||||
|
m_run = false;
|
||||||
|
wait(2000);
|
||||||
|
terminate();
|
||||||
|
}
|
||||||
|
|
||||||
|
signals:
|
||||||
|
void Count(quint32 fileCount, quint32 folderCount, quint64 totalSize);
|
||||||
|
|
||||||
|
protected:
|
||||||
|
void run();
|
||||||
|
|
||||||
|
QString m_BoxPath;
|
||||||
|
bool m_run;
|
||||||
|
};
|
||||||
|
|
||||||
class CRecoveryWindow : public QDialog
|
class CRecoveryWindow : public QDialog
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
@ -13,6 +38,9 @@ public:
|
||||||
CRecoveryWindow(const CSandBoxPtr& pBox, QWidget *parent = Q_NULLPTR);
|
CRecoveryWindow(const CSandBoxPtr& pBox, QWidget *parent = Q_NULLPTR);
|
||||||
~CRecoveryWindow();
|
~CRecoveryWindow();
|
||||||
|
|
||||||
|
virtual void accept() {}
|
||||||
|
virtual void reject() { this->close(); }
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
int exec();
|
int exec();
|
||||||
|
|
||||||
|
@ -24,10 +52,14 @@ private slots:
|
||||||
void OnRecoverTo() { RecoverFiles(true); }
|
void OnRecoverTo() { RecoverFiles(true); }
|
||||||
void OnDeleteAll();
|
void OnDeleteAll();
|
||||||
|
|
||||||
|
void OnCount(quint32 fileCount, quint32 folderCount, quint64 totalSize);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void closeEvent(QCloseEvent *e);
|
void closeEvent(QCloseEvent *e);
|
||||||
|
|
||||||
int FindFiles(const QString& Folder);
|
int FindFiles(const QString& Folder);
|
||||||
|
int FindBoxFiles(const QString& Folder);
|
||||||
|
int FindFiles(const QString& RecParent, const QString& BoxedFolder, const QString& RealFolder);
|
||||||
|
|
||||||
void RecoverFiles(bool bBrowse);
|
void RecoverFiles(bool bBrowse);
|
||||||
|
|
||||||
|
@ -35,7 +67,9 @@ protected:
|
||||||
|
|
||||||
QMap<QVariant, QVariantMap> m_FileMap;
|
QMap<QVariant, QVariantMap> m_FileMap;
|
||||||
|
|
||||||
QMap<QString, QString> m_RecoveryFolders;
|
QStringList m_RecoveryFolders;
|
||||||
|
|
||||||
|
CRecoveryCounter* m_pCounter;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
Ui::RecoveryWindow ui;
|
Ui::RecoveryWindow ui;
|
||||||
|
|
|
@ -8,13 +8,13 @@
|
||||||
|
|
||||||
|
|
||||||
CSettingsWindow::CSettingsWindow(QWidget *parent)
|
CSettingsWindow::CSettingsWindow(QWidget *parent)
|
||||||
: QMainWindow(parent)
|
: QDialog(parent)
|
||||||
{
|
{
|
||||||
QWidget* centralWidget = new QWidget();
|
ui.setupUi(this);
|
||||||
ui.setupUi(centralWidget);
|
|
||||||
this->setCentralWidget(centralWidget);
|
|
||||||
this->setWindowTitle(tr("Sandboxie Plus - Settings"));
|
this->setWindowTitle(tr("Sandboxie Plus - Settings"));
|
||||||
|
|
||||||
|
ui.tabs->setCurrentIndex(0);
|
||||||
|
|
||||||
ui.uiLang->addItem("International English", "");
|
ui.uiLang->addItem("International English", "");
|
||||||
QDir langDir(QApplication::applicationDirPath() + "/translations/");
|
QDir langDir(QApplication::applicationDirPath() + "/translations/");
|
||||||
foreach(const QString& langFile, langDir.entryList(QStringList("sandman_*.qm"), QDir::Files))
|
foreach(const QString& langFile, langDir.entryList(QStringList("sandman_*.qm"), QDir::Files))
|
||||||
|
@ -27,6 +27,7 @@ CSettingsWindow::CSettingsWindow(QWidget *parent)
|
||||||
ui.uiLang->setCurrentIndex(ui.uiLang->findData(theConf->GetString("Options/Language")));
|
ui.uiLang->setCurrentIndex(ui.uiLang->findData(theConf->GetString("Options/Language")));
|
||||||
|
|
||||||
ui.chkAutoStart->setChecked(IsAutorunEnabled());
|
ui.chkAutoStart->setChecked(IsAutorunEnabled());
|
||||||
|
ui.chkSvcStart->setChecked(theAPI->GetUserSettings()->GetBool("SbieCtrl_EnableAutoStart", true));
|
||||||
|
|
||||||
switch (theConf->GetInt("Options/CheckForUpdates", 2)) {
|
switch (theConf->GetInt("Options/CheckForUpdates", 2)) {
|
||||||
case 0: ui.chkAutoUpdate->setCheckState(Qt::Unchecked); break;
|
case 0: ui.chkAutoUpdate->setCheckState(Qt::Unchecked); break;
|
||||||
|
@ -47,6 +48,8 @@ CSettingsWindow::CSettingsWindow(QWidget *parent)
|
||||||
case 2: ui.chkSandboxUrls->setCheckState(Qt::PartiallyChecked); break;
|
case 2: ui.chkSandboxUrls->setCheckState(Qt::PartiallyChecked); break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ui.chkShowRecovery->setChecked(theConf->GetBool("Options/ShowRecovery", false));
|
||||||
|
|
||||||
ui.chkWatchConfig->setChecked(theConf->GetBool("Options/WatchIni", true));
|
ui.chkWatchConfig->setChecked(theConf->GetBool("Options/WatchIni", true));
|
||||||
|
|
||||||
ui.onClose->addItem(tr("Close to Tray"), "ToTray");
|
ui.onClose->addItem(tr("Close to Tray"), "ToTray");
|
||||||
|
@ -112,6 +115,8 @@ CSettingsWindow::CSettingsWindow(QWidget *parent)
|
||||||
}
|
}
|
||||||
m_WarnProgsChanged = false;
|
m_WarnProgsChanged = false;
|
||||||
|
|
||||||
|
connect(ui.btnBrowse, SIGNAL(pressed()), this, SLOT(OnBrowse()));
|
||||||
|
|
||||||
int PortableRootDir = theConf->GetInt("Options/PortableRootDir", -1);
|
int PortableRootDir = theConf->GetInt("Options/PortableRootDir", -1);
|
||||||
if (PortableRootDir != -1 && theConf->IsPortable())
|
if (PortableRootDir != -1 && theConf->IsPortable())
|
||||||
ui.chkAutoRoot->setChecked(PortableRootDir == 0 ? Qt::Unchecked : Qt::Checked);
|
ui.chkAutoRoot->setChecked(PortableRootDir == 0 ? Qt::Unchecked : Qt::Checked);
|
||||||
|
@ -131,7 +136,7 @@ CSettingsWindow::CSettingsWindow(QWidget *parent)
|
||||||
|
|
||||||
connect(ui.tabs, SIGNAL(currentChanged(int)), this, SLOT(OnTab()));
|
connect(ui.tabs, SIGNAL(currentChanged(int)), this, SLOT(OnTab()));
|
||||||
|
|
||||||
connect(ui.buttonBox->button(QDialogButtonBox::Ok), SIGNAL(pressed()), this, SLOT(accept()));
|
connect(ui.buttonBox->button(QDialogButtonBox::Ok), SIGNAL(pressed()), this, SLOT(ok()));
|
||||||
connect(ui.buttonBox->button(QDialogButtonBox::Apply), SIGNAL(pressed()), this, SLOT(apply()));
|
connect(ui.buttonBox->button(QDialogButtonBox::Apply), SIGNAL(pressed()), this, SLOT(apply()));
|
||||||
connect(ui.buttonBox, SIGNAL(rejected()), this, SLOT(reject()));
|
connect(ui.buttonBox, SIGNAL(rejected()), this, SLOT(reject()));
|
||||||
|
|
||||||
|
@ -154,6 +159,7 @@ void CSettingsWindow::showCompat()
|
||||||
|
|
||||||
void CSettingsWindow::closeEvent(QCloseEvent *e)
|
void CSettingsWindow::closeEvent(QCloseEvent *e)
|
||||||
{
|
{
|
||||||
|
emit Closed();
|
||||||
this->deleteLater();
|
this->deleteLater();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -164,6 +170,7 @@ void CSettingsWindow::apply()
|
||||||
theConf->SetValue("Options/DarkTheme", ui.chkDarkTheme->isChecked());
|
theConf->SetValue("Options/DarkTheme", ui.chkDarkTheme->isChecked());
|
||||||
|
|
||||||
AutorunEnable(ui.chkAutoStart->isChecked());
|
AutorunEnable(ui.chkAutoStart->isChecked());
|
||||||
|
theAPI->GetUserSettings()->SetBool("SbieCtrl_EnableAutoStart", ui.chkSvcStart->isChecked());
|
||||||
|
|
||||||
switch (ui.chkAutoUpdate->checkState()) {
|
switch (ui.chkAutoUpdate->checkState()) {
|
||||||
case Qt::Unchecked: theConf->SetValue("Options/CheckForUpdates", 0); break;
|
case Qt::Unchecked: theConf->SetValue("Options/CheckForUpdates", 0); break;
|
||||||
|
@ -187,6 +194,8 @@ void CSettingsWindow::apply()
|
||||||
case Qt::Checked: theConf->SetValue("Options/OpenUrlsSandboxed", 1); break;
|
case Qt::Checked: theConf->SetValue("Options/OpenUrlsSandboxed", 1); break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
theConf->SetValue("Options/ShowRecovery", ui.chkShowRecovery->isChecked());
|
||||||
|
|
||||||
theConf->SetValue("Options/WatchIni", ui.chkWatchConfig->isChecked());
|
theConf->SetValue("Options/WatchIni", ui.chkWatchConfig->isChecked());
|
||||||
|
|
||||||
theConf->SetValue("Options/OnClose", ui.onClose->currentData());
|
theConf->SetValue("Options/OnClose", ui.onClose->currentData());
|
||||||
|
@ -280,7 +289,7 @@ void CSettingsWindow::apply()
|
||||||
emit OptionsChanged();
|
emit OptionsChanged();
|
||||||
}
|
}
|
||||||
|
|
||||||
void CSettingsWindow::accept()
|
void CSettingsWindow::ok()
|
||||||
{
|
{
|
||||||
apply();
|
apply();
|
||||||
|
|
||||||
|
@ -292,6 +301,15 @@ void CSettingsWindow::reject()
|
||||||
this->close();
|
this->close();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void CSettingsWindow::OnBrowse()
|
||||||
|
{
|
||||||
|
QString Value = QFileDialog::getExistingDirectory(this, tr("Select Directory")).replace("/", "\\");
|
||||||
|
if (Value.isEmpty())
|
||||||
|
return;
|
||||||
|
|
||||||
|
ui.fileRoot->setText(Value + "\\%SANDBOX%");
|
||||||
|
}
|
||||||
|
|
||||||
void CSettingsWindow::OnChange()
|
void CSettingsWindow::OnChange()
|
||||||
{
|
{
|
||||||
//ui.chkLinuxStyle->setEnabled(!ui.chkUseCycles->isChecked());
|
//ui.chkLinuxStyle->setEnabled(!ui.chkUseCycles->isChecked());
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
#include <QtWidgets/QMainWindow>
|
#include <QtWidgets/QMainWindow>
|
||||||
#include "ui_SettingsWindow.h"
|
#include "ui_SettingsWindow.h"
|
||||||
|
|
||||||
class CSettingsWindow : public QMainWindow
|
class CSettingsWindow : public QDialog
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
|
@ -11,13 +11,16 @@ public:
|
||||||
CSettingsWindow(QWidget *parent = Q_NULLPTR);
|
CSettingsWindow(QWidget *parent = Q_NULLPTR);
|
||||||
~CSettingsWindow();
|
~CSettingsWindow();
|
||||||
|
|
||||||
|
virtual void accept() {}
|
||||||
|
virtual void reject();
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
void OptionsChanged();
|
void OptionsChanged();
|
||||||
|
void Closed();
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
|
void ok();
|
||||||
void apply();
|
void apply();
|
||||||
void accept();
|
|
||||||
void reject();
|
|
||||||
|
|
||||||
void showCompat();
|
void showCompat();
|
||||||
|
|
||||||
|
@ -26,6 +29,8 @@ private slots:
|
||||||
|
|
||||||
void OnTab();
|
void OnTab();
|
||||||
|
|
||||||
|
void OnBrowse();
|
||||||
|
|
||||||
void OnSetPassword();
|
void OnSetPassword();
|
||||||
|
|
||||||
void OnWarnChanged() { m_WarnProgsChanged = true; }
|
void OnWarnChanged() { m_WarnProgsChanged = true; }
|
||||||
|
|
|
@ -6,11 +6,9 @@
|
||||||
|
|
||||||
|
|
||||||
CSnapshotsWindow::CSnapshotsWindow(const CSandBoxPtr& pBox, QWidget *parent)
|
CSnapshotsWindow::CSnapshotsWindow(const CSandBoxPtr& pBox, QWidget *parent)
|
||||||
: QMainWindow(parent)
|
: QDialog(parent)
|
||||||
{
|
{
|
||||||
QWidget* centralWidget = new QWidget();
|
ui.setupUi(this);
|
||||||
ui.setupUi(centralWidget);
|
|
||||||
this->setCentralWidget(centralWidget);
|
|
||||||
this->setWindowTitle(tr("%1 - Snapshots").arg(pBox->GetName()));
|
this->setWindowTitle(tr("%1 - Snapshots").arg(pBox->GetName()));
|
||||||
|
|
||||||
m_pBox = pBox;
|
m_pBox = pBox;
|
||||||
|
@ -20,6 +18,7 @@ CSnapshotsWindow::CSnapshotsWindow(const CSandBoxPtr& pBox, QWidget *parent)
|
||||||
QStyle* pStyle = QStyleFactory::create("windows");
|
QStyle* pStyle = QStyleFactory::create("windows");
|
||||||
ui.treeSnapshots->setStyle(pStyle);
|
ui.treeSnapshots->setStyle(pStyle);
|
||||||
#endif
|
#endif
|
||||||
|
ui.treeSnapshots->setExpandsOnDoubleClick(false);
|
||||||
|
|
||||||
m_pSnapshotModel = new CSimpleTreeModel();
|
m_pSnapshotModel = new CSimpleTreeModel();
|
||||||
m_pSnapshotModel->AddColumn(tr("Snapshot"), "Name");
|
m_pSnapshotModel->AddColumn(tr("Snapshot"), "Name");
|
||||||
|
@ -45,7 +44,11 @@ CSnapshotsWindow::CSnapshotsWindow(const CSandBoxPtr& pBox, QWidget *parent)
|
||||||
connect(ui.txtName, SIGNAL(textEdited(const QString&)), this, SLOT(SaveInfo()));
|
connect(ui.txtName, SIGNAL(textEdited(const QString&)), this, SLOT(SaveInfo()));
|
||||||
connect(ui.txtInfo, SIGNAL(textChanged()), this, SLOT(SaveInfo()));
|
connect(ui.txtInfo, SIGNAL(textChanged()), this, SLOT(SaveInfo()));
|
||||||
|
|
||||||
statusBar();
|
ui.groupBox->setEnabled(false);
|
||||||
|
ui.btnSelect->setEnabled(false);
|
||||||
|
ui.btnRemove->setEnabled(false);
|
||||||
|
|
||||||
|
//statusBar();
|
||||||
|
|
||||||
restoreGeometry(theConf->GetBlob("SnapshotsWindow/Window_Geometry"));
|
restoreGeometry(theConf->GetBlob("SnapshotsWindow/Window_Geometry"));
|
||||||
|
|
||||||
|
@ -91,6 +94,10 @@ void CSnapshotsWindow::UpdateSnapshots()
|
||||||
|
|
||||||
void CSnapshotsWindow::UpdateSnapshot(const QModelIndex& Index)
|
void CSnapshotsWindow::UpdateSnapshot(const QModelIndex& Index)
|
||||||
{
|
{
|
||||||
|
ui.groupBox->setEnabled(true);
|
||||||
|
ui.btnSelect->setEnabled(true);
|
||||||
|
ui.btnRemove->setEnabled(true);
|
||||||
|
|
||||||
//QModelIndex Index = ui.treeSnapshots->currentIndex();
|
//QModelIndex Index = ui.treeSnapshots->currentIndex();
|
||||||
//QModelIndex ModelIndex = m_pSortProxy->mapToSource(Index);
|
//QModelIndex ModelIndex = m_pSortProxy->mapToSource(Index);
|
||||||
//QVariant ID = m_pSnapshotModel->GetItemID(ModelIndex);
|
//QVariant ID = m_pSnapshotModel->GetItemID(ModelIndex);
|
||||||
|
@ -106,7 +113,7 @@ void CSnapshotsWindow::UpdateSnapshot(const QModelIndex& Index)
|
||||||
ui.txtInfo->setPlainText(BoxSnapshot["Info"].toString());
|
ui.txtInfo->setPlainText(BoxSnapshot["Info"].toString());
|
||||||
m_SaveInfoPending = 0;
|
m_SaveInfoPending = 0;
|
||||||
|
|
||||||
statusBar()->showMessage(tr("Snapshot: %1 taken: %2").arg(BoxSnapshot["Name"].toString()).arg(BoxSnapshot["Date"].toDateTime().toString()));
|
//statusBar()->showMessage(tr("Snapshot: %1 taken: %2").arg(BoxSnapshot["Name"].toString()).arg(BoxSnapshot["Date"].toDateTime().toString()));
|
||||||
}
|
}
|
||||||
|
|
||||||
void CSnapshotsWindow::SaveInfo()
|
void CSnapshotsWindow::SaveInfo()
|
||||||
|
@ -143,7 +150,7 @@ void CSnapshotsWindow::OnSelectSnapshot()
|
||||||
//QVariant ID = m_pSnapshotModel->GetItemID(ModelIndex);
|
//QVariant ID = m_pSnapshotModel->GetItemID(ModelIndex);
|
||||||
QVariant ID = m_pSnapshotModel->GetItemID(Index);
|
QVariant ID = m_pSnapshotModel->GetItemID(Index);
|
||||||
|
|
||||||
if (QMessageBox("Sandboxie-Plus", tr("Do you really want to switch the active snapshot? Doing so will delete the current state!"), QMessageBox::Warning, QMessageBox::Yes, QMessageBox::No | QMessageBox::Default | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
if (QMessageBox("Sandboxie-Plus", tr("Do you really want to switch the active snapshot? Doing so will delete the current state!"), QMessageBox::Question, QMessageBox::Yes, QMessageBox::No | QMessageBox::Default | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
HandleResult(m_pBox->SelectSnapshot(ID.toString()));
|
HandleResult(m_pBox->SelectSnapshot(ID.toString()));
|
||||||
|
@ -156,7 +163,7 @@ void CSnapshotsWindow::OnRemoveSnapshot()
|
||||||
//QVariant ID = m_pSnapshotModel->GetItemID(ModelIndex);
|
//QVariant ID = m_pSnapshotModel->GetItemID(ModelIndex);
|
||||||
QVariant ID = m_pSnapshotModel->GetItemID(Index);
|
QVariant ID = m_pSnapshotModel->GetItemID(Index);
|
||||||
|
|
||||||
if (QMessageBox("Sandboxie-Plus", tr("Do you really want to delete the selected snapshot?"), QMessageBox::Warning, QMessageBox::Yes, QMessageBox::No | QMessageBox::Default | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
if (QMessageBox("Sandboxie-Plus", tr("Do you really want to delete the selected snapshot?"), QMessageBox::Question, QMessageBox::Yes, QMessageBox::No | QMessageBox::Default | QMessageBox::Escape, QMessageBox::NoButton).exec() != QMessageBox::Yes)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
HandleResult(m_pBox->RemoveSnapshot(ID.toString()));
|
HandleResult(m_pBox->RemoveSnapshot(ID.toString()));
|
||||||
|
|
|
@ -5,7 +5,7 @@
|
||||||
#include "SbiePlusAPI.h"
|
#include "SbiePlusAPI.h"
|
||||||
class CSimpleTreeModel;
|
class CSimpleTreeModel;
|
||||||
|
|
||||||
class CSnapshotsWindow : public QMainWindow
|
class CSnapshotsWindow : public QDialog
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
|
@ -13,6 +13,9 @@ public:
|
||||||
CSnapshotsWindow(const CSandBoxPtr& pBox, QWidget *parent = Q_NULLPTR);
|
CSnapshotsWindow(const CSandBoxPtr& pBox, QWidget *parent = Q_NULLPTR);
|
||||||
~CSnapshotsWindow();
|
~CSnapshotsWindow();
|
||||||
|
|
||||||
|
virtual void accept() {}
|
||||||
|
virtual void reject() { this->close(); }
|
||||||
|
|
||||||
private slots:
|
private slots:
|
||||||
void UpdateSnapshots();
|
void UpdateSnapshots();
|
||||||
void UpdateSnapshot(const QModelIndex& Index);
|
void UpdateSnapshot(const QModelIndex& Index);
|
||||||
|
|
|
@ -20,6 +20,7 @@ int main(int argc, char *argv[])
|
||||||
//QCoreApplication::setAttribute(Qt::AA_DisableHighDpiScaling);
|
//QCoreApplication::setAttribute(Qt::AA_DisableHighDpiScaling);
|
||||||
|
|
||||||
QtSingleApplication app(argc, argv);
|
QtSingleApplication app(argc, argv);
|
||||||
|
app.setQuitOnLastWindowClosed(false);
|
||||||
|
|
||||||
//InitConsole(false);
|
//InitConsole(false);
|
||||||
|
|
||||||
|
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
@ -217,6 +217,18 @@
|
||||||
<source>Please enter an auto exec command</source>
|
<source>Please enter an auto exec command</source>
|
||||||
<translation>Пожалуйста, введите команду auto exec</translation>
|
<translation>Пожалуйста, введите команду auto exec</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>This sandbox has been deleted hence configuration can not be saved.</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Some changes haven't been saved yet, do you really want to close this options window?</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Executables (*.exe *.cmd);;All files (*.*)</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CPopUpMessage</name>
|
<name>CPopUpMessage</name>
|
||||||
|
@ -282,6 +294,10 @@
|
||||||
<source>Request timed out</source>
|
<source>Request timed out</source>
|
||||||
<translation>Срок действия запроса истек</translation>
|
<translation>Срок действия запроса истек</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Yes and add to allowed programs</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CPopUpRecovery</name>
|
<name>CPopUpRecovery</name>
|
||||||
|
@ -363,27 +379,47 @@
|
||||||
<message>
|
<message>
|
||||||
<source>Do you want to allow %4 (%5) to copy a %1 large file into sandbox: %2?
|
<source>Do you want to allow %4 (%5) to copy a %1 large file into sandbox: %2?
|
||||||
File name: %3</source>
|
File name: %3</source>
|
||||||
<translation>Разрешить%4 (%5) копировать большой файл %1 в песочницу:%2?
|
<translation type="vanished">Разрешить%4 (%5) копировать большой файл %1 в песочницу:%2?
|
||||||
Имя файла:%3</translation>
|
Имя файла:%3</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Do you want to allow %1 (%2) access to the internet?
|
<source>Do you want to allow %1 (%2) access to the internet?
|
||||||
Full path: %3</source>
|
Full path: %3</source>
|
||||||
<translation>Вы хотите разрешить %1 (%2) доступ к Интернету?
|
<translation type="vanished">Вы хотите разрешить %1 (%2) доступ к Интернету?
|
||||||
Полный путь: %3</translation>
|
Полный путь: %3</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>%1 is eligible for quick recovery from %2.
|
<source>%1 is eligible for quick recovery from %2.
|
||||||
The file was written by: %3</source>
|
The file was written by: %3</source>
|
||||||
<translation>%1 имеет право на быстрое восстановление с %2.
|
<translation type="vanished">%1 имеет право на быстрое восстановление с %2.
|
||||||
Файл был записан: %3</translation>
|
Файл был записан: %3</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Migrating a large file %1 into the sandbox %2, %3 left.
|
<source>Migrating a large file %1 into the sandbox %2, %3 left.
|
||||||
Full path: %4</source>
|
Full path: %4</source>
|
||||||
<translation>Перенос большого файла %1 в песочницу %2, осталось %3.
|
<translation type="vanished">Перенос большого файла %1 в песочницу %2, осталось %3.
|
||||||
Полный путь: %4</translation>
|
Полный путь: %4</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Do you want to allow %4 (%5) to copy a %1 large file into sandbox: %2?
|
||||||
|
File name: %3</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Do you want to allow %1 (%2) access to the internet?
|
||||||
|
Full path: %3</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>%1 is eligible for quick recovery from %2.
|
||||||
|
The file was written by: %3</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Migrating a large file %1 into the sandbox %2, %3 left.
|
||||||
|
Full path: %4</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CRecoveryWindow</name>
|
<name>CRecoveryWindow</name>
|
||||||
|
@ -407,6 +443,14 @@ Full path: %4</source>
|
||||||
<source>%1 - File Recovery</source>
|
<source>%1 - File Recovery</source>
|
||||||
<translation>%1 - Восстановление файла</translation>
|
<translation>%1 - Восстановление файла</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>One or more selected files are located on a network share, and must be recovered to a local drive, please select a folder to recover all selected files to.</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>There are %1 files and %2 folders in the sandbox, occupying %3 bytes of disk space.</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CResMonModel</name>
|
<name>CResMonModel</name>
|
||||||
|
@ -996,6 +1040,30 @@ Please download the latest release and set it up with the Sandboxie.ini as instr
|
||||||
<source><p>Sandboxie-Plus is an open source continuation of Sandboxie.</p><p></p><p>Visit <a href="https://sandboxie-plus.com">sandboxie-plus.com</a> for more information.</p><p></p><p></p><p></p><p>Icons from <a href="https://icons8.com">icons8.com</a></p><p></p></source>
|
<source><p>Sandboxie-Plus is an open source continuation of Sandboxie.</p><p></p><p>Visit <a href="https://sandboxie-plus.com">sandboxie-plus.com</a> for more information.</p><p></p><p></p><p></p><p>Icons from <a href="https://icons8.com">icons8.com</a></p><p></p></source>
|
||||||
<translation><p>Sandboxie-Plus - это продолжение Sandboxie с открытым исходным кодом.</p><p></p><p>Посетите <a href="https://sandboxie-plus.com">sandboxie-plus.com</a> для дополнительной информации.</p><p></p><p></p><p></p><p>Иконки из <a href="https://icons8.com">icons8.com</a></p><p></p></translation>
|
<translation><p>Sandboxie-Plus - это продолжение Sandboxie с открытым исходным кодом.</p><p></p><p>Посетите <a href="https://sandboxie-plus.com">sandboxie-plus.com</a> для дополнительной информации.</p><p></p><p></p><p></p><p>Иконки из <a href="https://icons8.com">icons8.com</a></p><p></p></translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Always on Top</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Sellect box:</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Some compatybility templates (%1) are missing, probably deleted, do you want to remove them from all boxes?</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Cleaned up removed templates...</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Can not create snapshot of an empty sandbox</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>A sandbox with that name already exists</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CSbieModel</name>
|
<name>CSbieModel</name>
|
||||||
|
@ -1053,7 +1121,7 @@ Please download the latest release and set it up with the Sandboxie.ini as instr
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Do you really want to delete the content of the selected sandbox(es)?</source>
|
<source>Do you really want to delete the content of the selected sandbox(es)?</source>
|
||||||
<translation>Вы действительно хотите удалить содержимое выбранных песочниц?</translation>
|
<translation type="vanished">Вы действительно хотите удалить содержимое выбранных песочниц?</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Drop Admin Rights</source>
|
<source>Drop Admin Rights</source>
|
||||||
|
@ -1230,6 +1298,22 @@ Please download the latest release and set it up with the Sandboxie.ini as instr
|
||||||
<source>This box does not have Internet restrictions in place, do you want to enable them?</source>
|
<source>This box does not have Internet restrictions in place, do you want to enable them?</source>
|
||||||
<translation>В этой песочнице нет ограничений на доступ к Интернет, вы хотите их включить?</translation>
|
<translation>В этой песочнице нет ограничений на доступ к Интернет, вы хотите их включить?</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Don't show this message again.</source>
|
||||||
|
<translation type="unfinished">Больше не показывать это сообщение.</translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>This Sandbox is already empty.</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Do you want to delete the content of the selected sandbox?</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Do you really want to delete the content of multiple sandboxes?</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CSettingsWindow</name>
|
<name>CSettingsWindow</name>
|
||||||
|
@ -1294,7 +1378,7 @@ Please download the latest release and set it up with the Sandboxie.ini as instr
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Snapshot: %1 taken: %2</source>
|
<source>Snapshot: %1 taken: %2</source>
|
||||||
<translation>Снимок: %1 сделан: %2</translation>
|
<translation type="vanished">Снимок: %1 сделан: %2</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Do you really want to switch the active snapshot? Doing so will delete the current state!</source>
|
<source>Do you really want to switch the active snapshot? Doing so will delete the current state!</source>
|
||||||
|
@ -1817,7 +1901,7 @@ Note: Forced Programs and Force Folders settings for a sandbox do not apply to
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Start the sandboxed RpcSs as a SYSTEM process (breaks some compatibility)</source>
|
<source>Start the sandboxed RpcSs as a SYSTEM process (breaks some compatibility)</source>
|
||||||
<translation>Запускать RpcSs в песочнице как СИСТЕМНЫЙ процесс (нарушает некоторую совместимость)</translation>
|
<translation type="vanished">Запускать RpcSs в песочнице как СИСТЕМНЫЙ процесс (нарушает некоторую совместимость)</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>COM Class Trace</source>
|
<source>COM Class Trace</source>
|
||||||
|
@ -1898,6 +1982,29 @@ Note: Forced Programs and Force Folders settings for a sandbox do not apply to
|
||||||
<translation>Диск %1</translation>
|
<translation>Диск %1</translation>
|
||||||
</message>
|
</message>
|
||||||
</context>
|
</context>
|
||||||
|
<context>
|
||||||
|
<name>QPlatformTheme</name>
|
||||||
|
<message>
|
||||||
|
<source>Cancel</source>
|
||||||
|
<translation type="vanished">Отмена</translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Apply</source>
|
||||||
|
<translation type="vanished">Применить</translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>OK</source>
|
||||||
|
<translation type="vanished">ОК</translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>&Yes</source>
|
||||||
|
<translation type="vanished">&Да</translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>&No</source>
|
||||||
|
<translation type="vanished">&Нет</translation>
|
||||||
|
</message>
|
||||||
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>RecoveryWindow</name>
|
<name>RecoveryWindow</name>
|
||||||
<message>
|
<message>
|
||||||
|
@ -1928,6 +2035,14 @@ Note: Forced Programs and Force Folders settings for a sandbox do not apply to
|
||||||
<source>Delete all</source>
|
<source>Delete all</source>
|
||||||
<translation>Удалить все</translation>
|
<translation>Удалить все</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Show All Files</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>TextLabel</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>SettingsWindow</name>
|
<name>SettingsWindow</name>
|
||||||
|
@ -2069,7 +2184,7 @@ Note: Forced Programs and Force Folders settings for a sandbox do not apply to
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Start with Windows</source>
|
<source>Start with Windows</source>
|
||||||
<translation>Запускать с Windows</translation>
|
<translation type="vanished">Запускать с Windows</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Open urls from this ui sandboxed</source>
|
<source>Open urls from this ui sandboxed</source>
|
||||||
|
@ -2091,6 +2206,26 @@ Note: Forced Programs and Force Folders settings for a sandbox do not apply to
|
||||||
<source>Portable root folder</source>
|
<source>Portable root folder</source>
|
||||||
<translation>Корневая папка портативной версии</translation>
|
<translation>Корневая папка портативной версии</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Start UI with Windows</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Start UI when a sandboxed process is started</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Show first recovery window when emptying sandboxes</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>...</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Other settings</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>SnapshotsWindow</name>
|
<name>SnapshotsWindow</name>
|
||||||
|
@ -2116,11 +2251,19 @@ Note: Forced Programs and Force Folders settings for a sandbox do not apply to
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Snapshot Details</source>
|
<source>Snapshot Details</source>
|
||||||
<translation>Детали снимка</translation>
|
<translation type="vanished">Детали снимка</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Take Snapshot</source>
|
<source>Take Snapshot</source>
|
||||||
<translation>Сделать снимок</translation>
|
<translation>Сделать снимок</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Selected Snapshot Details</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Snapshot Actions</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
</TS>
|
</TS>
|
||||||
|
|
|
@ -1,29 +1,6 @@
|
||||||
<?xml version="1.0" encoding="utf-8"?>
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
<!DOCTYPE TS>
|
<!DOCTYPE TS>
|
||||||
<TS version="2.1" language="zh">
|
<TS version="2.1" language="zh">
|
||||||
<context>
|
|
||||||
<name>QPlatformTheme</name>
|
|
||||||
<message>
|
|
||||||
<source>OK</source>
|
|
||||||
<translation>确定</translation>
|
|
||||||
</message>
|
|
||||||
<message>
|
|
||||||
<source>Apply</source>
|
|
||||||
<translation>应用</translation>
|
|
||||||
</message>
|
|
||||||
<message>
|
|
||||||
<source>Cancel</source>
|
|
||||||
<translation>取消</translation>
|
|
||||||
</message>
|
|
||||||
<message>
|
|
||||||
<source>&Yes</source>
|
|
||||||
<translation>&是</translation>
|
|
||||||
</message>
|
|
||||||
<message>
|
|
||||||
<source>&No</source>
|
|
||||||
<translation>&否</translation>
|
|
||||||
</message>
|
|
||||||
</context>
|
|
||||||
<context>
|
<context>
|
||||||
<name>CApiMonModel</name>
|
<name>CApiMonModel</name>
|
||||||
<message>
|
<message>
|
||||||
|
@ -239,6 +216,18 @@
|
||||||
<source>Please enter an auto exec command</source>
|
<source>Please enter an auto exec command</source>
|
||||||
<translation>请输入自动运行命令</translation>
|
<translation>请输入自动运行命令</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>This sandbox has been deleted hence configuration can not be saved.</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Some changes haven't been saved yet, do you really want to close this options window?</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Executables (*.exe *.cmd);;All files (*.*)</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CPopUpMessage</name>
|
<name>CPopUpMessage</name>
|
||||||
|
@ -304,6 +293,10 @@
|
||||||
<source>Request timed out</source>
|
<source>Request timed out</source>
|
||||||
<translation>请求超时</translation>
|
<translation>请求超时</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Yes and add to allowed programs</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CPopUpRecovery</name>
|
<name>CPopUpRecovery</name>
|
||||||
|
@ -385,27 +378,47 @@
|
||||||
<message>
|
<message>
|
||||||
<source>Do you want to allow %4 (%5) to copy a %1 large file into sandbox: %2?
|
<source>Do you want to allow %4 (%5) to copy a %1 large file into sandbox: %2?
|
||||||
File name: %3</source>
|
File name: %3</source>
|
||||||
<translation>您想允许 %4 (%5) 复制 %1 大文件到沙盒: %2 吗?
|
<translation type="vanished">您想允许 %4 (%5) 复制 %1 大文件到沙盒: %2 吗?
|
||||||
文件名称: %3</translation>
|
文件名称: %3</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Do you want to allow %1 (%2) access to the internet?
|
<source>Do you want to allow %1 (%2) access to the internet?
|
||||||
Full path: %3</source>
|
Full path: %3</source>
|
||||||
<translation>您想允许 %1 (%2) 访问网络吗?
|
<translation type="vanished">您想允许 %1 (%2) 访问网络吗?
|
||||||
完整路径: %3</translation>
|
完整路径: %3</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>%1 is eligible for quick recovery from %2.
|
<source>%1 is eligible for quick recovery from %2.
|
||||||
The file was written by: %3</source>
|
The file was written by: %3</source>
|
||||||
<translation>%1 可以从 %2 快速恢复.
|
<translation type="vanished">%1 可以从 %2 快速恢复.
|
||||||
文件写入自: %3</translation>
|
文件写入自: %3</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Migrating a large file %1 into the sandbox %2, %3 left.
|
<source>Migrating a large file %1 into the sandbox %2, %3 left.
|
||||||
Full path: %4</source>
|
Full path: %4</source>
|
||||||
<translation>移动大文件 %1 到沙盒 %2, %3 遗留.
|
<translation type="vanished">移动大文件 %1 到沙盒 %2, %3 遗留.
|
||||||
完整路径: %4</translation>
|
完整路径: %4</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Do you want to allow %4 (%5) to copy a %1 large file into sandbox: %2?
|
||||||
|
File name: %3</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Do you want to allow %1 (%2) access to the internet?
|
||||||
|
Full path: %3</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>%1 is eligible for quick recovery from %2.
|
||||||
|
The file was written by: %3</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Migrating a large file %1 into the sandbox %2, %3 left.
|
||||||
|
Full path: %4</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CRecoveryWindow</name>
|
<name>CRecoveryWindow</name>
|
||||||
|
@ -429,6 +442,14 @@ Full path: %4</source>
|
||||||
<source>%1 - File Recovery</source>
|
<source>%1 - File Recovery</source>
|
||||||
<translation>%1 - 文件恢复</translation>
|
<translation>%1 - 文件恢复</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>One or more selected files are located on a network share, and must be recovered to a local drive, please select a folder to recover all selected files to.</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>There are %1 files and %2 folders in the sandbox, occupying %3 bytes of disk space.</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CResMonModel</name>
|
<name>CResMonModel</name>
|
||||||
|
@ -1018,6 +1039,30 @@ Please download the latest release and set it up with the Sandboxie.ini as instr
|
||||||
<source><p>Sandboxie-Plus is an open source continuation of Sandboxie.</p><p></p><p>Visit <a href="https://sandboxie-plus.com">sandboxie-plus.com</a> for more information.</p><p></p><p></p><p></p><p>Icons from <a href="https://icons8.com">icons8.com</a></p><p></p></source>
|
<source><p>Sandboxie-Plus is an open source continuation of Sandboxie.</p><p></p><p>Visit <a href="https://sandboxie-plus.com">sandboxie-plus.com</a> for more information.</p><p></p><p></p><p></p><p>Icons from <a href="https://icons8.com">icons8.com</a></p><p></p></source>
|
||||||
<translation><p>Sandboxie-Plus是著名开源程序Sandboxie的延续.</p><p></p><p>访问 <a href="https://sandboxie-plus.com">sandboxie-plus.com</a> 来获取更多信息.</p><p></p><p></p><p></p><p>图标来自 <a href="https://icons8.com">icons8.com</a></p><p></p></translation>
|
<translation><p>Sandboxie-Plus是著名开源程序Sandboxie的延续.</p><p></p><p>访问 <a href="https://sandboxie-plus.com">sandboxie-plus.com</a> 来获取更多信息.</p><p></p><p></p><p></p><p>图标来自 <a href="https://icons8.com">icons8.com</a></p><p></p></translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Always on Top</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Sellect box:</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Some compatybility templates (%1) are missing, probably deleted, do you want to remove them from all boxes?</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Cleaned up removed templates...</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Can not create snapshot of an empty sandbox</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>A sandbox with that name already exists</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CSbieModel</name>
|
<name>CSbieModel</name>
|
||||||
|
@ -1075,7 +1120,7 @@ Please download the latest release and set it up with the Sandboxie.ini as instr
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Do you really want to delete the content of the selected sandbox(es)?</source>
|
<source>Do you really want to delete the content of the selected sandbox(es)?</source>
|
||||||
<translation>确定要删除所选沙盒的所有内容吗?</translation>
|
<translation type="vanished">确定要删除所选沙盒的所有内容吗?</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Drop Admin Rights</source>
|
<source>Drop Admin Rights</source>
|
||||||
|
@ -1251,6 +1296,22 @@ Please download the latest release and set it up with the Sandboxie.ini as instr
|
||||||
<source>Allow internet access</source>
|
<source>Allow internet access</source>
|
||||||
<translation>允许网络访问</translation>
|
<translation>允许网络访问</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Don't show this message again.</source>
|
||||||
|
<translation type="unfinished">不再显示此消息</translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>This Sandbox is already empty.</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Do you want to delete the content of the selected sandbox?</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Do you really want to delete the content of multiple sandboxes?</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>CSettingsWindow</name>
|
<name>CSettingsWindow</name>
|
||||||
|
@ -1315,7 +1376,7 @@ Please download the latest release and set it up with the Sandboxie.ini as instr
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Snapshot: %1 taken: %2</source>
|
<source>Snapshot: %1 taken: %2</source>
|
||||||
<translation>快照: %1 取自: %2</translation>
|
<translation type="vanished">快照: %1 取自: %2</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Do you really want to switch the active snapshot? Doing so will delete the current state!</source>
|
<source>Do you really want to switch the active snapshot? Doing so will delete the current state!</source>
|
||||||
|
@ -1783,7 +1844,7 @@ Note: Forced Programs and Force Folders settings for a sandbox do not apply to
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Start the sandboxed RpcSs as a SYSTEM process (breaks some compatibility)</source>
|
<source>Start the sandboxed RpcSs as a SYSTEM process (breaks some compatibility)</source>
|
||||||
<translation>启动沙盒化的RpcSs作为系统进程 (破坏一些兼容性)</translation>
|
<translation type="vanished">启动沙盒化的RpcSs作为系统进程 (破坏一些兼容性)</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Issue message 1308 when a program fails to start</source>
|
<source>Issue message 1308 when a program fails to start</source>
|
||||||
|
@ -1918,6 +1979,29 @@ instead of "*".</source>
|
||||||
<translation>磁盘 %1</translation>
|
<translation>磁盘 %1</translation>
|
||||||
</message>
|
</message>
|
||||||
</context>
|
</context>
|
||||||
|
<context>
|
||||||
|
<name>QPlatformTheme</name>
|
||||||
|
<message>
|
||||||
|
<source>OK</source>
|
||||||
|
<translation type="vanished">确定</translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Apply</source>
|
||||||
|
<translation type="vanished">应用</translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Cancel</source>
|
||||||
|
<translation type="vanished">取消</translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>&Yes</source>
|
||||||
|
<translation type="vanished">&是</translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>&No</source>
|
||||||
|
<translation type="vanished">&否</translation>
|
||||||
|
</message>
|
||||||
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>RecoveryWindow</name>
|
<name>RecoveryWindow</name>
|
||||||
<message>
|
<message>
|
||||||
|
@ -1948,6 +2032,14 @@ instead of "*".</source>
|
||||||
<source>Delete all</source>
|
<source>Delete all</source>
|
||||||
<translation>删除全部</translation>
|
<translation>删除全部</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Show All Files</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>TextLabel</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>SettingsWindow</name>
|
<name>SettingsWindow</name>
|
||||||
|
@ -2105,12 +2197,32 @@ instead of "*".</source>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Start with Windows</source>
|
<source>Start with Windows</source>
|
||||||
<translation>开机启动</translation>
|
<translation type="vanished">开机启动</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Portable root folder</source>
|
<source>Portable root folder</source>
|
||||||
<translation>便携化根目录</translation>
|
<translation>便携化根目录</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Start UI with Windows</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Start UI when a sandboxed process is started</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Show first recovery window when emptying sandboxes</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>...</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Other settings</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
<context>
|
<context>
|
||||||
<name>SnapshotsWindow</name>
|
<name>SnapshotsWindow</name>
|
||||||
|
@ -2136,11 +2248,19 @@ instead of "*".</source>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Snapshot Details</source>
|
<source>Snapshot Details</source>
|
||||||
<translation>快照详情</translation>
|
<translation type="vanished">快照详情</translation>
|
||||||
</message>
|
</message>
|
||||||
<message>
|
<message>
|
||||||
<source>Take Snapshot</source>
|
<source>Take Snapshot</source>
|
||||||
<translation>抓取快照</translation>
|
<translation>抓取快照</translation>
|
||||||
</message>
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Selected Snapshot Details</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
|
<message>
|
||||||
|
<source>Snapshot Actions</source>
|
||||||
|
<translation type="unfinished"></translation>
|
||||||
|
</message>
|
||||||
</context>
|
</context>
|
||||||
</TS>
|
</TS>
|
||||||
|
|
Loading…
Reference in New Issue