This commit is contained in:
DavidXanatos 2023-07-02 18:09:18 +02:00
parent 7dd578beba
commit 1978e2c7a7
11 changed files with 250 additions and 147 deletions

View File

@ -25,6 +25,8 @@ This project adheres to [Semantic Versioning](http://semver.org/).
### Changed ### Changed
- setup wizard has now a dedicated update configuration page - setup wizard has now a dedicated update configuration page
- split the support page into Sandboxie Support and Sandboxie Updater tabs - split the support page into Sandboxie Support and Sandboxie Updater tabs
- when the troubleshooting.7z is available the script engine is use to match comaptybility templates
- this allows a better granularity in template selection, the script AppCompatibility.js is used
### Fixed ### Fixed
- fixed uninstall issue in the Sandboxie Classic installer [d1863ff](https://github.com/sandboxie-plus/Sandboxie/commit/d1863ffadfe105c695de71c9e841c2fd568116fe) - fixed uninstall issue in the Sandboxie Classic installer [d1863ff](https://github.com/sandboxie-plus/Sandboxie/commit/d1863ffadfe105c695de71c9e841c2fd568116fe)

View File

@ -3668,6 +3668,17 @@ Tmpl.Title=Yubikey Authentication
Tmpl.Class=Security Tmpl.Class=Security
OpenIpcPath=\RPC Control\keysvc OpenIpcPath=\RPC Control\keysvc
[Template_Chrome_KB5027231_fix]
Tmpl.Title=Chromium fix for windows 11 with KB5027231
Tmpl.Class=WebBrowser
Tmpl.Scan=x
#Tmpl.Scan=u
#Tmpl.ScanUpd=KB5027231
Tmpl.ScanScript=if(system.version().major != 11) return false; return system.checkUpdates("KB5027231");
ClosedKeyPath=<Template_Chromes>,HKEY_CURRENT_USER\Software\Microsoft\Windows\Shell\Associations\UrlAssociations\http\UserChoice
ClosedKeyPath=<Template_Chromes>,HKEY_CURRENT_USER\Software\Microsoft\Windows\Shell\Associations\UrlAssociations\https\UserChoice
ProcessGroup=<Template_Chromes>,chrome.exe

View File

@ -11,9 +11,9 @@ class QSBIEAPI_EXPORT CSbieTemplates : public QObject
public: public:
CSbieTemplates(class CSbieAPI* pAPI, QObject* paretn = 0); CSbieTemplates(class CSbieAPI* pAPI, QObject* paretn = 0);
void RunCheck(); virtual void RunCheck();
void SetCheckResult(const QStringList& Result); virtual void SetCheckResult(const QStringList& Result);
bool GetCheckState(); virtual bool GetCheckState();
enum EStates enum EStates
{ {
@ -24,7 +24,7 @@ public:
eConfigured = eEnabled | eDisabled eConfigured = eEnabled | eDisabled
}; };
void Reset(); virtual void Reset();
QStringList GetObjects(); QStringList GetObjects();
QStringList GetClasses(); QStringList GetClasses();

View File

@ -42,7 +42,7 @@ CJSEngineExt* CJSEngineExt::getEngineByHandle(void* handle)
static QV4::ReturnedValue printCall(const QV4::FunctionObject* b, const QV4::Value* v, const QV4::Value* argv, int argc); static QV4::ReturnedValue printCall(const QV4::FunctionObject* b, const QV4::Value* v, const QV4::Value* argv, int argc);
static QV4::ReturnedValue debuggerCall(const QV4::FunctionObject* b, const QV4::Value* v, const QV4::Value* argv, int argc); static QV4::ReturnedValue debuggerCall(const QV4::FunctionObject* b, const QV4::Value* v, const QV4::Value* argv, int argc);
static QV4::ReturnedValue evalCall(const QV4::FunctionObject* b, const QV4::Value* v, const QV4::Value* argv, int argc); //static QV4::ReturnedValue evalCall(const QV4::FunctionObject* b, const QV4::Value* v, const QV4::Value* argv, int argc);
CJSEngineExt::CJSEngineExt(QObject* parent) CJSEngineExt::CJSEngineExt(QObject* parent)
: QJSEngine(parent) : QJSEngine(parent)
@ -54,7 +54,7 @@ CJSEngineExt::CJSEngineExt(QObject* parent)
// provide ability to invoke the debugger // provide ability to invoke the debugger
scope.engine->globalObject->defineDefaultProperty(QStringLiteral("_debugger"), debuggerCall); scope.engine->globalObject->defineDefaultProperty(QStringLiteral("_debugger"), debuggerCall);
// overwrite the eval function with our own copy which traces the scripts // overwrite the eval function with our own copy which traces the scripts
scope.engine->globalObject->defineDefaultProperty(QStringLiteral("eval"), evalCall); //scope.engine->globalObject->defineDefaultProperty(QStringLiteral("eval"), evalCall);
QMutexLocker locker(&g_engineMutex); QMutexLocker locker(&g_engineMutex);
g_engineMap.insert(handle(), this); g_engineMap.insert(handle(), this);
@ -112,9 +112,9 @@ QV4::ReturnedValue debuggerCall(const QV4::FunctionObject* b, const QV4::Value*
return QV4::Encode::undefined(); return QV4::Encode::undefined();
} }
QV4::ReturnedValue evalCall(const QV4::FunctionObject* b, const QV4::Value* v, const QV4::Value* argv, int argc) //QV4::ReturnedValue evalCall(const QV4::FunctionObject* b, const QV4::Value* v, const QV4::Value* argv, int argc)
{ //{
// not implemented // // not implemented
//
return QV4::Encode::undefined(); // return QV4::Encode::undefined();
} //}

View File

@ -18,8 +18,6 @@ typedef long NTSTATUS;
#define MAX_VALUE_NAME 16383 #define MAX_VALUE_NAME 16383
#define MAX_VALUE_DATA 1024000 #define MAX_VALUE_DATA 1024000
#include <comdef.h>
#include <wuapi.h>
JSysObject::JSysObject(CBoxEngine* pEngine) JSysObject::JSysObject(CBoxEngine* pEngine)
: m_pEngine(pEngine) : m_pEngine(pEngine)
@ -495,121 +493,15 @@ QJSValue JSysObject::version()
QJSValue JSysObject::enumUpdates() QJSValue JSysObject::enumUpdates()
{ {
QVariantMap out; return m_pEngine->m_pEngine->toScriptValue(theGUI->GetCompat()->GetUpdates());
IUpdateSession *updateSession = NULL;
IUpdateSearcher *updateSearcher = NULL;
ISearchResult *searchResult = NULL;
IUpdateCollection *updates = NULL;
HRESULT res;
int ret = 1;
res = CoInitializeEx(NULL, 0);
if (FAILED(res)) {
out["error"] = "Failed to initialize COM";
goto cleanup;
}
res = CoCreateInstance(CLSID_UpdateSession, NULL, CLSCTX_INPROC_SERVER, IID_IUpdateSession, (LPVOID *)&updateSession);
if (FAILED(res)) {
out["error"] = "Failed to create update session";
goto cleanup;
}
res = updateSession->CreateUpdateSearcher(&updateSearcher);
if (FAILED(res)) {
out["error"] = "Failed to create update searcher";
goto cleanup;
}
res = updateSearcher->put_IncludePotentiallySupersededUpdates(VARIANT_TRUE);
if (FAILED(res)) {
out["error"] = "Failed to set search options";
goto cleanup;
}
{BSTR criteria = SysAllocString(L"IsInstalled=1"); // or IsHidden=1
res = updateSearcher->Search(criteria, &searchResult);
SysFreeString(criteria);}
if (FAILED(res)) {
out["error"] = "Failed to search for updates";
goto cleanup;
}
res = searchResult->get_Updates(&updates);
if (FAILED(res)) {
out["error"] = "Failed to retrieve update list from search result";
goto cleanup;
}
LONG updateCount;
res = updates->get_Count(&updateCount);
if (FAILED(res)) {
out["error"] = "Failed to get update count";
goto cleanup;
}
{QVariantList list;
for (LONG i = 0L; i < updateCount; ++i)
{
QVariantMap entry;
IUpdate* update = NULL;
res = updates->get_Item(i, &update);
if (FAILED(res))
entry["error"] = "Failed to get update item";
else
{
IStringCollection* updateKBIDs = NULL;
res = update->get_KBArticleIDs(&updateKBIDs);
if (SUCCEEDED(res)) {
LONG kbIDCount;
res = updateKBIDs->get_Count(&kbIDCount);
if (SUCCEEDED(res)) {
QVariantList kb;
for (LONG j = 0L; j < kbIDCount; ++j) {
BSTR kbID;
res = updateKBIDs->get_Item(j, &kbID);
if (FAILED(res))
continue;
kb.append("KB" + QString::fromWCharArray(kbID));
SysFreeString(kbID);
}
entry["kb"] = kb;
}
updateKBIDs->Release();
}
BSTR updateTitle;
res = update->get_Title(&updateTitle);
if (FAILED(res))
entry["error"] = "Failed to get update title";
else {
entry["title"] = QString::fromWCharArray(updateTitle);
SysFreeString(updateTitle);
}
update->Release();
}
list.append(entry);
}
out["list"] = list;}
cleanup:
if (updates != NULL) updates->Release();
if (searchResult != NULL) searchResult->Release();
if (updateSearcher != NULL) updateSearcher->Release();
if (updateSession != NULL) updateSession->Release();
CoUninitialize();
return m_pEngine->m_pEngine->toScriptValue(out);
} }
// //
void JSysObject::resetData()
// todo: add sync to usage of GetCompat() {
theGUI->GetCompat()->Reset();
}
QJSValue JSysObject::enumClasses() QJSValue JSysObject::enumClasses()
{ {
@ -666,3 +558,9 @@ QJSValue JSysObject::checkObjects(const QString& value)
{ {
return theGUI->GetCompat()->CheckObjects(value); return theGUI->GetCompat()->CheckObjects(value);
} }
QJSValue JSysObject::checkUpdates(const QString& value)
{
return theGUI->GetCompat()->CheckUpdates(value);
}

View File

@ -34,13 +34,15 @@ public:
// OS // OS
static QVariantMap GetOSVersion(); static QVariantMap GetOSVersion();
Q_INVOKABLE QJSValue version(); Q_INVOKABLE QJSValue version();
Q_INVOKABLE QJSValue enumUpdates(); // this can take quite a while
// //
Q_INVOKABLE void resetData();
Q_INVOKABLE QJSValue enumClasses(); Q_INVOKABLE QJSValue enumClasses();
Q_INVOKABLE QJSValue enumServices(); Q_INVOKABLE QJSValue enumServices();
Q_INVOKABLE QJSValue enumProducts(); Q_INVOKABLE QJSValue enumProducts();
Q_INVOKABLE QJSValue enumObjects(); Q_INVOKABLE QJSValue enumObjects();
Q_INVOKABLE QJSValue enumUpdates(); // this can take quite a while
Q_INVOKABLE QJSValue expandPath(const QString& path); Q_INVOKABLE QJSValue expandPath(const QString& path);
Q_INVOKABLE QJSValue checkFile(const QString& value); Q_INVOKABLE QJSValue checkFile(const QString& value);
@ -49,9 +51,10 @@ public:
Q_INVOKABLE QJSValue checkServices(const QString& value); Q_INVOKABLE QJSValue checkServices(const QString& value);
Q_INVOKABLE QJSValue checkProducts(const QString& value); Q_INVOKABLE QJSValue checkProducts(const QString& value);
Q_INVOKABLE QJSValue checkObjects(const QString& value); Q_INVOKABLE QJSValue checkObjects(const QString& value);
Q_INVOKABLE QJSValue checkUpdates(const QString& value);
protected: protected:
CBoxEngine* m_pEngine; CBoxEngine* m_pEngine;
}; };

