mirror of
https://gitea.tendokyu.moe/TeamTofuShop/taitools.git
synced 2026-09-22 22:28:06 +03:00
change how dongle is attached for games that care
This commit is contained in:
@@ -35,3 +35,10 @@ void k9101258_config_load(struct usbio_config *cfg, const wchar_t *filename)
|
||||
|
||||
cfg->enabled = GetPrivateProfileIntW(L"usbio", L"enable", 1, filename);
|
||||
}
|
||||
|
||||
void dongle_config_load(struct dongle_config *cfg, const wchar_t *filename)
|
||||
{
|
||||
assert(cfg != NULL);
|
||||
assert(filename != NULL);
|
||||
GetPrivateProfileStringW(L"reader", L"card_serial", L"702039200000000", cfg->serial, _countof(cfg->serial), filename);
|
||||
}
|
||||
|
||||
@@ -4,9 +4,11 @@
|
||||
#include <stddef.h>
|
||||
|
||||
#include "board/io4.h"
|
||||
#include "board/dongle.h"
|
||||
#include "board/k92x0249.h"
|
||||
#include "board/k9101258.h"
|
||||
|
||||
void io4_config_load(struct io4_config *cfg, const wchar_t *filename);
|
||||
void k92x0249_config_load(struct k92x0249_config *cfg, const wchar_t *filename);
|
||||
void k9101258_config_load(struct usbio_config *cfg, const wchar_t *filename);
|
||||
void dongle_config_load(struct dongle_config *cfg, const wchar_t *filename);
|
||||
|
||||
+451
@@ -0,0 +1,451 @@
|
||||
#include <windows.h>
|
||||
|
||||
#include <assert.h>
|
||||
#include <stdbool.h>
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "board/dongle.h"
|
||||
#include "board/config.h"
|
||||
|
||||
#include "jvs/jvs-bus.h"
|
||||
#include "jvs/jvs-cmd.h"
|
||||
#include "jvs/jvs-util.h"
|
||||
|
||||
#include "util/dprintf.h"
|
||||
#include "util/dump.h"
|
||||
|
||||
// JVS card reader, A/B/C vairants
|
||||
|
||||
static const uint8_t dongle_ident[] = "TAITO CORP.;RFID CTRL P.C.B.;Ver1.11;";
|
||||
static const uint8_t card_uid[] = { 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x00 };
|
||||
static const uint8_t card_id[] = {
|
||||
0x01, 0x2E, 0x4C, 0xE4, 0x00, 0x01, 0x00, 0x01,
|
||||
0x00, 0x78, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
|
||||
};
|
||||
static struct dongle_config cfg;
|
||||
|
||||
static uint8_t dongle_features[] = {
|
||||
// Misc. SW
|
||||
0x07,
|
||||
0x00,
|
||||
0x08,
|
||||
0x00,
|
||||
|
||||
// GPIO Out
|
||||
0x12,
|
||||
0x08,
|
||||
0x00,
|
||||
0x00,
|
||||
|
||||
// End
|
||||
0x00,
|
||||
};
|
||||
|
||||
static void dongle_transact(
|
||||
struct jvs_node *node,
|
||||
const void *bytes,
|
||||
size_t nbytes,
|
||||
struct iobuf *resp);
|
||||
|
||||
static bool dongle_sense(struct jvs_node *node);
|
||||
|
||||
static HRESULT dongle_cmd(
|
||||
void *ctx,
|
||||
struct const_iobuf *req,
|
||||
struct iobuf *resp);
|
||||
|
||||
static HRESULT dongle_cmd_reset(struct dongle *dongle, struct const_iobuf *req_buf);
|
||||
static HRESULT dongle_cmd_assign_addr(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf);
|
||||
static HRESULT dongle_cmd_read_id(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf);
|
||||
static HRESULT dongle_cmd_get_cmd_version(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf);
|
||||
static HRESULT dongle_cmd_get_jvs_version(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf);
|
||||
static HRESULT dongle_cmd_get_comm_version(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf);
|
||||
static HRESULT dongle_cmd_get_features(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf);
|
||||
static HRESULT dongle_cmd_write_gpio1(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf);
|
||||
static HRESULT dongle_cmd_read_misc_switches(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf);
|
||||
static HRESULT dongle_cmd_taito_nesica_read(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf);
|
||||
static HRESULT dongle_cmd_taito_aic_read(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf);
|
||||
|
||||
void dongle_init(
|
||||
struct dongle *dongle,
|
||||
struct jvs_node *next,
|
||||
void *ops_ctx)
|
||||
{
|
||||
assert(dongle != NULL);
|
||||
|
||||
dongle_config_load(&cfg, L".\\taitools.ini");
|
||||
|
||||
dongle->jvs.next = next;
|
||||
dongle->jvs.transact = dongle_transact;
|
||||
dongle->jvs.sense = dongle_sense;
|
||||
dongle->jvs.sense_out = true;
|
||||
dongle->addr = 0xFF;
|
||||
dongle->state = IDLE;
|
||||
dongle->ops_ctx = ops_ctx;
|
||||
}
|
||||
|
||||
struct jvs_node *dongle_to_jvs_node(struct dongle *dongle)
|
||||
{
|
||||
assert(dongle != NULL);
|
||||
|
||||
return &dongle->jvs;
|
||||
}
|
||||
|
||||
static void dongle_transact(
|
||||
struct jvs_node *node,
|
||||
const void *bytes,
|
||||
size_t nbytes,
|
||||
struct iobuf *resp)
|
||||
{
|
||||
struct dongle *dongle;
|
||||
|
||||
assert(node != NULL);
|
||||
assert(bytes != NULL);
|
||||
assert(resp != NULL);
|
||||
|
||||
dongle = CONTAINING_RECORD(node, struct dongle, jvs);
|
||||
|
||||
jvs_crack_request(bytes, nbytes, resp, dongle->addr, dongle_cmd, dongle);
|
||||
}
|
||||
|
||||
static bool dongle_sense(struct jvs_node *node)
|
||||
{
|
||||
struct dongle *dongle;
|
||||
|
||||
assert(node != NULL);
|
||||
|
||||
dongle = CONTAINING_RECORD(node, struct dongle, jvs);
|
||||
|
||||
return dongle->addr == 0xFF;
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd(
|
||||
void *ctx,
|
||||
struct const_iobuf *req,
|
||||
struct iobuf *resp)
|
||||
{
|
||||
struct dongle *dongle;
|
||||
|
||||
dongle = (struct dongle *)ctx;
|
||||
|
||||
switch (req->bytes[req->pos]) {
|
||||
case JVS_CMD_RESET:
|
||||
return dongle_cmd_reset(dongle, req);
|
||||
|
||||
case JVS_CMD_ASSIGN_ADDR:
|
||||
return dongle_cmd_assign_addr(dongle, req, resp);
|
||||
|
||||
case JVS_CMD_READ_ID:
|
||||
return dongle_cmd_read_id(dongle, req, resp);
|
||||
|
||||
case JVS_CMD_GET_CMD_VERSION:
|
||||
return dongle_cmd_get_cmd_version(dongle, req, resp);
|
||||
|
||||
case JVS_CMD_GET_JVS_VERSION:
|
||||
return dongle_cmd_get_jvs_version(dongle, req, resp);
|
||||
|
||||
case JVS_CMD_GET_COMM_VERSION:
|
||||
return dongle_cmd_get_comm_version(dongle, req, resp);
|
||||
|
||||
case JVS_CMD_GET_FEATURES:
|
||||
return dongle_cmd_get_features(dongle, req, resp);
|
||||
|
||||
case JVS_CMD_WRITE_GPIO1: // Set reader state
|
||||
return dongle_cmd_write_gpio1(dongle, req, resp);
|
||||
|
||||
case JVS_CMD_READ_MISC_SWITCHES: // Read for old (1.00/0.02) fw
|
||||
return dongle_cmd_read_misc_switches(dongle, req, resp);
|
||||
|
||||
case JVS_CMD_TAITO_NESICA_READ: // Check reader state for new fw
|
||||
return dongle_cmd_taito_nesica_read(dongle, req, resp);
|
||||
|
||||
case JVS_CMD_TAITO_AIC_READ: // Check reader state for new fw
|
||||
return dongle_cmd_taito_aic_read(dongle, req, resp);
|
||||
|
||||
default:
|
||||
dprintf("DONGLE: Node %02x: Unhandled command byte @ %02X %02x\n",
|
||||
dongle->addr,
|
||||
req->pos,
|
||||
req->bytes[req->pos]);
|
||||
dump_const_iobuf(req);
|
||||
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd_reset(struct dongle *dongle, struct const_iobuf *req_buf)
|
||||
{
|
||||
struct jvs_req_reset req;
|
||||
HRESULT hr;
|
||||
|
||||
hr = iobuf_read(req_buf, &req, sizeof(req));
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
dprintf("DONGLE: Reset (param %02x)\n", req.unknown);
|
||||
dongle->addr = 0xFF;
|
||||
dongle->jvs.sense_out = false;
|
||||
|
||||
/* No ack for this since it really is addressed to everybody */
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd_assign_addr(
|
||||
struct dongle *dongle,
|
||||
struct const_iobuf *req_buf,
|
||||
struct iobuf *resp_buf)
|
||||
{
|
||||
struct jvs_req_assign_addr req;
|
||||
bool sense;
|
||||
HRESULT hr;
|
||||
|
||||
hr = iobuf_read(req_buf, &req, sizeof(req));
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
sense = jvs_node_sense(dongle->jvs.next);
|
||||
dprintf("DONGLE: Assign addr %02x sense %i\n", req.addr, sense);
|
||||
|
||||
if (sense) {
|
||||
/* That address is for somebody else */
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
dongle->addr = req.addr;
|
||||
dongle->jvs.sense_out = true;
|
||||
|
||||
return iobuf_write_8(resp_buf, 0x01);
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd_read_id(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf)
|
||||
{
|
||||
uint8_t req;
|
||||
HRESULT hr;
|
||||
|
||||
hr = iobuf_read_8(req_buf, &req);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
dprintf("DONGLE: Read ID\n");
|
||||
|
||||
/* Write report byte */
|
||||
|
||||
hr = iobuf_write_8(resp_buf, 0x01);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
/* Write the identification string. The NUL terminator at the end of this C
|
||||
string is also sent, and it naturally terminates the response chunk. */
|
||||
|
||||
return iobuf_write(resp_buf, dongle_ident, sizeof(dongle_ident));
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd_get_cmd_version(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf)
|
||||
{
|
||||
uint8_t req;
|
||||
uint8_t resp[2];
|
||||
HRESULT hr;
|
||||
|
||||
hr = iobuf_read_8(req_buf, &req);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
dprintf("DONGLE: Get command format version\n");
|
||||
resp[0] = 0x01; /* Report byte */
|
||||
resp[1] = 0x13; /* Command format version BCD */
|
||||
|
||||
return iobuf_write(resp_buf, resp, sizeof(resp));
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd_get_jvs_version(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf)
|
||||
{
|
||||
uint8_t req;
|
||||
uint8_t resp[2];
|
||||
HRESULT hr;
|
||||
|
||||
hr = iobuf_read_8(req_buf, &req);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
dprintf("DONGLE: Get JVS format version\n");
|
||||
resp[0] = 0x01; /* Report byte */
|
||||
resp[1] = 0x30; /* JVS format version BCD */
|
||||
|
||||
return iobuf_write(resp_buf, resp, sizeof(resp));
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd_get_comm_version(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf)
|
||||
{
|
||||
uint8_t req;
|
||||
uint8_t resp[2];
|
||||
HRESULT hr;
|
||||
|
||||
hr = iobuf_read_8(req_buf, &req);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
dprintf("DONGLE: Get COMM format version\n");
|
||||
resp[0] = 0x01; /* Report byte */
|
||||
resp[1] = 0x10; /* COMM format version BCD */
|
||||
|
||||
return iobuf_write(resp_buf, resp, sizeof(resp));
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd_get_features(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf)
|
||||
{
|
||||
uint8_t req;
|
||||
uint8_t resp[2];
|
||||
HRESULT hr;
|
||||
|
||||
hr = iobuf_read_8(req_buf, &req);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
dprintf("DONGLE: Get reader features\n");
|
||||
|
||||
hr = iobuf_write_8(resp_buf, 0x01); /* Write report byte */
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
return iobuf_write(resp_buf, dongle_features, sizeof(dongle_features));
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd_write_gpio1(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf)
|
||||
{
|
||||
uint8_t unk;
|
||||
uint8_t num_io;
|
||||
uint8_t io_state[255];
|
||||
HRESULT hr = iobuf_read_8(req_buf, &unk);
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = iobuf_read_8(req_buf, &num_io);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = iobuf_read(req_buf, io_state, num_io);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
if (dongle->state != io_state[0]) {
|
||||
dprintf("DONGLE: Update state %02X\n", io_state[0], num_io);
|
||||
}
|
||||
|
||||
dongle->state = io_state[0];
|
||||
return iobuf_write_8(resp_buf, 0x01); /* Write report byte */
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd_read_misc_switches(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf)
|
||||
{
|
||||
uint8_t cmd;
|
||||
uint8_t arg;
|
||||
HRESULT hr;
|
||||
|
||||
hr = iobuf_read_8(req_buf, &cmd);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = iobuf_read_8(req_buf, &arg);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = iobuf_write_8(resp_buf, 0x01); /* Write report byte */
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
return iobuf_write_8(resp_buf, NO_CARD); /* Write status byte */
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd_taito_nesica_read(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf)
|
||||
{
|
||||
uint8_t cmd;
|
||||
HRESULT hr = iobuf_read_8(req_buf, &cmd);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = iobuf_write_8(resp_buf, 0x01); /* Write report byte */
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = iobuf_write(resp_buf, card_uid, 8); // AICC: Unused, should be IDm
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
return iobuf_write(resp_buf, cfg.serial, 16); // AICC: SPAD0
|
||||
}
|
||||
|
||||
static HRESULT dongle_cmd_taito_aic_read(struct dongle *dongle, struct const_iobuf *req_buf, struct iobuf *resp_buf)
|
||||
{
|
||||
uint8_t cmd;
|
||||
HRESULT hr = iobuf_read_8(req_buf, &cmd);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = iobuf_write_8(resp_buf, 0x01); /* Write report byte */
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = iobuf_write(resp_buf, card_id, 16); // ID
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = iobuf_write(resp_buf, "\x00\x01", 2); // CKV
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = iobuf_write(resp_buf, "\x02\x00\x00", 3); // WCNT
|
||||
|
||||
if (FAILED(hr)) {
|
||||
return hr;
|
||||
}
|
||||
|
||||
return iobuf_write(resp_buf, "12345678", 8); // MAC_A?
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
#pragma once
|
||||
#include <windows.h>
|
||||
|
||||
#include "jvs/jvs-bus.h"
|
||||
|
||||
#pragma pack(push,1)
|
||||
struct dongle {
|
||||
struct jvs_node jvs;
|
||||
uint8_t state;
|
||||
uint8_t addr;
|
||||
void *ops_ctx;
|
||||
};
|
||||
|
||||
struct dongle_config {
|
||||
wchar_t serial[16];
|
||||
};
|
||||
|
||||
#pragma pack(pop)
|
||||
|
||||
void dongle_init(
|
||||
struct dongle *dongle,
|
||||
struct jvs_node *next,
|
||||
void *ops_ctx);
|
||||
|
||||
struct jvs_node *dongle_to_jvs_node(struct dongle *dongle);
|
||||
@@ -14,6 +14,8 @@ board_lib = static_library(
|
||||
'config.h',
|
||||
'guid.c',
|
||||
'guid.h',
|
||||
'dongle.c',
|
||||
'dongle.h',
|
||||
'io3.c',
|
||||
'io3.h',
|
||||
'k92x0249.c',
|
||||
|
||||
@@ -57,7 +57,6 @@ static DWORD CALLBACK gc_pre_startup(void)
|
||||
|
||||
struct idmac_hardware idhw = {
|
||||
.dipsw = 0b0000,
|
||||
.dongle = NULL,
|
||||
.jvs = gc_reader_init,
|
||||
.fastio_main = gc_fastio_init,
|
||||
.fastio_sub = NULL,
|
||||
|
||||
+4
-1
@@ -4,6 +4,7 @@
|
||||
#include "jvs/jvs-bus.h"
|
||||
#include "idmac/jvs.h"
|
||||
#include "board/k92x0249.h"
|
||||
#include "board/dongle.h"
|
||||
|
||||
#include "gchook/reader.h"
|
||||
#include "gchook/gc-dll.h"
|
||||
@@ -11,6 +12,7 @@
|
||||
#include "util/dprintf.h"
|
||||
|
||||
static struct k92x0249 gc_jvs_reader;
|
||||
static struct dongle gc_dongle;
|
||||
|
||||
HRESULT gc_reader_init(struct jvs_node **out)
|
||||
{
|
||||
@@ -20,7 +22,8 @@ HRESULT gc_reader_init(struct jvs_node **out)
|
||||
|
||||
dprintf("Gc Nesica Reader: Init\n");
|
||||
|
||||
k92x0249_init(&gc_jvs_reader, NULL, NULL);
|
||||
dongle_init(&gc_dongle, NULL, NULL);
|
||||
k92x0249_init(&gc_jvs_reader, dongle_to_jvs_node(&gc_dongle), NULL);
|
||||
*out = k92x0249_to_jvs_node(&gc_jvs_reader);
|
||||
|
||||
return S_OK;
|
||||
|
||||
@@ -16,7 +16,6 @@ struct idmac_config {
|
||||
|
||||
struct idmac_hardware {
|
||||
uint8_t dipsw;
|
||||
jvs_provider_t dongle;
|
||||
jvs_provider_t jvs;
|
||||
fastio_provider_t fastio_main;
|
||||
fastio_provider_t fastio_sub;
|
||||
|
||||
@@ -59,7 +59,6 @@ static DWORD CALLBACK siva_pre_startup(void)
|
||||
|
||||
struct idmac_hardware idhw = {
|
||||
.dipsw = 0b0000,
|
||||
.dongle = NULL,
|
||||
.jvs = siva_reader_init,
|
||||
.fastio_main = siva_fastio_init,
|
||||
.fastio_sub = NULL,
|
||||
|
||||
Reference in New Issue
Block a user