forked from Dniel97/segatools
cxb: server support added, bugfixes, thanks @Midorica
This commit is contained in:
parent
2590e749ca
commit
097b74d849
@ -1,6 +1,6 @@
|
|||||||
# Segatools
|
# Segatools
|
||||||
|
|
||||||
Version: `2024-02-27`
|
Version: `2024-03-13`
|
||||||
|
|
||||||
Loaders and hardware emulators for SEGA games that run on the Nu and ALLS platforms.
|
Loaders and hardware emulators for SEGA games that run on the Nu and ALLS platforms.
|
||||||
|
|
||||||
@ -8,7 +8,9 @@ Loaders and hardware emulators for SEGA games that run on the Nu and ALLS platfo
|
|||||||
|
|
||||||
* CHUNITHM
|
* CHUNITHM
|
||||||
* up to [CHUNITHM PARADISE LOST](doc/chunihook.md)
|
* up to [CHUNITHM PARADISE LOST](doc/chunihook.md)
|
||||||
* starting from CHUNITHM NEW!!
|
* starting from CHUNITHM NEW!!
|
||||||
|
* crossbeats REV.
|
||||||
|
* up to crossbeats REV. SUNRISE
|
||||||
* Initial D
|
* Initial D
|
||||||
* [Initial D Arcade Stage Zero](doc/idzhook.md)
|
* [Initial D Arcade Stage Zero](doc/idzhook.md)
|
||||||
* Initial D THE ARCADE
|
* Initial D THE ARCADE
|
||||||
|
@ -68,7 +68,6 @@ static void aime_io_config_read(
|
|||||||
cfg->felica_path,
|
cfg->felica_path,
|
||||||
_countof(cfg->felica_path),
|
_countof(cfg->felica_path),
|
||||||
filename);
|
filename);
|
||||||
// dprintf("NFC: felicaPath GetLastError %lx\n", GetLastError());
|
|
||||||
|
|
||||||
cfg->felica_gen = GetPrivateProfileIntW(
|
cfg->felica_gen = GetPrivateProfileIntW(
|
||||||
L"aime",
|
L"aime",
|
||||||
|
@ -154,7 +154,7 @@ static int my_cCommIo_GetTrigger()
|
|||||||
|
|
||||||
out &= ~last_triggers;
|
out &= ~last_triggers;
|
||||||
|
|
||||||
dprintf("Revio: GetTrigger %X\n", out);
|
// dprintf("Revio: GetTrigger %X\n", out);
|
||||||
last_triggers = out;
|
last_triggers = out;
|
||||||
return out;
|
return out;
|
||||||
}
|
}
|
||||||
@ -188,7 +188,7 @@ static int my_cCommIo_GetRelease()
|
|||||||
|
|
||||||
out &= ~btns;
|
out &= ~btns;
|
||||||
|
|
||||||
dprintf("Revio: GetRelease %X\n", out);
|
// dprintf("Revio: GetRelease %X\n", out);
|
||||||
last_triggers = btns;
|
last_triggers = btns;
|
||||||
return out;
|
return out;
|
||||||
}
|
}
|
||||||
|
9
dist/cxb/segatools.ini
vendored
9
dist/cxb/segatools.ini
vendored
@ -19,10 +19,10 @@ appdata=
|
|||||||
|
|
||||||
[aime]
|
[aime]
|
||||||
; Aime reader emulation
|
; Aime reader emulation
|
||||||
; CXB is stupid, so we have to make the paths go back one
|
|
||||||
enable=1
|
enable=1
|
||||||
|
; CXB is stupid, so we have to make the paths go back two directories. This
|
||||||
|
; will load the file from "resource\DEVICE\aime.txt".
|
||||||
aimePath=../DEVICE/aime.txt
|
aimePath=../DEVICE/aime.txt
|
||||||
felicaPath=../DEVICE/felica.txt
|
|
||||||
|
|
||||||
[led]
|
[led]
|
||||||
; Emulation for the LED board. Currently it's just dummy responses,
|
; Emulation for the LED board. Currently it's just dummy responses,
|
||||||
@ -39,6 +39,10 @@ enable=1
|
|||||||
; Note that 127.0.0.1, localhost etc are specifically rejected.
|
; Note that 127.0.0.1, localhost etc are specifically rejected.
|
||||||
default=127.0.0.1
|
default=127.0.0.1
|
||||||
|
|
||||||
|
; Set the title server hostname or IP address here, as the title server
|
||||||
|
; is hardcoded in the game.
|
||||||
|
title=https://127.0.0.1:9002
|
||||||
|
|
||||||
[netenv]
|
[netenv]
|
||||||
; Simulate an ideal LAN environment. This may interfere with head-to-head play.
|
; Simulate an ideal LAN environment. This may interfere with head-to-head play.
|
||||||
; Crossbeats is extremely picky about its LAN environment, so leaving this
|
; Crossbeats is extremely picky about its LAN environment, so leaving this
|
||||||
@ -113,6 +117,7 @@ test=0x70
|
|||||||
service=0x71
|
service=0x71
|
||||||
; Keyboard button to increment coin counter. Default is the F3 key.
|
; Keyboard button to increment coin counter. Default is the F3 key.
|
||||||
coin=0x72
|
coin=0x72
|
||||||
|
|
||||||
; Menu up key. Default is up arrow.
|
; Menu up key. Default is up arrow.
|
||||||
up=0x26
|
up=0x26
|
||||||
; Menu down key. Default is down arrow.
|
; Menu down key. Default is down arrow.
|
||||||
|
@ -153,6 +153,13 @@ setting. Also, loopback addresses are specifically checked for and rejected by
|
|||||||
the games themselves; this needs to be a LAN or WAN IP (or a hostname that
|
the games themselves; this needs to be a LAN or WAN IP (or a hostname that
|
||||||
resolves to one).
|
resolves to one).
|
||||||
|
|
||||||
|
### `title`
|
||||||
|
|
||||||
|
Default: `title`
|
||||||
|
|
||||||
|
Leave it as `title` to use the title server returned by ALL.Net. Rewrites
|
||||||
|
the title server hostname for certain games, such as crossbeats REV.
|
||||||
|
|
||||||
### `router`
|
### `router`
|
||||||
|
|
||||||
Default: Empty string (i.e. use value from `default` setting)
|
Default: Empty string (i.e. use value from `default` setting)
|
||||||
@ -388,13 +395,29 @@ Bit values are:
|
|||||||
- 3: EXP: Export (for Asian markets)
|
- 3: EXP: Export (for Asian markets)
|
||||||
- 4: CHS: China (Simplified Chinese?)
|
- 4: CHS: China (Simplified Chinese?)
|
||||||
|
|
||||||
|
### `billingCa`
|
||||||
|
|
||||||
|
Default: `DEVICE\\ca.crt`
|
||||||
|
|
||||||
|
Set the billing certificate path. This has to match the one used for the
|
||||||
|
SSL billing server. The DER certificate must fit in 1024 bytes so it must be
|
||||||
|
small.
|
||||||
|
|
||||||
|
### `billingPub`
|
||||||
|
|
||||||
|
Default: `DEVICE\\billing.pub`
|
||||||
|
|
||||||
|
Set the actual keychip RSA public key path. This public key has to match the
|
||||||
|
private key `billing.key` of the billing server in order to decrypt/encrypt
|
||||||
|
the billing transactions.
|
||||||
|
|
||||||
### `billingType`
|
### `billingType`
|
||||||
|
|
||||||
Default: `1`
|
Default: `1`
|
||||||
|
|
||||||
Set the billing "type" for the keychip. The type determins what kind of revenue share,
|
Set the billing "type" for the keychip. The type determins what kind of revenue share,
|
||||||
if any, the game maker has with SEGA. Some games may be picky and require types other
|
if any, the game maker has with SEGA. Some games may be picky and require types other
|
||||||
then 1 (ex. Crossbeats requires billing type 2), so this option is provided if this
|
then 1 (ex. crossbeats REV. requires billing type 2), so this option is provided if this
|
||||||
is an issue. Billing types are:
|
is an issue. Billing types are:
|
||||||
|
|
||||||
- 0: No billing?
|
- 0: No billing?
|
||||||
|
@ -13,6 +13,8 @@
|
|||||||
#include "hook/hr.h"
|
#include "hook/hr.h"
|
||||||
#include "hook/table.h"
|
#include "hook/table.h"
|
||||||
|
|
||||||
|
#include "util/dprintf.h"
|
||||||
|
|
||||||
#include "hooklib/dns.h"
|
#include "hooklib/dns.h"
|
||||||
|
|
||||||
/* Latest w32headers does not include DnsQueryEx, so we'll have to "polyfill"
|
/* Latest w32headers does not include DnsQueryEx, so we'll have to "polyfill"
|
||||||
@ -66,13 +68,19 @@ static int WSAAPI hook_getaddrinfo(
|
|||||||
const char *pServiceName,
|
const char *pServiceName,
|
||||||
const ADDRINFOA *pHints,
|
const ADDRINFOA *pHints,
|
||||||
ADDRINFOA **ppResult);
|
ADDRINFOA **ppResult);
|
||||||
|
|
||||||
static HINTERNET WINAPI hook_WinHttpConnect(
|
static HINTERNET WINAPI hook_WinHttpConnect(
|
||||||
HINTERNET hSession,
|
HINTERNET hSession,
|
||||||
const wchar_t *pwszServerName,
|
const wchar_t *pwszServerName,
|
||||||
INTERNET_PORT nServerPort,
|
INTERNET_PORT nServerPort,
|
||||||
DWORD dwReserved);
|
DWORD dwReserved);
|
||||||
|
|
||||||
|
static bool WINAPI hook_WinHttpCrackUrl(
|
||||||
|
const wchar_t *pwszUrl,
|
||||||
|
DWORD dwUrlLength,
|
||||||
|
DWORD dwFlags,
|
||||||
|
LPURL_COMPONENTS lpUrlComponents);
|
||||||
|
|
||||||
/* Link pointers */
|
/* Link pointers */
|
||||||
|
|
||||||
static DNS_STATUS (WINAPI *next_DnsQuery_A)(
|
static DNS_STATUS (WINAPI *next_DnsQuery_A)(
|
||||||
@ -108,6 +116,12 @@ static HINTERNET (WINAPI *next_WinHttpConnect)(
|
|||||||
INTERNET_PORT nServerPort,
|
INTERNET_PORT nServerPort,
|
||||||
DWORD dwReserved);
|
DWORD dwReserved);
|
||||||
|
|
||||||
|
static bool (WINAPI *next_WinHttpCrackUrl)(
|
||||||
|
const wchar_t *pwszUrl,
|
||||||
|
DWORD dwUrlLength,
|
||||||
|
DWORD dwFlags,
|
||||||
|
LPURL_COMPONENTS lpUrlComponents);
|
||||||
|
|
||||||
static const struct hook_symbol dns_hook_syms_dnsapi[] = {
|
static const struct hook_symbol dns_hook_syms_dnsapi[] = {
|
||||||
{
|
{
|
||||||
.name = "DnsQuery_A",
|
.name = "DnsQuery_A",
|
||||||
@ -138,13 +152,19 @@ static const struct hook_symbol dns_hook_syms_winhttp[] = {
|
|||||||
.name = "WinHttpConnect",
|
.name = "WinHttpConnect",
|
||||||
.patch = hook_WinHttpConnect,
|
.patch = hook_WinHttpConnect,
|
||||||
.link = (void **) &next_WinHttpConnect,
|
.link = (void **) &next_WinHttpConnect,
|
||||||
|
}, {
|
||||||
|
.name = "WinHttpCrackUrl",
|
||||||
|
.patch = hook_WinHttpCrackUrl,
|
||||||
|
.link = (void **) &next_WinHttpCrackUrl,
|
||||||
}
|
}
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
static bool dns_hook_initted;
|
static bool dns_hook_initted;
|
||||||
static CRITICAL_SECTION dns_hook_lock;
|
static CRITICAL_SECTION dns_hook_lock;
|
||||||
static struct dns_hook_entry *dns_hook_entries;
|
static struct dns_hook_entry *dns_hook_entries;
|
||||||
static size_t dns_hook_nentries;
|
static size_t dns_hook_nentries;
|
||||||
|
static char received_title_url[255];
|
||||||
|
|
||||||
static void dns_hook_init(void)
|
static void dns_hook_init(void)
|
||||||
{
|
{
|
||||||
@ -522,3 +542,48 @@ static HINTERNET WINAPI hook_WinHttpConnect(
|
|||||||
|
|
||||||
return next_WinHttpConnect(hSession, pwszServerName, nServerPort, dwReserved);
|
return next_WinHttpConnect(hSession, pwszServerName, nServerPort, dwReserved);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Hook to replace CXB title url
|
||||||
|
static bool WINAPI hook_WinHttpCrackUrl(
|
||||||
|
const wchar_t *pwszUrl,
|
||||||
|
DWORD dwUrlLength,
|
||||||
|
DWORD dwFlags,
|
||||||
|
LPURL_COMPONENTS lpUrlComponents)
|
||||||
|
{
|
||||||
|
const struct dns_hook_entry *pos;
|
||||||
|
size_t i;
|
||||||
|
|
||||||
|
EnterCriticalSection(&dns_hook_lock);
|
||||||
|
|
||||||
|
for (i = 0 ; i < dns_hook_nentries ; i++) {
|
||||||
|
pos = &dns_hook_entries[i];
|
||||||
|
|
||||||
|
if (_wcsicmp(pwszUrl, pos->from) == 0) {
|
||||||
|
wchar_t* toAddr = pos->to;
|
||||||
|
wchar_t titleBuffer[255];
|
||||||
|
|
||||||
|
if(wcscmp(toAddr, L"title") == 0) {
|
||||||
|
size_t wstr_c;
|
||||||
|
mbstowcs_s(&wstr_c, titleBuffer, 255, received_title_url, strlen(received_title_url));
|
||||||
|
toAddr = titleBuffer;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool result = next_WinHttpCrackUrl(
|
||||||
|
toAddr,
|
||||||
|
wcslen(toAddr),
|
||||||
|
dwFlags,
|
||||||
|
lpUrlComponents
|
||||||
|
);
|
||||||
|
LeaveCriticalSection(&dns_hook_lock);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
LeaveCriticalSection(&dns_hook_lock);
|
||||||
|
return next_WinHttpCrackUrl(
|
||||||
|
pwszUrl,
|
||||||
|
dwUrlLength,
|
||||||
|
dwFlags,
|
||||||
|
lpUrlComponents
|
||||||
|
);
|
||||||
|
}
|
||||||
|
@ -13,7 +13,6 @@ EXPORTS
|
|||||||
amDllVideoSetResolution @3
|
amDllVideoSetResolution @3
|
||||||
idac_io_get_api_version
|
idac_io_get_api_version
|
||||||
idac_io_init
|
idac_io_init
|
||||||
idac_io_poll
|
|
||||||
idac_io_get_opbtns
|
idac_io_get_opbtns
|
||||||
idac_io_get_gamebtns
|
idac_io_get_gamebtns
|
||||||
idac_io_get_shifter
|
idac_io_get_shifter
|
||||||
|
@ -52,10 +52,6 @@ HRESULT idac_xi_init(const struct idac_xi_config *cfg, const struct idac_io_back
|
|||||||
return S_OK;
|
return S_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
HRESULT idac_io_poll(void) {
|
|
||||||
return S_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
static HRESULT idac_xi_config_apply(const struct idac_xi_config *cfg) {
|
static HRESULT idac_xi_config_apply(const struct idac_xi_config *cfg) {
|
||||||
/* Deadzones check */
|
/* Deadzones check */
|
||||||
if (cfg->left_stick_deadzone > 32767 || cfg->left_stick_deadzone < 0) {
|
if (cfg->left_stick_deadzone > 32767 || cfg->left_stick_deadzone < 0) {
|
||||||
|
@ -113,6 +113,14 @@ void dns_config_load(struct dns_config *cfg, const wchar_t *filename)
|
|||||||
cfg->aimedb,
|
cfg->aimedb,
|
||||||
_countof(cfg->aimedb),
|
_countof(cfg->aimedb),
|
||||||
filename);
|
filename);
|
||||||
|
|
||||||
|
GetPrivateProfileStringW(
|
||||||
|
L"dns",
|
||||||
|
L"title",
|
||||||
|
L"title",
|
||||||
|
cfg->title,
|
||||||
|
_countof(cfg->title),
|
||||||
|
filename);
|
||||||
}
|
}
|
||||||
|
|
||||||
void hwmon_config_load(struct hwmon_config *cfg, const wchar_t *filename)
|
void hwmon_config_load(struct hwmon_config *cfg, const wchar_t *filename)
|
||||||
|
@ -82,6 +82,13 @@ HRESULT dns_platform_hook_init(const struct dns_config *cfg)
|
|||||||
return hr;
|
return hr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// croosbeats REV.
|
||||||
|
hr = dns_hook_push(L"https://rev-ent.ac.capcom.jp:443", cfg->title);
|
||||||
|
|
||||||
|
if (FAILED(hr)) {
|
||||||
|
return hr;
|
||||||
|
}
|
||||||
|
|
||||||
// AimePay
|
// AimePay
|
||||||
hr = dns_hook_push(L"api-aime.am-all.net", cfg->startup);
|
hr = dns_hook_push(L"api-aime.am-all.net", cfg->startup);
|
||||||
|
|
||||||
|
@ -11,6 +11,7 @@ struct dns_config {
|
|||||||
wchar_t startup[128];
|
wchar_t startup[128];
|
||||||
wchar_t billing[128];
|
wchar_t billing[128];
|
||||||
wchar_t aimedb[128];
|
wchar_t aimedb[128];
|
||||||
|
wchar_t title[128];
|
||||||
};
|
};
|
||||||
|
|
||||||
HRESULT dns_platform_hook_init(const struct dns_config *cfg);
|
HRESULT dns_platform_hook_init(const struct dns_config *cfg);
|
||||||
|
@ -14,22 +14,22 @@
|
|||||||
#include "util/str.h"
|
#include "util/str.h"
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
NUSEC_IOCTL_PING = 0x22A114,
|
NUSEC_IOCTL_PING = CTL_CODE(0x22, 0x845, METHOD_BUFFERED, FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_ERASE_TRACE_LOG = 0x22E188,
|
NUSEC_IOCTL_GET_PLAY_COUNT = CTL_CODE(0x22, 0x854, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_TD_ERASE_USED = 0x22E18C,
|
NUSEC_IOCTL_ADD_PLAY_COUNT = CTL_CODE(0x22, 0x855, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_ADD_PLAY_COUNT = 0x22E154,
|
NUSEC_IOCTL_ERASE_TRACE_LOG = CTL_CODE(0x22, 0x862, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_GET_BILLING_CA_CERT = 0x22E1C4,
|
NUSEC_IOCTL_TD_ERASE_USED = CTL_CODE(0x22, 0x863, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_GET_BILLING_PUBKEY = 0x22E1C8,
|
NUSEC_IOCTL_PUT_TRACE_LOG_DATA = CTL_CODE(0x22, 0x864, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_GET_NEARFULL = 0x22E20C,
|
NUSEC_IOCTL_GET_TRACE_LOG_DATA = CTL_CODE(0x22, 0x865, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_GET_NVRAM_AVAILABLE = 0x22E19C,
|
NUSEC_IOCTL_GET_TRACE_LOG_STATE = CTL_CODE(0x22, 0x866, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_GET_NVRAM_GEOMETRY = 0x22E24C,
|
NUSEC_IOCTL_GET_NVRAM_AVAILABLE = CTL_CODE(0x22, 0x867, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_GET_PLAY_COUNT = 0x22E150,
|
NUSEC_IOCTL_GET_BILLING_CA_CERT = CTL_CODE(0x22, 0x871, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_GET_PLAY_LIMIT = 0x22E204,
|
NUSEC_IOCTL_GET_BILLING_PUBKEY = CTL_CODE(0x22, 0x872, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_GET_TRACE_LOG_DATA = 0x22E194,
|
NUSEC_IOCTL_GET_PLAY_LIMIT = CTL_CODE(0x22, 0x881, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_GET_TRACE_LOG_STATE = 0x22E198,
|
NUSEC_IOCTL_PUT_PLAY_LIMIT = CTL_CODE(0x22, 0x882, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_PUT_NEARFULL = 0x22E210,
|
NUSEC_IOCTL_GET_NEARFULL = CTL_CODE(0x22, 0x883, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_PUT_PLAY_LIMIT = 0x22E208,
|
NUSEC_IOCTL_PUT_NEARFULL = CTL_CODE(0x22, 0x884, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
NUSEC_IOCTL_PUT_TRACE_LOG_DATA = 0x22E190,
|
NUSEC_IOCTL_GET_NVRAM_GEOMETRY = CTL_CODE(0x22, 0x893, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS),
|
||||||
};
|
};
|
||||||
|
|
||||||
struct nusec_log_record {
|
struct nusec_log_record {
|
||||||
|
Loading…
Reference in New Issue
Block a user