View File

@ -190,7 +190,7 @@ CSandMan::CSandMan(QWidget *parent)
m_pBoxBorder = new CBoxBorder(theAPI, this); m_pBoxBorder = new CBoxBorder(theAPI, this);
m_SbieTemplates = new CSbieTemplates(theAPI, this); m_SbieTemplates = new CSbieTemplatesEx(theAPI, this);

View File

@ -19,7 +19,7 @@
class CSbieView; class CSbieView;
class CFileView; class CFileView;
class CBoxBorder; class CBoxBorder;
class CSbieTemplates; class CSbieTemplatesEx;
class CTraceView; class CTraceView;
class CAddonManager; class CAddonManager;
@ -42,7 +42,7 @@ public:
CSandMan(QWidget *parent = Q_NULLPTR); CSandMan(QWidget *parent = Q_NULLPTR);
virtual ~CSandMan(); virtual ~CSandMan();
CSbieTemplates* GetCompat() { return m_SbieTemplates; } CSbieTemplatesEx* GetCompat() { return m_SbieTemplates; }
void CheckCompat(QObject* receiver, const char* member); void CheckCompat(QObject* receiver, const char* member);
CAddonManager* GetAddonManager() { return m_AddonManager; } CAddonManager* GetAddonManager() { return m_AddonManager; }
@ -132,7 +132,7 @@ protected:
bool m_bConnectPending; bool m_bConnectPending;
bool m_bStopPending; bool m_bStopPending;
CBoxBorder* m_pBoxBorder; CBoxBorder* m_pBoxBorder;
CSbieTemplates* m_SbieTemplates; CSbieTemplatesEx* m_SbieTemplates;
CAddonManager* m_AddonManager; CAddonManager* m_AddonManager;
QMap<CSbieProgress*, QPair<CSbieProgressPtr, QPointer<QWidget>>> m_pAsyncProgress; QMap<CSbieProgress*, QPair<CSbieProgressPtr, QPointer<QWidget>>> m_pAsyncProgress;

