Add more good stuff
This commit is contained in:
parent
f3febb89d8
commit
96f856dca4
@ -154,14 +154,14 @@ int baseboardIoctl(int fd, unsigned int request, void *data)
|
||||
switch (_data[0])
|
||||
{
|
||||
|
||||
case BASEBOARD_GET_SERIAL:
|
||||
case BASEBOARD_GET_SERIAL: // bcCmdSysInfoGetReq
|
||||
{
|
||||
serialCommand.destAddress = _data[1];
|
||||
serialCommand.destSize = _data[2];
|
||||
}
|
||||
break;
|
||||
|
||||
case BASEBOARD_WRITE_FLASH:
|
||||
case BASEBOARD_WRITE_FLASH: // bcCmdSysFlashWrite
|
||||
{
|
||||
printf("Warning: The game attempted to write to the baseboard flash\n");
|
||||
}
|
||||
@ -173,8 +173,8 @@ int baseboardIoctl(int fd, unsigned int request, void *data)
|
||||
jvsCommand.srcSize = _data[2];
|
||||
jvsCommand.destAddress = _data[3];
|
||||
jvsCommand.destSize = _data[4];
|
||||
// memcpy(inputBuffer, &shm[jvsCommand.srcAddress], jvsCommand.srcSize);
|
||||
// processPacket(&io);
|
||||
memcpy(inputBuffer, &sharedMemory[jvsCommand.srcAddress], jvsCommand.srcSize);
|
||||
processPacket();
|
||||
}
|
||||
break;
|
||||
|
||||
@ -207,16 +207,15 @@ int baseboardIoctl(int fd, unsigned int request, void *data)
|
||||
|
||||
case BASEBOARD_GET_SENSE_LINE:
|
||||
{
|
||||
// _data[2] = getSenseLine();
|
||||
_data[2] = 3;
|
||||
_data[2] = getSenseLine();
|
||||
}
|
||||
break;
|
||||
|
||||
case BASEBOARD_PROCESS_JVS:
|
||||
{
|
||||
// memcpy(&sharedMemory[jvsCommand.destAddress], outputBuffer, outputPacket.length + 3);
|
||||
memcpy(&sharedMemory[jvsCommand.destAddress], outputBuffer, outputPacket.length + 3);
|
||||
_data[2] = jvsCommand.destAddress;
|
||||
// dp[3] = outputPacket.length + 3;
|
||||
_data[3] = outputPacket.length + 3;
|
||||
}
|
||||
break;
|
||||
|
||||
|
@ -6,6 +6,7 @@
|
||||
#include <errno.h>
|
||||
#include <linux/sockios.h>
|
||||
#include <signal.h>
|
||||
#include <ucontext.h>
|
||||
|
||||
#include "hook.h"
|
||||
|
||||
@ -14,6 +15,7 @@
|
||||
#include "rideboard.h"
|
||||
#include "eeprom.h"
|
||||
#include "jvs.h"
|
||||
#include "securityboard.h"
|
||||
|
||||
#define HOOK_FILE_NAME "/dev/zero"
|
||||
|
||||
@ -24,6 +26,8 @@
|
||||
|
||||
int hooks[4] = {-1, -1, -1, -1};
|
||||
|
||||
uint16_t basePortAddress = 0xFFFF;
|
||||
|
||||
void __attribute__((constructor)) hook_init()
|
||||
{
|
||||
printf("SEGA Lindbergh Loader\nRobert Dilley 2022\nNot for public consumption\n\n");
|
||||
@ -37,6 +41,11 @@ void __attribute__((constructor)) hook_init()
|
||||
|
||||
if (initJVS() != 0)
|
||||
exit(1);
|
||||
|
||||
if(initSecurityBoard() != 0)
|
||||
exit(1);
|
||||
|
||||
printf("Loader init success\n");
|
||||
}
|
||||
|
||||
int open(const char *pathname, int flags)
|
||||
@ -179,9 +188,26 @@ int select(int nfds, fd_set *restrict readfds, fd_set *restrict writefds, fd_set
|
||||
return _select(nfds, readfds, writefds, exceptfds, timeout);
|
||||
}
|
||||
|
||||
#include <ucontext.h>
|
||||
int system(const char *command)
|
||||
{
|
||||
int (*_system)(const char *command) = dlsym(RTLD_NEXT, "system");
|
||||
|
||||
static void exceptionTrampoline(int signum, siginfo_t *info, void *ptr)
|
||||
if (strcmp(command, "lsmod | grep basebd > /dev/null") == 0)
|
||||
return 0;
|
||||
/*
|
||||
if (strcmp(command, "lspci | grep \"Multimedia audio controller: %Creative\" > /dev/null") == 0)
|
||||
return 0;
|
||||
|
||||
if (strcmp(command, "lsmod | grep ctaud") == 0)
|
||||
return 0;
|
||||
|
||||
if (strcmp(command, "lspci | grep MPC8272 > /dev/null") == 0)
|
||||
return 0;
|
||||
*/
|
||||
return _system(command);
|
||||
}
|
||||
|
||||
static void handleSegfault(int signal, siginfo_t *info, void *ptr)
|
||||
{
|
||||
ucontext_t *ctx = ptr;
|
||||
|
||||
@ -193,15 +219,14 @@ static void exceptionTrampoline(int signum, siginfo_t *info, void *ptr)
|
||||
{
|
||||
uint16_t port = ctx->uc_mcontext.gregs[REG_EDX] & 0xFFFF;
|
||||
|
||||
switch (port)
|
||||
{
|
||||
case 0x38:
|
||||
ctx->uc_mcontext.gregs[REG_EAX] = 0xFFFFFFFF;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
// printf("Warning: IO READ Port %X\n", port);
|
||||
if(basePortAddress == 0xFFFF)
|
||||
basePortAddress = port;
|
||||
|
||||
if(port > 0x38)
|
||||
port = port - basePortAddress;
|
||||
|
||||
securityBoardIn(port, (uint32_t *) &(ctx->uc_mcontext.gregs[REG_EAX]));
|
||||
|
||||
ctx->uc_mcontext.gregs[REG_EIP]++;
|
||||
return;
|
||||
}
|
||||
@ -209,7 +234,7 @@ static void exceptionTrampoline(int signum, siginfo_t *info, void *ptr)
|
||||
|
||||
case 0xE7:
|
||||
{
|
||||
//printf("Warning: IO WRITE IMMIDIATE %X\n", code[1]);
|
||||
// printf("Warning: IO WRITE IMMIDIATE %X\n", code[1]);
|
||||
ctx->uc_mcontext.gregs[REG_EIP] += 2;
|
||||
return;
|
||||
}
|
||||
@ -217,7 +242,7 @@ static void exceptionTrampoline(int signum, siginfo_t *info, void *ptr)
|
||||
|
||||
case 0xE6:
|
||||
{
|
||||
//printf("Warning: IO WRITE IMMIDIATE %X\n", code[1]);
|
||||
// printf("Warning: IO WRITE IMMIDIATE %X\n", code[1]);
|
||||
ctx->uc_mcontext.gregs[REG_EIP] += 2;
|
||||
return;
|
||||
}
|
||||
@ -227,7 +252,7 @@ static void exceptionTrampoline(int signum, siginfo_t *info, void *ptr)
|
||||
{
|
||||
uint16_t port = ctx->uc_mcontext.gregs[REG_EDX] & 0xFFFF;
|
||||
uint8_t data = ctx->uc_mcontext.gregs[REG_EAX] & 0xFF;
|
||||
//printf("Warning: IO WRITE Port %X Data %X\n", port, data);
|
||||
// printf("Warning: IO WRITE Port %X Data %X\n", port, data);
|
||||
ctx->uc_mcontext.gregs[REG_EIP]++;
|
||||
return;
|
||||
}
|
||||
@ -236,7 +261,7 @@ static void exceptionTrampoline(int signum, siginfo_t *info, void *ptr)
|
||||
case 0xEF:
|
||||
{
|
||||
uint16_t port = ctx->uc_mcontext.gregs[REG_EDX] & 0xFFFF;
|
||||
//printf("Warning: IO WRITE Port %X\n", port);
|
||||
// printf("Warning: IO WRITE Port %X\n", port);
|
||||
ctx->uc_mcontext.gregs[REG_EIP]++;
|
||||
return;
|
||||
}
|
||||
@ -250,19 +275,12 @@ static void exceptionTrampoline(int signum, siginfo_t *info, void *ptr)
|
||||
|
||||
int iopl(int level)
|
||||
{
|
||||
static int hasRunAlready = 0;
|
||||
struct sigaction act;
|
||||
|
||||
if (hasRunAlready == 0)
|
||||
{
|
||||
struct sigaction act;
|
||||
act.sa_sigaction = handleSegfault;
|
||||
act.sa_flags = SA_SIGINFO;
|
||||
|
||||
act.sa_sigaction = exceptionTrampoline;
|
||||
act.sa_flags = SA_SIGINFO;
|
||||
|
||||
sigaction(SIGSEGV, &act, NULL);
|
||||
|
||||
hasRunAlready = 1;
|
||||
}
|
||||
sigaction(SIGSEGV, &act, NULL);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -160,12 +160,12 @@ void writeFeatures(JVSPacket *outputPacket, JVSCapabilities *capabilities)
|
||||
*
|
||||
* @returns The status of the entire operation
|
||||
*/
|
||||
JVSStatus processPacket(JVSIO *jvsIO)
|
||||
JVSStatus processPacket()
|
||||
{
|
||||
readPacket(&inputPacket);
|
||||
|
||||
/* Check if the packet is for us */
|
||||
if (inputPacket.destination != BROADCAST && inputPacket.destination != jvsIO->deviceID)
|
||||
if (inputPacket.destination != BROADCAST && inputPacket.destination != io.deviceID)
|
||||
return JVS_STATUS_NOT_FOR_US;
|
||||
|
||||
/* Setup the output packet */
|
||||
@ -209,8 +209,8 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
{
|
||||
// printf("CMD_REQUEST_ID\n");
|
||||
outputPacket.data[outputPacket.length] = REPORT_SUCCESS;
|
||||
memcpy(&outputPacket.data[outputPacket.length + 1], jvsIO->capabilities.name, strlen(jvsIO->capabilities.name) + 1);
|
||||
outputPacket.length += strlen(jvsIO->capabilities.name) + 2;
|
||||
memcpy(&outputPacket.data[outputPacket.length + 1], io.capabilities.name, strlen(io.capabilities.name) + 1);
|
||||
outputPacket.length += strlen(io.capabilities.name) + 2;
|
||||
}
|
||||
break;
|
||||
|
||||
@ -219,7 +219,7 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
{
|
||||
// printf("CMD_COMMAND_VERSION\n");
|
||||
outputPacket.data[outputPacket.length] = REPORT_SUCCESS;
|
||||
outputPacket.data[outputPacket.length + 1] = jvsIO->capabilities.commandVersion;
|
||||
outputPacket.data[outputPacket.length + 1] = io.capabilities.commandVersion;
|
||||
outputPacket.length += 2;
|
||||
}
|
||||
break;
|
||||
@ -227,9 +227,9 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
/* Asks for version information */
|
||||
case CMD_JVS_VERSION:
|
||||
{
|
||||
////printf("CMD_JVS_VERSION\n");
|
||||
// printf("CMD_JVS_VERSION\n");
|
||||
outputPacket.data[outputPacket.length] = REPORT_SUCCESS;
|
||||
outputPacket.data[outputPacket.length + 1] = jvsIO->capabilities.jvsVersion;
|
||||
outputPacket.data[outputPacket.length + 1] = io.capabilities.jvsVersion;
|
||||
outputPacket.length += 2;
|
||||
}
|
||||
break;
|
||||
@ -237,9 +237,9 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
/* Asks for version information */
|
||||
case CMD_COMMS_VERSION:
|
||||
{
|
||||
////printf("CMD_COMMS_VERSION\n");
|
||||
// printf("CMD_COMMS_VERSION\n");
|
||||
outputPacket.data[outputPacket.length] = REPORT_SUCCESS;
|
||||
outputPacket.data[outputPacket.length + 1] = jvsIO->capabilities.commsVersion;
|
||||
outputPacket.data[outputPacket.length + 1] = io.capabilities.commsVersion;
|
||||
outputPacket.length += 2;
|
||||
}
|
||||
break;
|
||||
@ -248,7 +248,7 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
case CMD_CAPABILITIES:
|
||||
{
|
||||
// printf("CMD_CAPABILITIES\n");
|
||||
writeFeatures(&outputPacket, &jvsIO->capabilities);
|
||||
writeFeatures(&outputPacket, &io.capabilities);
|
||||
}
|
||||
break;
|
||||
|
||||
@ -258,13 +258,13 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
// printf("CMD_READ_SWITCHES\n");
|
||||
size = 3;
|
||||
outputPacket.data[outputPacket.length] = REPORT_SUCCESS;
|
||||
outputPacket.data[outputPacket.length + 1] = jvsIO->state.inputSwitch[0];
|
||||
outputPacket.data[outputPacket.length + 1] = io.state.inputSwitch[0];
|
||||
outputPacket.length += 2;
|
||||
for (int i = 0; i < inputPacket.data[index + 1]; i++)
|
||||
{
|
||||
for (int j = 0; j < inputPacket.data[index + 2]; j++)
|
||||
{
|
||||
outputPacket.data[outputPacket.length++] = jvsIO->state.inputSwitch[i + 1] >> (8 - (j * 8));
|
||||
outputPacket.data[outputPacket.length++] = io.state.inputSwitch[i + 1] >> (8 - (j * 8));
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -279,8 +279,8 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
|
||||
for (int i = 0; i < numberCoinSlots; i++)
|
||||
{
|
||||
outputPacket.data[outputPacket.length] = (jvsIO->state.coinCount[i] << 8) & 0x1F;
|
||||
outputPacket.data[outputPacket.length + 1] = jvsIO->state.coinCount[i] & 0xFF;
|
||||
outputPacket.data[outputPacket.length] = (io.state.coinCount[i] << 8) & 0x1F;
|
||||
outputPacket.data[outputPacket.length + 1] = io.state.coinCount[i] & 0xFF;
|
||||
outputPacket.length += 2;
|
||||
}
|
||||
}
|
||||
@ -296,7 +296,7 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
for (int i = 0; i < inputPacket.data[index + 1]; i++)
|
||||
{
|
||||
/* By default left align the data */
|
||||
int analogueData = jvsIO->state.analogueChannel[i] << jvsIO->analogueRestBits;
|
||||
int analogueData = io.state.analogueChannel[i] << io.analogueRestBits;
|
||||
outputPacket.data[outputPacket.length] = analogueData >> 8;
|
||||
outputPacket.data[outputPacket.length + 1] = analogueData;
|
||||
outputPacket.length += 2;
|
||||
@ -313,8 +313,8 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
|
||||
for (int i = 0; i < inputPacket.data[index + 1]; i++)
|
||||
{
|
||||
outputPacket.data[outputPacket.length] = jvsIO->state.rotaryChannel[i] >> 8;
|
||||
outputPacket.data[outputPacket.length + 1] = jvsIO->state.rotaryChannel[i];
|
||||
outputPacket.data[outputPacket.length] = io.state.rotaryChannel[i] >> 8;
|
||||
outputPacket.data[outputPacket.length + 1] = io.state.rotaryChannel[i];
|
||||
outputPacket.length += 2;
|
||||
}
|
||||
}
|
||||
@ -414,9 +414,9 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
outputPacket.data[outputPacket.length++] = REPORT_SUCCESS;
|
||||
|
||||
/* Prevent overflow of coins */
|
||||
if (coin_increment + jvsIO->state.coinCount[slot_index] > 16383)
|
||||
coin_increment = 16383 - jvsIO->state.coinCount[slot_index];
|
||||
jvsIO->state.coinCount[slot_index] += coin_increment;
|
||||
if (coin_increment + io.state.coinCount[slot_index] > 16383)
|
||||
coin_increment = 16383 - io.state.coinCount[slot_index];
|
||||
io.state.coinCount[slot_index] += coin_increment;
|
||||
}
|
||||
break;
|
||||
|
||||
@ -439,9 +439,9 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
outputPacket.data[outputPacket.length++] = REPORT_SUCCESS;
|
||||
|
||||
/* Prevent underflow of coins */
|
||||
if (coin_decrement > jvsIO->state.coinCount[slot_index])
|
||||
coin_decrement = jvsIO->state.coinCount[slot_index];
|
||||
jvsIO->state.coinCount[slot_index] -= coin_decrement;
|
||||
if (coin_decrement > io.state.coinCount[slot_index])
|
||||
coin_decrement = io.state.coinCount[slot_index];
|
||||
io.state.coinCount[slot_index] -= coin_decrement;
|
||||
}
|
||||
break;
|
||||
|
||||
@ -462,23 +462,6 @@ JVSStatus processPacket(JVSIO *jvsIO)
|
||||
}
|
||||
break;
|
||||
|
||||
/* The touch screen and light gun input, simply using analogue channels */
|
||||
case CMD_READ_LIGHTGUN:
|
||||
{
|
||||
////printf("CMD_READ_LIGHTGUN\n");
|
||||
size = 2;
|
||||
|
||||
int analogueXData = jvsIO->state.gunChannel[0] << jvsIO->gunXRestBits;
|
||||
int analogueYData = jvsIO->state.gunChannel[1] << jvsIO->gunYRestBits;
|
||||
outputPacket.data[outputPacket.length] = REPORT_SUCCESS;
|
||||
outputPacket.data[outputPacket.length + 1] = analogueXData >> 8;
|
||||
outputPacket.data[outputPacket.length + 2] = analogueXData;
|
||||
outputPacket.data[outputPacket.length + 3] = analogueYData >> 8;
|
||||
outputPacket.data[outputPacket.length + 4] = analogueYData;
|
||||
outputPacket.length += 5;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
{
|
||||
printf("Error: JVS command not supported [0x%02hhX]\n", inputPacket.data[index]);
|
||||
@ -624,34 +607,34 @@ int getSenseLine()
|
||||
return senseLine;
|
||||
}
|
||||
|
||||
int setSwitch(JVSIO *io, JVSPlayer player, JVSInput switchNumber, int value)
|
||||
int setSwitch(JVSPlayer player, JVSInput switchNumber, int value)
|
||||
{
|
||||
if (player > io->capabilities.players)
|
||||
if (player > io.capabilities.players)
|
||||
return 0;
|
||||
|
||||
if (value)
|
||||
{
|
||||
io->state.inputSwitch[player] |= switchNumber;
|
||||
io.state.inputSwitch[player] |= switchNumber;
|
||||
}
|
||||
else
|
||||
{
|
||||
io->state.inputSwitch[player] &= ~switchNumber;
|
||||
io.state.inputSwitch[player] &= ~switchNumber;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
int incrementCoin(JVSIO *io, JVSPlayer player, int amount)
|
||||
int incrementCoin(JVSPlayer player, int amount)
|
||||
{
|
||||
if (player == SYSTEM)
|
||||
return 0;
|
||||
|
||||
io->state.coinCount[player - 1] = io->state.coinCount[player - 1] + amount;
|
||||
io.state.coinCount[player - 1] = io.state.coinCount[player - 1] + amount;
|
||||
return 1;
|
||||
}
|
||||
|
||||
int setAnalogue(JVSIO *io, JVSInput channel, int value)
|
||||
int setAnalogue(JVSInput channel, int value)
|
||||
{
|
||||
io->state.analogueChannel[channel] = value;
|
||||
io.state.analogueChannel[channel] = value;
|
||||
return 1;
|
||||
}
|
||||
|
@ -223,7 +223,7 @@ typedef enum
|
||||
|
||||
int initJVS();
|
||||
|
||||
JVSStatus processPacket(JVSIO *jvsIO);
|
||||
JVSStatus processPacket();
|
||||
|
||||
JVSStatus readPacket(JVSPacket *packet);
|
||||
JVSStatus writePacket(JVSPacket *packet);
|
||||
@ -239,9 +239,9 @@ int getSenseLine();
|
||||
JVSCapabilities *getCapabilities();
|
||||
JVSState *getState();
|
||||
|
||||
int initIO(JVSIO *io);
|
||||
int setSwitch(JVSIO *io, JVSPlayer player, JVSInput switchNumber, int value);
|
||||
int incrementCoin(JVSIO *io, JVSPlayer player, int amount);
|
||||
int setAnalogue(JVSIO *io, JVSInput channel, int value);
|
||||
int initIO();
|
||||
int setSwitch(JVSPlayer player, JVSInput switchNumber, int value);
|
||||
int incrementCoin(JVSPlayer player, int amount);
|
||||
int setAnalogue(JVSInput channel, int value);
|
||||
|
||||
#endif // JVS_H_
|
||||
|
91
src/lindbergh/securityboard.c
Normal file
91
src/lindbergh/securityboard.c
Normal file
@ -0,0 +1,91 @@
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "securityboard.h"
|
||||
|
||||
#define SECURITY_BOARD_FRONT_PANEL 0x38
|
||||
#define SECURITY_BOARD_KEYCHIP 0xFF
|
||||
|
||||
#define DIP_SWITCH_ROTATION 2
|
||||
|
||||
typedef struct
|
||||
{
|
||||
int serviceSwitch;
|
||||
int testSwitch;
|
||||
int dipSwitch[8];
|
||||
int led[2];
|
||||
} SecurityBoard;
|
||||
|
||||
SecurityBoard securityBoard = {0};
|
||||
|
||||
int initSecurityBoard()
|
||||
{
|
||||
securityBoard.dipSwitch[DIP_SWITCH_ROTATION] = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int securityBoardSetRotation(int rotation)
|
||||
{
|
||||
securityBoard.dipSwitch[DIP_SWITCH_ROTATION] = rotation;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int securityBoardSetSwitch(JVSInput switchNumber, int value)
|
||||
{
|
||||
switch (switchNumber)
|
||||
{
|
||||
case BUTTON_TEST:
|
||||
securityBoard.testSwitch = value;
|
||||
break;
|
||||
case BUTTON_SERVICE:
|
||||
securityBoard.serviceSwitch = value;
|
||||
break;
|
||||
default:
|
||||
printf("Error: Attempted to set a security board switch incorrectly");
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int securityBoardOut(uint16_t port, uint32_t *data)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int securityBoardIn(uint16_t port, uint32_t *data)
|
||||
{
|
||||
switch (port)
|
||||
{
|
||||
case SECURITY_BOARD_FRONT_PANEL:
|
||||
uint32_t result = 0xFFFFFFFF;
|
||||
|
||||
if (securityBoard.serviceSwitch)
|
||||
result &= ~0x08;
|
||||
if (securityBoard.testSwitch)
|
||||
result &= ~0x04;
|
||||
if (securityBoard.dipSwitch[7])
|
||||
result &= ~0x800;
|
||||
if (securityBoard.dipSwitch[0])
|
||||
result &= ~0x400;
|
||||
if (securityBoard.dipSwitch[1])
|
||||
result &= ~0x200;
|
||||
if (securityBoard.dipSwitch[2])
|
||||
result &= ~0x100;
|
||||
if (securityBoard.dipSwitch[3])
|
||||
result &= ~0x80;
|
||||
if (securityBoard.dipSwitch[4])
|
||||
result &= ~0x40;
|
||||
if (securityBoard.dipSwitch[5])
|
||||
result &= ~0x20;
|
||||
if (securityBoard.dipSwitch[6])
|
||||
result &= ~0x10;
|
||||
|
||||
*data = result;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
10
src/lindbergh/securityboard.h
Normal file
10
src/lindbergh/securityboard.h
Normal file
@ -0,0 +1,10 @@
|
||||
#include <stdint.h>
|
||||
|
||||
#include "jvs.h"
|
||||
|
||||
int initSecurityBoard();
|
||||
int securityBoardOut(uint16_t port, uint32_t *data);
|
||||
int securityBoardIn(uint16_t port, uint32_t *data);
|
||||
int securityBoardSetSwitch(JVSInput switchNumber, int value);
|
||||
int securityBoardSetRotation(int rotation);
|
||||
int securityBoardSetDipSwitch(int switchNumber, int value);
|
Loading…
x
Reference in New Issue
Block a user