1
0
mirror of https://gitea.tendokyu.moe/Dniel97/segatools.git synced 2025-02-07 23:01:28 +01:00

Merge pull request 'Add automatically apply OpenSSL patch for Intel Gen 10+ CPUs' (#43) from kagaminehaku/segatools:develop into develop

Reviewed-on: https://gitea.tendokyu.moe/Dniel97/segatools/pulls/43
This commit is contained in:
Dniel97 2024-12-23 19:43:47 +00:00
commit b4f5cdbe59
8 changed files with 127 additions and 0 deletions

View File

@ -600,3 +600,16 @@ Default: Empty string
Configure the location of the "Option" data mount point. This mount point is
optional (hence the name, probably) and contains directories which contain
minor over-the-air content updates.
## `[openssl]`
Enable or disable the application of the OpenSSL patch for Intel Gen 10 or newer CPUs.
### `enable`
Default: `1`
Enable the patch automatically sets the OPENSSL_ia32cap variable in the user's environment
table if the CPU meets the requirements. This setting must be enabled on PCs with
Intel Gen 10 or newer CPUs to ensure the game runs properly, but it's ok to leave enabled
on other CPUs since the patch will not run if the CPU requirements are not met.

View File

@ -23,6 +23,7 @@
#include "platform/platform.h"
#include "platform/vfs.h"
#include "platform/system.h"
#include "platform/opensslpatch.h"
void platform_config_load(struct platform_config *cfg, const wchar_t *filename)
{
@ -41,6 +42,7 @@ void platform_config_load(struct platform_config *cfg, const wchar_t *filename)
nusec_config_load(&cfg->nusec, filename);
vfs_config_load(&cfg->vfs, filename);
system_config_load(&cfg->system, filename);
openssl_patch_config_load(&cfg->openssl, filename);
}
void amvideo_config_load(struct amvideo_config *cfg, const wchar_t *filename)
@ -361,3 +363,16 @@ void epay_config_load(struct epay_config *cfg, const wchar_t *filename)
cfg->enable = GetPrivateProfileIntW(L"epay", L"enable", 1, filename);
}
void openssl_patch_config_load(struct openssl_patch_config *cfg, const wchar_t *filename)
{
assert(cfg != NULL);
assert(filename != NULL);
cfg->enable = GetPrivateProfileIntW(
L"openssl",
L"enable",
1,
filename
);
}

View File

@ -36,3 +36,4 @@ void nusec_config_load(struct nusec_config *cfg, const wchar_t *filename);
void pcbid_config_load(struct pcbid_config *cfg, const wchar_t *filename);
void vfs_config_load(struct vfs_config *cfg, const wchar_t *filename);
void system_config_load(struct system_config *cfg, const wchar_t *filename);
void openssl_patch_config_load(struct openssl_patch_config *cfg, const wchar_t *filename);

View File

@ -36,5 +36,7 @@ platform_lib = static_library(
'vfs.h',
'system.c',
'system.h',
'opensslpatch.c',
'opensslpatch.h',
],
)

80
platform/opensslpatch.c Normal file
View File

@ -0,0 +1,80 @@
#include <windows.h>
#include <stdio.h>
#include <string.h>
#include <intrin.h>
#include "util/dprintf.h"
#include "platform/opensslpatch.h"
int check_cpu() {
int cpui[4] = {0};
__cpuid(cpui, 0);
int nIds_ = cpui[0];
char vendor[0x20] = {0};
*((int*)vendor) = cpui[1];
*((int*)(vendor + 4)) = cpui[3];
*((int*)(vendor + 8)) = cpui[2];
int isIntel = (strcmp(vendor, "GenuineIntel") == 0);
if (isIntel && nIds_ >= 7) {
__cpuidex(cpui, 7, 0);
return (cpui[1] & (1 << 29)) != 0;
}
return 0;
}
static int is_env_variable_set(const char* variablename, const char* expectedvalue) {
char currentvalue[256];
DWORD length = GetEnvironmentVariableA(variablename, currentvalue, sizeof(currentvalue));
if (length > 0 && length < sizeof(currentvalue)) {
return strcmp(currentvalue, expectedvalue) == 0;
}
return 0;
}
static void openssl_patch(void) {
const char* variablename = "OPENSSL_ia32cap";
const char* variablevalue = "~0x20000000";
if (is_env_variable_set(variablename, variablevalue)) {
return;
}
HKEY hKey;
if (RegOpenKeyExA(HKEY_CURRENT_USER, "Environment", 0, KEY_SET_VALUE, &hKey) == ERROR_SUCCESS) {
if (RegSetValueExA(hKey, variablename, 0, REG_SZ, (const BYTE*)variablevalue, strlen(variablevalue) + 1) == ERROR_SUCCESS) {
dprintf("OpenSSL Patch: Applied successfully. User environment variable %s set to %s\n", variablename, variablevalue);
SendMessageTimeoutA(HWND_BROADCAST, WM_SETTINGCHANGE, 0, (LPARAM)"Environment", SMTO_ABORTIFHUNG, 5000, NULL);
dprintf(
"Please close this windows and reopen the game to enjoy.\n"
);
ExitProcess(0);
} else {
dprintf("OpenSSL Patch: Error: Failed to set the user environment variable.\n");
}
RegCloseKey(hKey);
} else {
dprintf("OpenSSL Patch: Error: Failed to open the user environment registry key.\n");
}
}
HRESULT openssl_patch_apply(const struct openssl_patch_config *cfg) {
HRESULT hr;
assert(cfg != NULL);
if (!cfg->enable) {
return S_FALSE;
}
if (check_cpu()) {
openssl_patch();
}
return S_OK;
}

7
platform/opensslpatch.h Normal file
View File

@ -0,0 +1,7 @@
#pragma once
struct openssl_patch_config {
int enable;
};
HRESULT openssl_patch_apply(const struct openssl_patch_config *cfg);

View File

@ -14,6 +14,7 @@
#include "platform/platform.h"
#include "platform/vfs.h"
#include "platform/system.h"
#include "platform/opensslpatch.h"
HRESULT platform_hook_init(
const struct platform_config *cfg,
@ -28,6 +29,12 @@ HRESULT platform_hook_init(
assert(platform_id != NULL);
assert(redir_mod != NULL);
hr = openssl_patch_apply(&cfg->openssl);
if (FAILED(hr)) {
return hr;
}
hr = amvideo_hook_init(&cfg->amvideo, redir_mod);
if (FAILED(hr)) {

View File

@ -14,6 +14,7 @@
#include "platform/pcbid.h"
#include "platform/vfs.h"
#include "platform/system.h"
#include "platform/opensslpatch.h"
struct platform_config {
struct amvideo_config amvideo;
@ -28,6 +29,7 @@ struct platform_config {
struct nusec_config nusec;
struct vfs_config vfs;
struct system_config system;
struct openssl_patch_config openssl;
};
HRESULT platform_hook_init(