View File

@ -1098,3 +1098,152 @@ QString CSandBoxPlus::GetFullCommand(const QString& Command)
// FullCmd.insert(1, m_FilePath); // FullCmd.insert(1, m_FilePath);
return FullCmd.replace("%BoxRoot%", m_FilePath, Qt::CaseInsensitive); return FullCmd.replace("%BoxRoot%", m_FilePath, Qt::CaseInsensitive);
} }
///////////////////////////////////////////////////////////////////////////////
// CSbieTemplatesEx
//
#include <ntstatus.h>
#define WIN32_NO_STATUS
typedef long NTSTATUS;
#include <Windows.h>
//#include <Winternl.h>
#include "..\..\Sandboxie\common\win32_ntddk.h"
#define MAX_KEY_NAME 255
#define MAX_VALUE_NAME 16383
#define MAX_VALUE_DATA 1024000
#include <comdef.h>
#include <wuapi.h>
void CSbieTemplatesEx::CollectUpdates()
{
IUpdateSession* updateSession = NULL;
IUpdateSearcher* updateSearcher = NULL;
ISearchResult* searchResult = NULL;
IUpdateCollection* updates = NULL;
HRESULT res;
res = CoInitializeEx(NULL, 0);
if (FAILED(res)) {
theGUI->OnLogMessage(tr("Failed to initialize COM"));
goto cleanup;
}
res = CoCreateInstance(CLSID_UpdateSession, NULL, CLSCTX_INPROC_SERVER, IID_IUpdateSession, (LPVOID*)&updateSession);
if (FAILED(res)) {
theGUI->OnLogMessage(tr("Failed to create update session"));
goto cleanup;
}
res = updateSession->CreateUpdateSearcher(&updateSearcher);
if (FAILED(res)) {
theGUI->OnLogMessage(tr("Failed to create update searcher"));
goto cleanup;
}
res = updateSearcher->put_IncludePotentiallySupersededUpdates(VARIANT_TRUE);
if (FAILED(res)) {
theGUI->OnLogMessage(tr("Failed to set search options"));
goto cleanup;
}
{BSTR criteria = SysAllocString(L"IsInstalled=1"); // or IsHidden=1
res = updateSearcher->Search(criteria, &searchResult);
SysFreeString(criteria); }
if (FAILED(res)) {
theGUI->OnLogMessage(tr("Failed to search for updates"));
goto cleanup;
}
res = searchResult->get_Updates(&updates);
if (FAILED(res)) {
theGUI->OnLogMessage(tr("Failed to retrieve update list from search result"));
goto cleanup;
}
LONG updateCount;
res = updates->get_Count(&updateCount);
if (FAILED(res)) {
theGUI->OnLogMessage(tr("Failed to get update count"));
goto cleanup;
}
for (LONG i = 0L; i < updateCount; ++i)
{
QVariantMap entry;
IUpdate* update = NULL;
res = updates->get_Item(i, &update);
if (!FAILED(res))
{
IStringCollection* updateKBIDs = NULL;
res = update->get_KBArticleIDs(&updateKBIDs);
if (SUCCEEDED(res)) {
LONG kbIDCount;
res = updateKBIDs->get_Count(&kbIDCount);
if (SUCCEEDED(res)) {
QVariantList kb;
for (LONG j = 0L; j < kbIDCount; ++j) {
BSTR kbID;
res = updateKBIDs->get_Item(j, &kbID);
if (FAILED(res))
continue;
kb.append("KB" + QString::fromWCharArray(kbID));
SysFreeString(kbID);
}
entry["kb"] = kb;
}
updateKBIDs->Release();
}
BSTR updateTitle;
res = update->get_Title(&updateTitle);
if (!FAILED(res)) {
entry["title"] = QString::fromWCharArray(updateTitle);
SysFreeString(updateTitle);
}
update->Release();
}
m_Updates.append(entry);
}
cleanup:
if (updates != NULL) updates->Release();
if (searchResult != NULL) searchResult->Release();
if (updateSearcher != NULL) updateSearcher->Release();
if (updateSession != NULL) updateSession->Release();
CoUninitialize();
}
void CSbieTemplatesEx::Reset()
{
CSbieTemplates::Reset();
m_Updates.clear();
}
QList<QVariantMap> CSbieTemplatesEx::GetUpdates()
{
if (m_Updates.isEmpty())
CollectUpdates();
return m_Updates;
}
bool CSbieTemplatesEx::CheckUpdates(const QString& value)
{
if (m_Updates.isEmpty())
CollectUpdates();
auto I = std::find_if(m_Updates.begin(), m_Updates.end(), [value](const QVariantMap& cur)->bool {
return cur["kb"].toStringList().contains(value, Qt::CaseInsensitive);
});
bool bRet = (I != m_Updates.end());
return bRet;
}

