From c8874c356a5974abd962eb073772a4c6df6ae647 Mon Sep 17 00:00:00 2001 From: DavidXanatos Date: Tue, 3 Nov 2020 16:45:04 +0100 Subject: [PATCH] --- CHANGELOG.md | 93 +++++++++++-------- Sandboxie/apps/com/RpcSs/rpcss.c | 1 + Sandboxie/apps/control/ShellDialog.cpp | 2 +- Sandboxie/common/my_version.h | 4 +- Sandboxie/core/dll/proc.c | 11 --- Sandboxie/core/drv/api_defs.h | 2 +- Sandboxie/core/drv/file.c | 24 ++++- Sandboxie/core/svc/sbieiniserver.cpp | 2 +- SandboxiePlus/QSbieAPI/Sandboxie/SandBox.cpp | 2 +- SandboxiePlus/QSbieAPI/SbieAPI.cpp | 9 +- SandboxiePlus/QSbieAPI/SbieAPI.h | 2 +- SandboxiePlus/SandMan/Forms/OptionsWindow.ui | 2 +- SandboxiePlus/SandMan/SandMan.cpp | 18 ++++ SandboxiePlus/SandMan/SandMan.h | 4 +- SandboxiePlus/SandMan/SbiePlusAPI.cpp | 13 ++- .../SandMan/Windows/OptionsWindow.cpp | 5 +- 16 files changed, 125 insertions(+), 69 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index f78195b7..ea1f6927 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,6 +3,23 @@ All notable changes to this project will be documented in this file. This project adheres to [Semantic Versioning](http://semver.org/). + +## [0.4.3 / 5.43.7] - 2020-11-03 + +### Added +- added disable forced programs menu command to he sandman ui + +### Changed + +### Fixed +- fixed file rename bug introduced with an earlier driver verifier fix +- fixed issue saving access lists +- fixed issue with program groups parsing in the SandMan UI +- fixed issue with intrnet access restriction options +- fixed issue deleting sandbox when located on a drive directly + + + ## [0.4.2 / 5.43.6] - 2020-10-10 ### Added @@ -11,28 +28,28 @@ This project adheres to [Semantic Versioning](http://semver.org/). ### Fixed - fixed thread handle leak in SbieSvc and other components - msedge.exe is now categorized as a chromium derivate -- fixed Chrome 86+ compatibility bug with Chrome's own sandbox +- fixed chrome 86+ compatybility bug with chroms own sandbox ## [0.4.1 / 5.43.5] - 2020-09-12 ### Added -- added core version compatibility check to sandman UI +- added core version compatybility check to sandman UI - added shell integration options to SbiePlus ### Changed -- SbieCtrl does no longer auto-show the tutorial on first start -- when hooking, the trampoline migrated section of the original function is no longer noped out -- it caused issues with unity games, will be investigated and re-enabled later +- SbieCtrl does not longer auto show the tutorian on first start +- when hooking, the to the trampoline migrated section of the original function is not longer noped out +-- it caused issues with unity games, will be investigated and re enabled later ### Fixed - fixed color issue with vertical tabs in dark mode - fixed wrong path separators when adding new forced folders -- fixed directory listing bug introduced in 5.43 +- fixed directroy listing bug intriduced in 5.43 - fixed issues with settings window when not being connected to driver -- fixed issue when starting Sandman UI as admin -- fixed auto content delete not working with Sandman UI +- fixed issue when starting sandman ui as admin +- fixed auto content delete not working with sandman ui @@ -40,20 +57,20 @@ This project adheres to [Semantic Versioning](http://semver.org/). ### Added - added a proper custom installer to the the Plus release -- added sandbox snapshot functionality to SBIE core -- filesystem is saved incrementally, the snapshots build upon each other -- each snapshot gets a full copy of the box registry for now -- each snapshot can have multiple children snapshots +- added sandbox snapshot functionality to sbie core +-- filesystem is saved incrementally, the snapshots built upon each other +-- each snapshot gets a full copy of the box registry for now +-- each snapshot can have multiple children snapshots - added access status to resource monitor - added setting to change border width - added snapshot manager UI to SandMan - added template to enable authentication with an Yubikey or comparable 2FA device -- added UI for program allert -- added software compatibility options to the UI +- added ui for program allert +- added software compatybility options to teh UI ### Changed - SandMan UI now handles deletion of sandboxe content on its own -- no longer adding redundant resource accesses as new events +- no longer adding redundnat resource accesses as new events ### Fixed - fixed issues when hooking functions from delay loaded libraries @@ -68,8 +85,8 @@ This project adheres to [Semantic Versioning](http://semver.org/). ## [0.3.5 / 5.42.1] - 2020-07-19 ### Added -- added settings window -- added translation support +- Added settings window +- added translationsupport - added dark theme - added auto start option - added sandbox options @@ -83,7 +100,7 @@ This project adheres to [Semantic Versioning](http://semver.org/). ### Fixed - fixed ini issue with sandman.exe when renaming sandboxes - fixed ini auto reload bug introduced in the last build -- fixed issue when hooking delayed loaded libraries +- fixed issue when hooking delayd loaded libraries @@ -91,21 +108,21 @@ This project adheres to [Semantic Versioning](http://semver.org/). ### Added - API_QUERY_PROCESS_INFO can be now used to get the original process token of sandboxed processes -- Note: this capability is used by TaskExplorer to allow inspecting sandbox internal tokens +-- Note: this capability is used by TaskExplorer to allow inspecting sandbox internal tokens - Added option "KeepTokenIntegrity=y" to make the sbie token keep its initial integrity level (debug option) -- Note: Do NOT USE Debug Options if you don't know their security implications (!) -- Added process ID to log messages very usefull for debugging +-- Note: Do NOT USE Debug Options if you dont know their security implications (!) +- Added process id to log messages very usefull for debugging - Added finder to resource log - Added option to hide host processes "HideHostProcess=[name]" -- Note: Sbie hides by default processes from other boxes, this behaviour can now be controlled with "HideOtherBoxes=n" +-- Note: Sbie hides by default processes from other boxes, this behavioure can now be controlled with "HideOtherBoxes=n" - Sandboxed RpcSs and DcomLaunch can now be run as system with the option "ProtectRpcSs=y" howeever tht breaks sandboxed explorer and other - BuiltIn Clsid whitelist can now be disabled with "OpenDefaultClsid=n" - Processes can be now terminated with the del key, and require a confirmation - Added sandboxed window border display to SandMan.exe - Added notification for sbie log messages - Added Sandbox Presets sub menu allowing to quickly change some settings -- Enable/Disable API logging, logapi_dll's are now distributed with SbiePlus -- And other: Drop admin rights; Block/Allow internet access; Block/Allow access to files on te network +-- Enable/Disable API logging, logapi_dll's are now distributed with SbiePlus +-- And other: Drop admin rights; Block/Allow internet access; Block/Allow access to files on te network - Added more info to the sandbox status column - Added path column to SbieModel - Added info tooltips in SbieView @@ -118,14 +135,14 @@ This project adheres to [Semantic Versioning](http://semver.org/). ### Fixed - added mising PreferExternalManifest itialization to portable mode - 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 -- Note: to disable the access check use "UnrestrictedSCM=y" (debug option) +-- Note: to disable the access check use "UnrestrictedSCM=y" (debug option) - fixed missing initialization in serviceserver that caused sandboxed programs to crash when querying service status - fixed many bugs that caused the SbieDrv.sys to BSOD when run with MSFT Driver Verifier active -- 0xF6 in GetThreadTokenOwnerPid and File_Api_Rename -- missing non-optional parameter for FltGetFileNameInformation in File_PreOperation -- 0xE3 in Key_StoreValue and Key_PreDataInject +-- 0xF6 in GetThreadTokenOwnerPid and File_Api_Rename +-- missing non optional parameter for FltGetFileNameInformation in File_PreOperation +-- 0xE3 in Key_StoreValue and Key_PreDataInject @@ -134,7 +151,7 @@ This project adheres to [Semantic Versioning](http://semver.org/). ### Added - added option SeparateUserFolders=n to no longer have the user profile files stored separately in the sandbox - added SandboxieLogon=y it makes processes run under the SID of the "Sandboxie" user instead of the Anonymous user -- Note: the global option AllowSandboxieLogon=y must be enabled, the "Sandboxie" user account must be manually created first and the driver reloaded, else process start will fail +-- Note: the global option AllowSandboxieLogon=y must be enabled, the "Sandboxie" user account must be manually created first and the driver reloaded, else process start will fail - improved debugging around process creation errors in the driver ### Fixed @@ -147,21 +164,21 @@ This project adheres to [Semantic Versioning](http://semver.org/). ### Added - added different sandbox icons for different types -- Red LogAPI/BSA enabled -- More to come :D +-- Red LogAPI/BSA enabled +-- More to come :D - Added progress window for async operations that take time - added DPI awareness - the driver file is now obfuscated to avoid false positives - additional debug options to sandboxie.ini OpenToken=y that combines UnrestrictedToken=y and UnfilteredToken=y -- 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 weekens the sandboxing, they are intended for debugging and may be used for better application virtualization later ### Changed -- SbieDll.dll when processing InjectDll now looks in the SbieHome folder for the Dll's if the entered path starts with a backslash -- i.e. "InjectDll=\LogAPI\i386\logapi32v.dll" or "InjectDll64=\LogAPI\amd64\logapi64v.dll" +- SbieDll.dll when processinh InjectDll now looks in the SbieHome folder for the Dll's if the entered path starts with a backslash +-- i.e. "InjectDll=\LogAPI\i386\logapi32v.dll" or "InjectDll64=\LogAPI\amd64\logapi64v.dll" ### Fixed - IniWatcher did not work in portable mode -- service path fix broke other services, now properly fixed, maybe +- service path fix broke other services, now properly fixed, may be - found workaround for the msi installer issue @@ -171,7 +188,7 @@ This project adheres to [Semantic Versioning](http://semver.org/). ### Added - IniWatcher, no more clicking reload, the ini is now reloaded automatically every time it changes - Added Mainanance menu to the Sandbox menu, allowing to install/uninstall and start/stop sandboxie driver, service -- SandMan.exe now is packed with Sbie files and when no sbie is installed acts as a portable installation +- SandMan.exe now is packed with Sbie files and when no sbie is installed acts as a portable instalation - Added option to clean up logs ### Changed @@ -202,7 +219,7 @@ This project adheres to [Semantic Versioning](http://semver.org/). ### Added - "Other" type for the Resource Access Monitor -- added call to StartService to the logged Resources +-- added call to StartService to the logged Resources ### Fixed - fixed "Windows Installer Service could not be accessed" that got introduced with Windows 1903 diff --git a/Sandboxie/apps/com/RpcSs/rpcss.c b/Sandboxie/apps/com/RpcSs/rpcss.c index 02c2a888..6546475c 100644 --- a/Sandboxie/apps/com/RpcSs/rpcss.c +++ b/Sandboxie/apps/com/RpcSs/rpcss.c @@ -466,6 +466,7 @@ _FX int __stdcall WinMain( } } + // todo: xxx /*if (1) { MSG_HEADER req; req.length = sizeof(req); diff --git a/Sandboxie/apps/control/ShellDialog.cpp b/Sandboxie/apps/control/ShellDialog.cpp index 65b2fd37..ca8bf7bb 100644 --- a/Sandboxie/apps/control/ShellDialog.cpp +++ b/Sandboxie/apps/control/ShellDialog.cpp @@ -142,7 +142,7 @@ BOOL CShellDialog::OnInitDialog() CUserSettings &user = CUserSettings::GetInstance(); user.GetBool(_EnableLogonStart, logonstart, TRUE); - user.GetBool(_EnableAutoStart, autostart, TRUE); + user.GetBool(_EnableAutoStart, autostart, FALSE); user.GetBool(_AddDesktopIcon, desktop, TRUE); user.GetBool(_AddQuickLaunchIcon, quicklaunch, TRUE); user.GetBool(_AddContextMenu, contextmenu, TRUE); diff --git a/Sandboxie/common/my_version.h b/Sandboxie/common/my_version.h index 1837584a..54ab1f99 100644 --- a/Sandboxie/common/my_version.h +++ b/Sandboxie/common/my_version.h @@ -20,8 +20,8 @@ #ifndef _MY_VERSION_H #define _MY_VERSION_H -#define MY_VERSION_BINARY 5,43,6 -#define MY_VERSION_STRING "5.43.6" +#define MY_VERSION_BINARY 5,43,7 +#define MY_VERSION_STRING "5.43.7" #define MY_VERSION_COMPAT "5.43.5" // These #defines are used by either Resource Compiler, or by NSIC installer diff --git a/Sandboxie/core/dll/proc.c b/Sandboxie/core/dll/proc.c index 85c1154c..5fb34ced 100644 --- a/Sandboxie/core/dll/proc.c +++ b/Sandboxie/core/dll/proc.c @@ -996,17 +996,6 @@ void *Proc_GetImageFullPath(const WCHAR *lpApplicationName, const WCHAR *lpComma return mybuf; } -#ifndef STARTUPINFOEXW -typedef struct _STARTUPINFOEXA { - STARTUPINFOA StartupInfo; - LPPROC_THREAD_ATTRIBUTE_LIST lpAttributeList; -} STARTUPINFOEXA, *LPSTARTUPINFOEXA; -typedef struct _STARTUPINFOEXW { - STARTUPINFOW StartupInfo; - LPPROC_THREAD_ATTRIBUTE_LIST lpAttributeList; -} STARTUPINFOEXW, *LPSTARTUPINFOEXW; -#endif - // Processes in Windows 10 RS5 will start with the Sandboxie restricted token. // Thus the expected failure of the original call to CreateProcessInternalW doesn't // happen. Proc_CreateProcessInternalW_RS5 handles this case. The main difference diff --git a/Sandboxie/core/drv/api_defs.h b/Sandboxie/core/drv/api_defs.h index 55fb189c..4c038e28 100644 --- a/Sandboxie/core/drv/api_defs.h +++ b/Sandboxie/core/drv/api_defs.h @@ -125,7 +125,7 @@ enum { API_GET_HOME_PATH, API_GET_BLOCKED_DLL, API_QUERY_LICENSE, - API_ACTIVATE_LICENSE, + API_ACTIVATE_LICENSE_DEPRECATED, // deprecated API_OPEN_DEVICE_MAP, API_OPEN_PROCESS, API_QUERY_PROCESS_INFO, diff --git a/Sandboxie/core/drv/file.c b/Sandboxie/core/drv/file.c index 4ad48a13..3093825b 100644 --- a/Sandboxie/core/drv/file.c +++ b/Sandboxie/core/drv/file.c @@ -1833,9 +1833,27 @@ _FX NTSTATUS File_Api_Rename(PROCESS *proc, ULONG64 *parms) info->FileNameLength = name_len; memcpy(info->FileName, name, name_len); - status = NtSetInformationFile( - args->file_handle.val, &IoStatusBlock, - info, info_len, FileRenameInformation); + + FILE_OBJECT *object; + status = ObReferenceObjectByHandle(args->file_handle.val, 0L, *IoFileObjectType, UserMode, (PVOID)&object, NULL); + + if (NT_SUCCESS(status)) { + + HANDLE handle; + status = ObOpenObjectByPointer((PVOID)object, OBJ_FORCE_ACCESS_CHECK | + OBJ_KERNEL_HANDLE, NULL, GENERIC_ALL, *IoFileObjectType, KernelMode, &handle); + + if (NT_SUCCESS(status)) { + + status = ZwSetInformationFile( + handle, &IoStatusBlock, //args->file_handle.val, &IoStatusBlock, + info, info_len, FileRenameInformation); + + ZwClose(handle); + } + + ObDereferenceObject(object); + } // FIXME, we may get STATUS_NOT_SAME_DEVICE, however, in most cases, // this API call is used to rename a file inside a folder, rather diff --git a/Sandboxie/core/svc/sbieiniserver.cpp b/Sandboxie/core/svc/sbieiniserver.cpp index c74ee33b..e7ff9a14 100644 --- a/Sandboxie/core/svc/sbieiniserver.cpp +++ b/Sandboxie/core/svc/sbieiniserver.cpp @@ -1681,7 +1681,7 @@ MSG_HEADER *SbieIniServer::RunSbieCtrl(HANDLE idProcess, bool isSandboxed) ch = towlower(buf[0]); } - if (ch == L'n') { + if (ch != L'y') { status = STATUS_LOGON_NOT_GRANTED; ok = FALSE; } diff --git a/SandboxiePlus/QSbieAPI/Sandboxie/SandBox.cpp b/SandboxiePlus/QSbieAPI/Sandboxie/SandBox.cpp index ece13a24..41a112b5 100644 --- a/SandboxiePlus/QSbieAPI/Sandboxie/SandBox.cpp +++ b/SandboxiePlus/QSbieAPI/Sandboxie/SandBox.cpp @@ -316,7 +316,7 @@ SB_STATUS CSandBox__OsRename(const wstring& SrcPath, const wstring& DestDir, con return SB_ERR(CSandBox::tr("Can't open source path"), status); } - wstring dst_path = L"\\??\\" + DestDir; + wstring dst_path = L"\\??\\" + DestDir + L"\\"; RtlInitUnicodeString(&uni, dst_path.c_str()); InitializeObjectAttributes(&objattrs, &uni, OBJ_CASE_INSENSITIVE, NULL, NULL); diff --git a/SandboxiePlus/QSbieAPI/SbieAPI.cpp b/SandboxiePlus/QSbieAPI/SbieAPI.cpp index d1d4ea48..5605488b 100644 --- a/SandboxiePlus/QSbieAPI/SbieAPI.cpp +++ b/SandboxiePlus/QSbieAPI/SbieAPI.cpp @@ -1371,9 +1371,10 @@ bool CSbieAPI::GetLog() // Forced Processes // -SB_STATUS CSbieAPI::DisableForceProcess(bool Set) +SB_STATUS CSbieAPI::DisableForceProcess(bool Set, int Seconds) { - //m_pGlobalSection->SetNum("ForceDisableSeconds", Seconds); + if(Seconds > 0) + m_pGlobalSection->SetNum("ForceDisableSeconds", Seconds); ULONG uEnable = Set ? TRUE : FALSE; @@ -1403,7 +1404,9 @@ bool CSbieAPI::AreForceProcessDisabled() args->set_flag.val = NULL; // NewState args->get_flag.val = &uEnabled; // OldState - return NT_SUCCESS(m->IoControl(parms)) && uEnabled; + if (!NT_SUCCESS(m->IoControl(parms))) + return false; + return uEnabled; } /////////////////////////////////////////////////////////////////////////////// diff --git a/SandboxiePlus/QSbieAPI/SbieAPI.h b/SandboxiePlus/QSbieAPI/SbieAPI.h index 14a0792f..057a0cbe 100644 --- a/SandboxiePlus/QSbieAPI/SbieAPI.h +++ b/SandboxiePlus/QSbieAPI/SbieAPI.h @@ -119,7 +119,7 @@ public: virtual void ClearPassword(); // Forced Processes - virtual SB_STATUS DisableForceProcess(bool Set); + virtual SB_STATUS DisableForceProcess(bool Set, int Seconds = 0); virtual bool AreForceProcessDisabled(); // Monitor diff --git a/SandboxiePlus/SandMan/Forms/OptionsWindow.ui b/SandboxiePlus/SandMan/Forms/OptionsWindow.ui index ec4444c5..99577d98 100644 --- a/SandboxiePlus/SandMan/Forms/OptionsWindow.ui +++ b/SandboxiePlus/SandMan/Forms/OptionsWindow.ui @@ -614,7 +614,7 @@ If leader processes are defined all others are threated as lingering processes.< - Block network files and folders, unless pecifically opened. + Block network files and folders, unless specifically opened. diff --git a/SandboxiePlus/SandMan/SandMan.cpp b/SandboxiePlus/SandMan/SandMan.cpp index bf67cfcc..1a4d5638 100644 --- a/SandboxiePlus/SandMan/SandMan.cpp +++ b/SandboxiePlus/SandMan/SandMan.cpp @@ -183,6 +183,8 @@ CSandMan::CSandMan(QWidget *parent) m_pNew = m_pMenuFile->addAction(QIcon(":/Actions/NewBox"), tr("Create New Box"), this, SLOT(OnNewBox())); m_pMenuFile->addSeparator(); m_pEmptyAll = m_pMenuFile->addAction(QIcon(":/Actions/EmptyAll"), tr("Terminate All Processes"), this, SLOT(OnEmptyAll())); + m_pDisableForce = m_pMenuFile->addAction(tr("Disable Forced Programs"), this, SLOT(OnDisableForce())); + m_pDisableForce->setCheckable(true); m_pMenuFile->addSeparator(); m_pMaintenance = m_pMenuFile->addMenu(QIcon(":/Actions/Maintenance"), tr("&Maintenance")); m_pConnect = m_pMaintenance->addAction(QIcon(":/Actions/Connect"), tr("Connect"), this, SLOT(OnMaintenance())); @@ -470,6 +472,8 @@ void CSandMan::timerEvent(QTimerEvent* pEvent) { theAPI->ReloadBoxes(); theAPI->UpdateProcesses(m_pKeepTerminated->isChecked()); + + m_pDisableForce->setChecked(theAPI->AreForceProcessDisabled()); } if (m_bIconEmpty != (theAPI->TotalProcesses() == 0)) @@ -651,6 +655,20 @@ void CSandMan::OnEmptyAll() theAPI->TerminateAll(); } +void CSandMan::OnDisableForce() +{ + bool Status = m_pDisableForce->isChecked(); + int Seconds = 0; + if (Status) + { + bool bOK = false; + Seconds = QInputDialog::getInt(this, "Sandboxie-Plus", tr("Please enter the duration for which disable forced programs."), 10, 0, 3600, 1, &bOK); + if (!bOK) + return; + } + theAPI->DisableForceProcess(Status, Seconds); +} + SB_STATUS CSandMan::ConnectSbie() { SB_STATUS Status; diff --git a/SandboxiePlus/SandMan/SandMan.h b/SandboxiePlus/SandMan/SandMan.h index 440042cf..5828643e 100644 --- a/SandboxiePlus/SandMan/SandMan.h +++ b/SandboxiePlus/SandMan/SandMan.h @@ -12,7 +12,7 @@ #define VERSION_MJR 0 #define VERSION_MIN 4 -#define VERSION_REV 2 +#define VERSION_REV 3 #define VERSION_UPD 0 @@ -83,6 +83,7 @@ private slots: void OnNewBox(); void OnEmptyAll(); + void OnDisableForce(); void OnMaintenance(); void OnCleanUp(); @@ -124,6 +125,7 @@ private: QMenu* m_pMenuFile; QAction* m_pNew; QAction* m_pEmptyAll; + QAction* m_pDisableForce; QMenu* m_pMaintenance; QAction* m_pConnect; QAction* m_pDisconnect; diff --git a/SandboxiePlus/SandMan/SbiePlusAPI.cpp b/SandboxiePlus/SandMan/SbiePlusAPI.cpp index c2100fd3..41d0abed 100644 --- a/SandboxiePlus/SandMan/SbiePlusAPI.cpp +++ b/SandboxiePlus/SandMan/SbiePlusAPI.cpp @@ -47,7 +47,14 @@ void CSandBoxPlus::UpdateDetails() { m_bLogApiFound = GetTextList("OpenPipePath").contains("\\Device\\NamedPipe\\LogAPI"); - m_bINetBlocked = GetTextList("ClosedFilePath").contains("InternetAccessDevices"); + m_bINetBlocked = false; + foreach(const QString& Entry, GetTextList("ClosedFilePath")) + { + if (Entry.contains("InternetAccessDevices")) { + m_bINetBlocked = true; + break; + } + } m_bSharesAllowed = GetBool("BlockNetworkFiles", true) == false; @@ -121,9 +128,9 @@ void CSandBoxPlus::SetLogApi(bool bEnable) void CSandBoxPlus::SetINetBlock(bool bEnable) { if (bEnable) - DelValue("ClosedFilePath", "!,InternetAccessDevices"); + InsertText("ClosedFilePath", "!,InternetAccessDevices"); else - InsertText("ClosedFilePath", "InternetAccessDevices"); + DelValue("ClosedFilePath", "!,InternetAccessDevices"); } void CSandBoxPlus::SetAllowShares(bool bEnable) diff --git a/SandboxiePlus/SandMan/Windows/OptionsWindow.cpp b/SandboxiePlus/SandMan/Windows/OptionsWindow.cpp index a6c0db11..9e8b2898 100644 --- a/SandboxiePlus/SandMan/Windows/OptionsWindow.cpp +++ b/SandboxiePlus/SandMan/Windows/OptionsWindow.cpp @@ -432,7 +432,7 @@ void COptionsWindow::LoadGroups() if (GroupName.length() > 2) GroupName = GroupName.mid(1, GroupName.length() - 2); pItem->setText(0, GroupName); - for (int i = 1; i < Entries.count(); i++) + for (int i = 0; i < Entries.count(); i++) { QTreeWidgetItem* pSubItem = new QTreeWidgetItem(); SetProgramItem(Entries[i], pSubItem, 0); @@ -864,6 +864,7 @@ void COptionsWindow::SetAccessEntry(EAccessType Type, const QString& Program, EA { if (GetAccessEntry(Type, Program, Mode, Path) != NULL) return; // already set + m_AccessChanged = true; AddAccessEntry(Type, Mode, Program, Path); } @@ -1070,7 +1071,7 @@ void COptionsWindow::SaveAccessList() int Mode = pItem->data(2, Qt::UserRole).toInt(); QString Program = pItem->data(1, Qt::UserRole).toString(); QString Value = pItem->data(3, Qt::UserRole).toString(); - if (Program.isEmpty()) + if (!Program.isEmpty()) Value.prepend(Program + ","); AccessMap.insertMulti(MakeAccessStr((EAccessType)Type, (EAccessMode)Mode), Value); }