Sfoglia il codice sorgente

libobs: Log which security software is in use

(Windows only)
3rd party antivirus / firewalls cause a large number of issues in OBS.
Logging which products are installed will help narrow down potential
issues when users ask for help and include their log files.

Closes jp9000/obs-studio#1124
Richard Stanway 7 anni fa
parent
commit
8395cfcbce
1 ha cambiato i file con 127 aggiunte e 0 eliminazioni
  1. 127 0
      libobs/obs-windows.c

+ 127 - 0
libobs/obs-windows.c

@@ -23,6 +23,8 @@
 #include "obs-internal.h"
 
 #include <windows.h>
+#include <wscapi.h>
+#include <iwscapi.h>
 
 static uint32_t win_ver = 0;
 
@@ -247,6 +249,130 @@ static void log_gaming_features(void)
 	}
 }
 
+static const char *get_str_for_state(int state)
+{
+	switch (state) {
+	case WSC_SECURITY_PRODUCT_STATE_ON:
+		return "enabled";
+	case WSC_SECURITY_PRODUCT_STATE_OFF:
+		return "disabled";
+	case WSC_SECURITY_PRODUCT_STATE_SNOOZED:
+		return "temporarily disabled";
+	case WSC_SECURITY_PRODUCT_STATE_EXPIRED:
+		return "expired";
+	default:
+		return "unknown";
+	}
+}
+
+static const char *get_str_for_type(int type)
+{
+	switch (type) {
+	case WSC_SECURITY_PROVIDER_ANTIVIRUS:
+		return "AV";
+	case WSC_SECURITY_PROVIDER_FIREWALL:
+		return "FW";
+	case WSC_SECURITY_PROVIDER_ANTISPYWARE:
+		return "ASW";
+	default:
+		return "unknown";
+	}
+}
+
+static void log_security_products_by_type(IWSCProductList *prod_list, int type)
+{
+	HRESULT hr;
+	LONG count = 0;
+	IWscProduct *prod;
+	BSTR name;
+	WSC_SECURITY_PRODUCT_STATE prod_state;
+
+	hr = prod_list->lpVtbl->Initialize(prod_list, type);
+
+	if (FAILED(hr))
+		return;
+
+	hr = prod_list->lpVtbl->get_Count(prod_list, &count);
+	if (FAILED(hr)) {
+		prod_list->lpVtbl->Release(prod_list);
+		return;
+	}
+
+	for (int i = 0; i < count; i++) {
+		hr = prod_list->lpVtbl->get_Item(prod_list, i, &prod);
+		if (FAILED(hr))
+			continue;
+
+		hr = prod->lpVtbl->get_ProductName(prod, &name);
+		if (FAILED(hr))
+			continue;
+
+		hr = prod->lpVtbl->get_ProductState(prod, &prod_state);
+		if (FAILED(hr)) {
+			SysFreeString(name);
+			continue;
+		}
+
+		blog(LOG_INFO, "\t%S: %s (%s)", name,
+				get_str_for_state(prod_state),
+				get_str_for_type(type));
+
+		SysFreeString(name);
+		prod->lpVtbl->Release(prod);
+	}
+
+	prod_list->lpVtbl->Release(prod_list);
+}
+
+static void log_security_products(void)
+{
+	IWSCProductList *prod_list = NULL;
+	HMODULE h_wsc;
+	HRESULT hr;
+
+	/* We load the DLL rather than import wcsapi.lib because the clsid /
+	 * iid only exists on Windows 8 or higher. */
+
+	h_wsc = LoadLibraryW(L"wscapi.dll");
+	if (!h_wsc)
+		return;
+
+	const CLSID *prod_list_clsid =
+		(const CLSID *)GetProcAddress(h_wsc, "CLSID_WSCProductList");
+	const IID *prod_list_iid =
+		(const IID *)GetProcAddress(h_wsc, "IID_IWSCProductList");
+
+	if (prod_list_clsid && prod_list_iid) {
+		blog(LOG_INFO, "Sec. Software Status:");
+
+		hr = CoCreateInstance(prod_list_clsid, NULL,
+				CLSCTX_INPROC_SERVER, prod_list_iid,
+				&prod_list);
+		if (!FAILED(hr)) {
+			log_security_products_by_type(prod_list,
+					WSC_SECURITY_PROVIDER_ANTIVIRUS);
+		}
+
+		hr = CoCreateInstance(prod_list_clsid, NULL,
+				CLSCTX_INPROC_SERVER, prod_list_iid,
+				&prod_list);
+		if (!FAILED(hr)) {
+			log_security_products_by_type(prod_list,
+					WSC_SECURITY_PROVIDER_FIREWALL);
+		}
+
+		hr = CoCreateInstance(prod_list_clsid, NULL,
+				CLSCTX_INPROC_SERVER, prod_list_iid,
+				&prod_list);
+		if (!FAILED(hr)) {
+			log_security_products_by_type(prod_list,
+					WSC_SECURITY_PROVIDER_ANTISPYWARE);
+		}
+	}
+
+	FreeLibrary(h_wsc);
+}
+
 void log_system_info(void)
 {
 	struct win_version_info ver;
@@ -261,6 +387,7 @@ void log_system_info(void)
 	log_admin_status();
 	log_aero();
 	log_gaming_features();
+	log_security_products();
 }