View File

@ -1,6 +1,7 @@
#pragma once #pragma once
#include "../QSbieAPI/SbieAPI.h" #include "../QSbieAPI/SbieAPI.h"
#include "../QSbieAPI/Sandboxie/SbieTemplates.h"
#include "BoxJob.h" #include "BoxJob.h"
enum ESbieExMsgCodes enum ESbieExMsgCodes
@ -241,3 +242,26 @@ protected:
bool m_NoForce; bool m_NoForce;
QRgb m_BoxColor; QRgb m_BoxColor;
}; };
///////////////////////////////////////////////////////////////////////////////
// CSbieTemplatesEx
//
class CSbieTemplatesEx : public CSbieTemplates
{
Q_OBJECT
public:
CSbieTemplatesEx(class CSbieAPI* pAPI, QObject* paretn = 0)
:CSbieTemplates(pAPI, paretn) {}
virtual void Reset();
QList<QVariantMap> GetUpdates();
bool CheckUpdates(const QString& Value);
protected:
void CollectUpdates();
QList<QVariantMap> m_Updates;
};

View File

@ -1,5 +1,5 @@
/* /*
* group: system * group: system
* name: Check for known conflicts * name: Check for known conflicts
* description: Box Engine test script ... * description: Box Engine test script ...
* *
@ -20,20 +20,31 @@ function checkTemplate(name)
{ {
let template = sbie.getTemplate(name); let template = sbie.getTemplate(name);
let title = template.getIniValue('Tmpl.Title'); //let title = template.getIniValue('Tmpl.Title');
let scanScript = template.getIniValue('Tmpl.ScanScript');
if(scanScript){
let ret = false;
try{
ret = eval('(()=>{' + scanScript + '})()');
} catch (error) {
sbie.logMessage("error:" + error);
}
return ret;
}
let scan = template.getIniValue('Tmpl.Scan'); let scan = template.getIniValue('Tmpl.Scan');
let scanIpc = (scan.indexOf('i') != -1); let scanIpc = (scan.indexOf('i') != -1);
let scanWin = (scan.indexOf('w') != -1); let scanWin = (scan.indexOf('w') != -1);
let scanSvc = (scan.indexOf('s') != -1); let scanSvc = (scan.indexOf('s') != -1);
if (!(scanIpc || scanWin || scanSvc)) if (!(scanIpc || scanWin || scanSvc))
return false; return false;
let settings = template.getIniSection(); let settings = template.getIniSection();
let keys = Object.keys(settings); let keys = Object.keys(settings);
for(let i=0; i < keys.length; i++) for(let i=0; i < keys.length; i++)
{ {
let setting = keys[i]; let setting = keys[i];
for(let j = 0; j < settings[setting].length; j++) for(let j = 0; j < settings[setting].length; j++)
@ -83,10 +94,15 @@ function checkTemplate(name)
if (system.checkFile(system.expandPath(value))) if (system.checkFile(system.expandPath(value)))
return true; return true;
} }
//else if (scanUpd && setting == "Tmpl.ScanUpd")
//{
// if (system.checkUpdates(value))
// return true;
//}
} }
} }
return false; return false;
} }