All cross-platform sys.c implementation (#455)

* adds missing fatalerror constant usage

* removes win95 polyfill bits

* tidies up dossys a little
This commit is contained in:
Dethrace Engineering Department 2025-06-16 21:49:06 +12:00 committed by GitHub
parent e852d1b9e7
commit 6cbc054790
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
25 changed files with 1538 additions and 1204 deletions

View File

@ -164,21 +164,16 @@ target_sources(dethrace_obj PRIVATE
# dethrace-added cross platform sys and network implementation
pc-all/allnet.c
# added in future PR
# pc-all/allsys.c
pc-all/allsys.c
# original win95 sys and network
# pc-win95/win95sys.c
# pc-win95/ssdx.c
# pc-win95/ssdx.h
# todo remove from normal compile
pc-win95/dinput.h
# original dos sys and network
#pc-dos/dosnet.c
# todo remove from normal compile
pc-dos/dossys.c
# pc-dos/dossys.c
)
# Create our main game binary.

View File

@ -234,7 +234,7 @@ void DeviouslyDimRectangle(br_pixelmap* pPixelmap, int pLeft, int pTop, int pRig
LOG_TRACE("(%p, %d, %d, %d, %d, %d)", pPixelmap, pLeft, pTop, pRight, pBottom, pKnock_out_corners);
if (pPixelmap != gBack_screen) {
FatalError(124);
FatalError(kFatalError_CanOnlyDimRectanglesOfgBack_screen);
}
gDim_model->vertices[1].p.v[0] = pLeft;

View File

@ -354,7 +354,7 @@ void InitLineStuff(void) {
gLine_material = BrMaterialAllocate("gLine_material");
gLine_actor = BrActorAllocate(BR_ACTOR_MODEL, NULL);
if (!gLine_model || !gLine_material || !gLine_actor) {
FatalError(94);
FatalError(kFatalError_OOMCarmageddon_S);
}
gLine_actor->identifier = "gLine_actor";
gLine_actor->render_style = BR_RSTYLE_EDGES;
@ -387,7 +387,7 @@ void InitSmokeStuff(void) {
gBlend_material = BrMaterialAllocate("gBlend_material");
gBlend_actor = BrActorAllocate(BR_ACTOR_MODEL, NULL);
if (!gBlend_model || !gBlend_material || !gBlend_actor) {
FatalError(94);
FatalError(kFatalError_OOMCarmageddon_S);
}
gBlend_actor->identifier = "gBlend_actor";
gBlend_actor->model = gBlend_model;
@ -418,7 +418,7 @@ void InitSmokeStuff(void) {
PathCat(path, path, "SMOKE.PIX");
gBlend_material->colour_map = DRPixelmapLoad(path);
if (!gBlend_material->colour_map) {
FatalError(79, path);
FatalError(kFatalError_LoadPixelmapFile_S, path);
}
gBlend_material->colour_map->map = gRender_palette;
BrMapAdd(gBlend_material->colour_map);
@ -452,7 +452,7 @@ void Init2DStuff(void) {
gPrat_material = BrMaterialAllocate("gPrat_material");
gPrat_actor = BrActorAllocate(BR_ACTOR_MODEL, NULL);
if (!gDim_model || !gDim_material || !gDim_actor || !gPrat_model || !gPrat_material || !gPrat_actor || !g2d_camera) {
FatalError(94);
FatalError(kFatalError_OOMCarmageddon_S);
}
g2d_camera->identifier = "g2d_camera";
camera = g2d_camera->type_data;

View File

@ -64,8 +64,6 @@ void QuitGame(void) {
#endif
PDShutdownSystem();
CloseDiagnostics();
exit(0);
}
// IDA: tU32 __cdecl TrackCount(br_actor *pActor, tU32 *pCount)

View File

@ -1063,7 +1063,7 @@ br_pixelmap* PaletteOf16Bits(br_pixelmap* pSrc) {
if (g16bit_palette == NULL) {
g16bit_palette = BrPixelmapAllocate(BR_PMT_RGB_565, 1, 256, g16bit_palette, 0);
if (g16bit_palette == NULL) {
FatalError(94, "16-bit palette");
FatalError(kFatalError_OOMCarmageddon_S, "16-bit palette");
}
}
if (!g16bit_palette_valid || pSrc != gSource_for_16bit_palette) {

View File

@ -2425,11 +2425,11 @@ void LoadExceptionsFile(char* pName) {
GetALineAndDontArgue(f, line);
tok = strtok(line, delimiters);
if (DRStricmp(tok, "VERSION")) {
FatalError(120, pName, "VERSION");
FatalError(kFatalError_FileMustStartWith_S, pName, "VERSION");
}
tok = strtok(NULL, delimiters);
if (sscanf(tok, "%d", &file_version) == 0 || file_version != 1) {
FatalError(121, tok, pName);
FatalError(kFatalError_CantCopeWithVersionFor_S, tok, pName);
}
while (1) {
@ -2456,7 +2456,7 @@ void LoadExceptionsFile(char* pName) {
} else if (DRStricmp(tok, "quadruple") == 0) {
e->flags |= ExceptionFlag_Quadruple;
} else {
FatalError(123, tok, pName);
FatalError(kFatalError_Mysterious_S_S, tok, pName);
}
}
AddExceptionToList(&gExceptions, e);

View File

@ -470,6 +470,17 @@ enum {
kFatalError_NetContentsTooBig_S = 114,
kFatalError_FileCorrupt_S = 115,
kFatalError_RandomNumberOutOfRange_S = 116,
#ifdef DETHRACE_3DFX_PATCH
kFatalError_CouldntLockPixelmap_S = 117,
kFatalError_ShouldBeLockedButIsnt_S = 118,
kFatalError_CannotPurifyPixelmap_S = 119,
kFatalError_FileMustStartWith_S = 120,
kFatalError_CantCopeWithVersionFor_S = 121,
kFatalError_CannotTilePixelmap_S = 122,
kFatalError_Mysterious_S_S = 123,
kFatalError_CanOnlyDimRectanglesOfgBack_screen = 124,
kFatalError_InvalidMaterialAlpha = 125
#endif
};
enum {

View File

@ -285,6 +285,7 @@ int PDNetInitialise(void) {
gNumber_of_networks = 1;
sa_len = sizeof(struct sockaddr_in);
dr_dprintf("PDNetInitialise()");
gNumber_of_networks = 1;
memset(&gAny_addr, 0, sizeof(gAny_addr));
memset(&gLocal_addr, 0, sizeof(gLocal_addr));

1195
src/DETHRACE/pc-all/allsys.c Normal file

File diff suppressed because it is too large Load Diff

View File

@ -24,15 +24,7 @@
#include <sys/stat.h>
#include <time.h>
// This code comes from DOS, so small changes need to be made to run correctly on windowed systems.
// Generally the pc-win95 does the same thing
#define PLAY_NICE_WITH_GUI 1
#ifdef PLAY_NICE_WITH_GUI
#define MOUSE_SPEED_MULTIPLIER 1
#else
#define MOUSE_SPEED_MULTIPLIER 0.25f
#endif
// Based on VOODOO2C.EXE
int gDOSGfx_initialized;
int gExtra_mem;
@ -40,7 +32,6 @@ int gReplay_override;
tGraf_spec gGraf_specs[2] = {
{ 8, 1, 0, 320, 200, 0, 0, "32X20X8", "MCGA,W:320,H:200,B:8", 320, 320, 200, NULL },
{ 8, 1, 0, 640, 480, 0, 0, "64X48X8", "VESA,W:640,H:480,B:8", 640, 640, 480, NULL }
// { 8, 1, 0, 1920, 1080, 0, 0, "64X48X8", "VESA,W:640,H:480,B:8", 640, 1920, 1080, NULL }
};
int gASCII_table[128];
tU32 gKeyboard_bits[8];
@ -71,9 +62,6 @@ tU8 gScan_code[123][2];
int gForce_voodoo_rush_mode;
int gForce_voodoo_mode;
br_device_gl_callback_procs gl_callbacks;
br_device_virtualfb_callback_procs virtualfb_callbacks;
// forward declare for `PDInitialiseSystem`
int InitJoysticks(void);
@ -84,6 +72,8 @@ void KeyboardHandler(void) {
static tU8 extended;
LOG_TRACE("()");
NOT_IMPLEMENTED();
// dos code reads scancodes from interrupt
}
// IDA: int __usercall KeyDown@<EAX>(tU8 pScan_code@<EAX>)
@ -240,11 +230,6 @@ void PDSetKeyArray(int* pKeys, int pMark) {
tS32 joyY;
LOG_TRACE10("(%p, %d)", pKeys, pMark);
#ifdef PLAY_NICE_WITH_GUI
// Required in some cases like a tight loop waiting for a keypress
gHarness_platform.ProcessWindowMessages(NULL);
#endif
gKeys_pressed = 0;
for (i = 0; i < COUNT_OF(gScan_code); i++) {
if (KeyDown(gScan_code[i][0]) || KeyDown(gScan_code[i][1])) {
@ -278,9 +263,7 @@ void PDFatalError(char* pThe_str) {
}
printf("FATAL ERROR: %s\n", pThe_str);
dr_dprintf("FATAL ERROR: %s\n", pThe_str);
#ifdef PLAY_NICE_WITH_GUI
gHarness_platform.ShowErrorMessage(NULL, "Carmageddon Fatal Error", pThe_str);
#endif
if (gBrZb_initialized) {
gBrZb_initialized = 0;
BrZbEnd();
@ -288,11 +271,9 @@ void PDFatalError(char* pThe_str) {
if (gBr_initialized) {
gBr_initialized = 0;
}
#ifndef PLAY_NICE_WITH_GUI
// There is no window to receive keyboard events from
while (PDAnyKeyDown() == -1) {
}
#endif
QuitGame();
}
@ -395,7 +376,7 @@ void PDLockRealBackScreen(int lock) {
sub_B4DB4();
BrPixelmapDirectLock(gReal_back_screen, 1);
if (!gReal_back_screen->pixels)
FatalError(117, "gReal_back_screen");
FatalError(kFatalError_CouldntLockPixelmap_S, "gReal_back_screen");
gReal_back_screen_locked = 1;
}
}
@ -416,27 +397,8 @@ void PDAllocateScreenAndBack(void) {
gScreen = NULL;
// added by dethrace. We default to software mode unless we explicitly ask for 3dfx opengl mode
if (harness_game_config.opengl_3dfx_mode) {
if (gGraf_spec_index != 0 && !gNo_voodoo) {
#ifdef PLAY_NICE_WITH_GUI
gl_callbacks.get_proc_address = gHarness_platform.GL_GetProcAddress;
gl_callbacks.swap_buffers = gHarness_platform.Swap;
gl_callbacks.get_viewport = gHarness_platform.GetViewport;
gHarness_platform.CreateWindow_("Carmageddon", gGraf_specs[gGraf_spec_index].phys_width, gGraf_specs[gGraf_spec_index].phys_height, eWindow_type_opengl);
BrDevBeginVar(&gScreen, "glrend",
BRT_WIDTH_I32, gGraf_specs[gGraf_spec_index].phys_width,
BRT_HEIGHT_I32, gGraf_specs[gGraf_spec_index].phys_height,
BRT_OPENGL_CALLBACKS_P, &gl_callbacks,
BRT_PIXEL_TYPE_U8, BR_PMT_RGB_565,
BR_NULL_TOKEN);
#else
BrDevBegin(&gScreen, "3dfx_dos,w:640,h:480,b:16");
#endif
}
if (gGraf_spec_index != 0 && !gNo_voodoo) {
BrDevBegin(&gScreen, "3dfx_dos,w:640,h:480,b:16");
}
if (gScreen != NULL) {
@ -466,19 +428,7 @@ void PDAllocateScreenAndBack(void) {
gInterpolate_textures = 1;
gExceptions_general_file = "SOFTWARE";
#ifdef PLAY_NICE_WITH_GUI
// Render framebuffer to memory and call hooks when swapping or palette changing
virtualfb_callbacks.palette_changed = gHarness_platform.PaletteChanged;
virtualfb_callbacks.swap_buffers = gHarness_platform.Swap;
gHarness_platform.CreateWindow_("Carmageddon", gGraf_specs[gGraf_spec_index].phys_width, gGraf_specs[gGraf_spec_index].phys_height, eWindow_type_software);
BrDevBeginVar(&gScreen, "virtualframebuffer",
BRT_WIDTH_I32, gGraf_specs[gGraf_spec_index].phys_width,
BRT_HEIGHT_I32, gGraf_specs[gGraf_spec_index].phys_height,
BRT_VIRTUALFB_CALLBACKS_P, &virtualfb_callbacks,
BR_NULL_TOKEN);
#else
gScreen = BrDevBeginOld(gGraf_specs[gGraf_spec_index].gfx_init_string);
#endif
gDOSGfx_initialized = 1;
}
gScreen->origin_x = 0;
@ -541,7 +491,7 @@ void Double8BitTo16BitPixelmap(br_pixelmap* pDst, br_pixelmap* pSrc, br_pixelmap
palette_entry = PaletteOf16Bits(pPalette)->pixels;
if (pSrc_width > 640) {
FatalError(94, "Double8BitTo16BitPixelmap");
FatalError(kFatalError_OOMCarmageddon_S, "Double8BitTo16BitPixelmap");
}
dst_y = 0;
for (y = 0; y < pSrc_height; y++) {
@ -756,8 +706,8 @@ void PDGetMousePosition(int* pX_coord, int* pY_coord) {
delta_x = mouse_x - gMouse_last_x_coord;
delta_y = mouse_y - gMouse_last_y_coord;
*pX_coord = gMouse_last_x_coord + (MOUSE_SPEED_MULTIPLIER * delta_x);
*pY_coord = gMouse_last_y_coord + (MOUSE_SPEED_MULTIPLIER * delta_y);
*pX_coord = gMouse_last_x_coord + (0.25f * delta_x);
*pY_coord = gMouse_last_y_coord + (0.25f * delta_y);
}
}
@ -768,11 +718,6 @@ int PDGetTotalTime(void) {
// IDA: int __usercall PDServiceSystem@<EAX>(tU32 pTime_since_last_call@<EAX>)
int PDServiceSystem(tU32 pTime_since_last_call) {
#ifdef PLAY_NICE_WITH_GUI
// Added by dethrace. Win95 code does the same
gHarness_platform.ProcessWindowMessages(NULL);
#endif
return 0;
}

View File

@ -1,153 +0,0 @@
/****************************************************************************
*
* DirectInput keyboard scan codes
*
****************************************************************************/
#define DIK_ESCAPE 0x01
#define DIK_1 0x02
#define DIK_2 0x03
#define DIK_3 0x04
#define DIK_4 0x05
#define DIK_5 0x06
#define DIK_6 0x07
#define DIK_7 0x08
#define DIK_8 0x09
#define DIK_9 0x0A
#define DIK_0 0x0B
#define DIK_MINUS 0x0C /* - on main keyboard */
#define DIK_EQUALS 0x0D
#define DIK_BACK 0x0E /* backspace */
#define DIK_TAB 0x0F
#define DIK_Q 0x10
#define DIK_W 0x11
#define DIK_E 0x12
#define DIK_R 0x13
#define DIK_T 0x14
#define DIK_Y 0x15
#define DIK_U 0x16
#define DIK_I 0x17
#define DIK_O 0x18
#define DIK_P 0x19
#define DIK_LBRACKET 0x1A
#define DIK_RBRACKET 0x1B
#define DIK_RETURN 0x1C /* Enter on main keyboard */
#define DIK_LCONTROL 0x1D
#define DIK_A 0x1E
#define DIK_S 0x1F
#define DIK_D 0x20
#define DIK_F 0x21
#define DIK_G 0x22
#define DIK_H 0x23
#define DIK_J 0x24
#define DIK_K 0x25
#define DIK_L 0x26
#define DIK_SEMICOLON 0x27
#define DIK_APOSTROPHE 0x28
#define DIK_GRAVE 0x29 /* accent grave */
#define DIK_LSHIFT 0x2A
#define DIK_BACKSLASH 0x2B
#define DIK_Z 0x2C
#define DIK_X 0x2D
#define DIK_C 0x2E
#define DIK_V 0x2F
#define DIK_B 0x30
#define DIK_N 0x31
#define DIK_M 0x32
#define DIK_COMMA 0x33
#define DIK_PERIOD 0x34 /* . on main keyboard */
#define DIK_SLASH 0x35 /* / on main keyboard */
#define DIK_RSHIFT 0x36
#define DIK_MULTIPLY 0x37 /* * on numeric keypad */
#define DIK_LMENU 0x38 /* left Alt */
#define DIK_SPACE 0x39
#define DIK_CAPITAL 0x3A
#define DIK_F1 0x3B
#define DIK_F2 0x3C
#define DIK_F3 0x3D
#define DIK_F4 0x3E
#define DIK_F5 0x3F
#define DIK_F6 0x40
#define DIK_F7 0x41
#define DIK_F8 0x42
#define DIK_F9 0x43
#define DIK_F10 0x44
#define DIK_NUMLOCK 0x45
#define DIK_SCROLL 0x46 /* Scroll Lock */
#define DIK_NUMPAD7 0x47
#define DIK_NUMPAD8 0x48
#define DIK_NUMPAD9 0x49
#define DIK_SUBTRACT 0x4A /* - on numeric keypad */
#define DIK_NUMPAD4 0x4B
#define DIK_NUMPAD5 0x4C
#define DIK_NUMPAD6 0x4D
#define DIK_ADD 0x4E /* + on numeric keypad */
#define DIK_NUMPAD1 0x4F
#define DIK_NUMPAD2 0x50
#define DIK_NUMPAD3 0x51
#define DIK_NUMPAD0 0x52
#define DIK_DECIMAL 0x53 /* . on numeric keypad */
#define DIK_OEM_102 0x56 /* <> or \| on RT 102-key keyboard (Non-U.S.) */
#define DIK_F11 0x57
#define DIK_F12 0x58
#define DIK_F13 0x64 /* (NEC PC98) */
#define DIK_F14 0x65 /* (NEC PC98) */
#define DIK_F15 0x66 /* (NEC PC98) */
#define DIK_KANA 0x70 /* (Japanese keyboard) */
#define DIK_ABNT_C1 0x73 /* /? on Brazilian keyboard */
#define DIK_CONVERT 0x79 /* (Japanese keyboard) */
#define DIK_NOCONVERT 0x7B /* (Japanese keyboard) */
#define DIK_YEN 0x7D /* (Japanese keyboard) */
#define DIK_ABNT_C2 0x7E /* Numpad . on Brazilian keyboard */
#define DIK_NUMPADEQUALS 0x8D /* = on numeric keypad (NEC PC98) */
#define DIK_PREVTRACK 0x90 /* Previous Track (DIK_CIRCUMFLEX on Japanese keyboard) */
#define DIK_AT 0x91 /* (NEC PC98) */
#define DIK_COLON 0x92 /* (NEC PC98) */
#define DIK_UNDERLINE 0x93 /* (NEC PC98) */
#define DIK_KANJI 0x94 /* (Japanese keyboard) */
#define DIK_STOP 0x95 /* (NEC PC98) */
#define DIK_AX 0x96 /* (Japan AX) */
#define DIK_UNLABELED 0x97 /* (J3100) */
#define DIK_NEXTTRACK 0x99 /* Next Track */
#define DIK_NUMPADENTER 0x9C /* Enter on numeric keypad */
#define DIK_RCONTROL 0x9D
#define DIK_MUTE 0xA0 /* Mute */
#define DIK_CALCULATOR 0xA1 /* Calculator */
#define DIK_PLAYPAUSE 0xA2 /* Play / Pause */
#define DIK_MEDIASTOP 0xA4 /* Media Stop */
#define DIK_VOLUMEDOWN 0xAE /* Volume - */
#define DIK_VOLUMEUP 0xB0 /* Volume + */
#define DIK_WEBHOME 0xB2 /* Web home */
#define DIK_NUMPADCOMMA 0xB3 /* , on numeric keypad (NEC PC98) */
#define DIK_DIVIDE 0xB5 /* / on numeric keypad */
#define DIK_SYSRQ 0xB7
#define DIK_RMENU 0xB8 /* right Alt */
#define DIK_PAUSE 0xC5 /* Pause */
#define DIK_HOME 0xC7 /* Home on arrow keypad */
#define DIK_UP 0xC8 /* UpArrow on arrow keypad */
#define DIK_PRIOR 0xC9 /* PgUp on arrow keypad */
#define DIK_LEFT 0xCB /* LeftArrow on arrow keypad */
#define DIK_RIGHT 0xCD /* RightArrow on arrow keypad */
#define DIK_END 0xCF /* End on arrow keypad */
#define DIK_DOWN 0xD0 /* DownArrow on arrow keypad */
#define DIK_NEXT 0xD1 /* PgDn on arrow keypad */
#define DIK_INSERT 0xD2 /* Insert on arrow keypad */
#define DIK_DELETE 0xD3 /* Delete on arrow keypad */
/*
* Alternate names for keys, to facilitate transition from DOS.
*/
#define DIK_BACKSPACE DIK_BACK /* backspace */
#define DIK_NUMPADSTAR DIK_MULTIPLY /* * on numeric keypad */
#define DIK_LALT DIK_LMENU /* left Alt */
#define DIK_CAPSLOCK DIK_CAPITAL /* CapsLock */
#define DIK_NUMPADMINUS DIK_SUBTRACT /* - on numeric keypad */
#define DIK_NUMPADPLUS DIK_ADD /* + on numeric keypad */
#define DIK_NUMPADPERIOD DIK_DECIMAL /* . on numeric keypad */
#define DIK_NUMPADSLASH DIK_DIVIDE /* / on numeric keypad */
#define DIK_RALT DIK_RMENU /* right Alt */
#define DIK_UPARROW DIK_UP /* UpArrow on arrow keypad */
#define DIK_PGUP DIK_PRIOR /* PgUp on arrow keypad */
#define DIK_LEFTARROW DIK_LEFT /* LeftArrow on arrow keypad */
#define DIK_RIGHTARROW DIK_RIGHT /* RightArrow on arrow keypad */
#define DIK_DOWNARROW DIK_DOWN /* DownArrow on arrow keypad */
#define DIK_PGDN DIK_NEXT /* PgDn on arrow keypad */

View File

@ -69,7 +69,7 @@ void PDSetKeyArray(int* pKeys, int pMark);
int PDGetASCIIFromKey(int pKey);
HARNESS_NORETURN void PDFatalError(char* pThe_str);
void PDFatalError(char* pThe_str);
void PDNonFatalError(char* pThe_str);

View File

@ -74,7 +74,7 @@ endif()
if(DETHRACE_PLATFORM_SDL2)
target_sources(harness PRIVATE
platforms/sdl2.c
platforms/sdl2_scancode_to_dinput.h
platforms/sdl_scancode_map.h
platforms/sdl2_syms.h
)
target_compile_definitions(harness PRIVATE DETHRACE_PLATFORM_SDL2)

View File

@ -0,0 +1,109 @@
#ifndef DETHRACE_SCANCODES_H
#define DETHRACE_SCANCODES_H
// These are copied from `KeyBegin`
// todo: remove duplication
#define SCANCODE_ESCAPE 0x01
#define SCANCODE_1 0x02
#define SCANCODE_2 0x03
#define SCANCODE_3 0x04
#define SCANCODE_4 0x05
#define SCANCODE_5 0x06
#define SCANCODE_6 0x07
#define SCANCODE_7 0x08
#define SCANCODE_8 0x09
#define SCANCODE_9 0x0A
#define SCANCODE_0 0x0B
#define SCANCODE_MINUS 0x0C /* - on main keyboard */
#define SCANCODE_EQUALS 0x0D
#define SCANCODE_BACK 0x0E /* backspace */
#define SCANCODE_TAB 0x0F
#define SCANCODE_Q 0x10
#define SCANCODE_W 0x11
#define SCANCODE_E 0x12
#define SCANCODE_R 0x13
#define SCANCODE_T 0x14
#define SCANCODE_Y 0x15
#define SCANCODE_U 0x16
#define SCANCODE_I 0x17
#define SCANCODE_O 0x18
#define SCANCODE_P 0x19
#define SCANCODE_LBRACKET 0x1A
#define SCANCODE_RBRACKET 0x1B
#define SCANCODE_RETURN 0x1C /* Enter on main keyboard */
#define SCANCODE_LCONTROL 0x1D
#define SCANCODE_A 0x1E
#define SCANCODE_S 0x1F
#define SCANCODE_D 0x20
#define SCANCODE_F 0x21
#define SCANCODE_G 0x22
#define SCANCODE_H 0x23
#define SCANCODE_J 0x24
#define SCANCODE_K 0x25
#define SCANCODE_L 0x26
#define SCANCODE_SEMICOLON 0x27
#define SCANCODE_APOSTROPHE 0x28
#define SCANCODE_GRAVE 0x29
#define SCANCODE_LSHIFT 0x2A
#define SCANCODE_BACKSLASH 0x2B
#define SCANCODE_Z 0x2C
#define SCANCODE_X 0x2D
#define SCANCODE_C 0x2E
#define SCANCODE_V 0x2F
#define SCANCODE_B 0x30
#define SCANCODE_N 0x31
#define SCANCODE_M 0x32
#define SCANCODE_COMMA 0x33
#define SCANCODE_PERIOD 0x34
#define SCANCODE_SLASH 0x35
#define SCANCODE_RSHIFT 0x36
#define SCANCODE_MULTIPLY 0x37 /* * on numeric keypad */
#define SCANCODE_LALT 0x38
#define SCANCODE_SPACE 0x39
#define SCANCODE_CAPITAL 0x3A
#define SCANCODE_F1 0x3B
#define SCANCODE_F2 0x3C
#define SCANCODE_F3 0x3D
#define SCANCODE_F4 0x3E
#define SCANCODE_F5 0x3F
#define SCANCODE_F6 0x40
#define SCANCODE_F7 0x41
#define SCANCODE_F8 0x42
#define SCANCODE_F9 0x43
#define SCANCODE_F10 0x44
#define SCANCODE_NUMLOCK 0x45
#define SCANCODE_SCROLL 0x46
#define SCANCODE_NUMPAD7 0x47
#define SCANCODE_NUMPAD8 0x48
#define SCANCODE_NUMPAD9 0x49
#define SCANCODE_SUBTRACT 0x4A /* - on numeric keypad */
#define SCANCODE_NUMPAD4 0x4B
#define SCANCODE_NUMPAD5 0x4C
#define SCANCODE_NUMPAD6 0x4D
#define SCANCODE_ADD 0x4E /* + on numeric keypad */
#define SCANCODE_NUMPAD1 0x4F
#define SCANCODE_NUMPAD2 0x50
#define SCANCODE_NUMPAD3 0x51
#define SCANCODE_NUMPAD0 0x52
#define SCANCODE_DECIMAL 0x53 /* . on numeric keypad */
#define SCANCODE_OEM_102 0x56 /* <> or \| on RT 102-key keyboard (Non-U.S.) */
#define SCANCODE_F11 0x57
#define SCANCODE_F12 0x58
#define SCANCODE_NUMPADENTER 0x9C /* Enter on numeric keypad */
#define SCANCODE_RCONTROL 0x9D
#define SCANCODE_DIVIDE 0xB5 /* / on numeric keypad */
#define SCANCODE_RALT 0xB8
#define SCANCODE_PAUSE 0xC5
#define SCANCODE_HOME 0xC7
#define SCANCODE_UP 0xC8
#define SCANCODE_PGUP 0xC9
#define SCANCODE_LEFT 0xCB
#define SCANCODE_RIGHT 0xCD
#define SCANCODE_END 0xCF
#define SCANCODE_DOWN 0xD0
#define SCANCODE_PGDN 0xD1
#define SCANCODE_INSERT 0xD2
#define SCANCODE_DELETE 0xD3
#endif

View File

@ -2,7 +2,6 @@
#define HARNESS_HOOKS_H
#include "brender.h"
#include "harness/win95_polyfill_defs.h"
#include <stdio.h>
typedef enum tHarness_window_type {
@ -15,27 +14,30 @@ typedef struct tHarness_platform {
// Render a fullscreen quad using the specified pixel data
void (*Renderer_Present)(br_pixelmap* src);
// Set the 256 color palette to use (BGRA format)
void (*Renderer_SetPalette)(PALETTEENTRY_* palette);
void (*Renderer_SetPalette)(br_colour* palette);
// Get mouse button state
int (*GetMouseButtons)(int* button_1, int* button_2);
// Get mouse position
int (*GetMousePosition)(int* pX, int* pY);
// Close specified window
void (*DestroyWindow)(void* window);
void (*DestroyWindow)(void);
// Process window messages, return any WM_QUIT message
void (*ProcessWindowMessages)(MSG_* msg);
void (*ProcessWindowMessages)(void);
// Set position of a window
int (*SetWindowPos)(void* hWnd, int x, int y, int nWidth, int nHeight);
// Show/hide the cursor
int (*ShowCursor)(int show);
// Get keyboard state. Expected to be in DirectInput key codes
void (*GetKeyboardState)(unsigned int count, uint8_t* buffer);
// invoked when key is set up or down
void (*SetKeyHandler)(void (*handler_func)(void));
// Get keyboard state. Argument expected to point to 32 byte buffer - 1 bit per key
void (*GetKeyboardState)(uint32_t* buffer);
// Sleep
void (*Sleep)(uint32_t dwMilliseconds);
// Get ticks
uint32_t (*GetTicks)(void);
// Show error message
int (*ShowErrorMessage)(void* window, char* text, char* caption);
int (*ShowErrorMessage)(char* title, char* message);
// Create a window. Uses an underscore to avoid name collisions with windows.h `CreateWindow` macro
void (*CreateWindow_)(const char* title, int nWidth, int nHeight, tHarness_window_type window_type);
@ -54,8 +56,8 @@ enum {
};
typedef struct tPlatform_bootstrap {
const char *name;
const char *description;
const char* name;
const char* description;
uint32_t capabilities;
int (*init)(tHarness_platform* platform);
} tPlatform_bootstrap;

View File

@ -1,88 +0,0 @@
#ifndef _POLYFILL_H_
#define _POLYFILL_H_
#include "harness/compiler.h"
#include "win95_polyfill_defs.h"
#include <assert.h>
#include <stdarg.h>
#include <stddef.h>
#include <stdint.h>
#include <stdio.h>
// All functions have a "_" suffix to avoid collisions with <windows.h>-defined types
uint32_t GetFileAttributesA_(char* path);
int SetFileAttributesA_(char* lpFileName, uint32_t dwFileAttributes);
void* CreateFileA_(
char* lpFileName,
uint32_t dwDesiredAccess,
uint32_t dwShareMode,
void* lpSecurityAttributes,
uint32_t dwCreationDisposition,
uint32_t dwFlagsAndAttributes,
void* hTemplateFile);
uint32_t GetFileSize_(
void* hFile,
uint32_t* lpFileSizeHigh);
int CloseHandle_(
void* hObject);
void GlobalMemoryStatus_(MEMORYSTATUS_* lpBuffer);
int GetCursorPos_(POINT_* lpPoint);
int ScreenToClient_(void* hWnd, POINT_* lpPoint);
uint32_t timeGetTime_(void);
uint32_t GetCurrentDirectoryA_(uint32_t nBufferLength, char* lpBuffer);
int SetCurrentDirectoryA_(char* lpPathName);
uint32_t GetShortPathNameA_(char* lpszLongPath, char* lpszShortPath, uint32_t cchBuffer);
HANDLE_ FindFirstFileA_(char* lpFileName, WIN32_FIND_DATAA_* lpFindFileData);
int FindNextFileA_(HANDLE_ hFindFile, WIN32_FIND_DATAA_* lpFindFileData);
int FindClose_(HANDLE_ hFindFile);
void* CreateWindowExA_(uint32_t dwExStyle, char* lpClassName, char* lpWindowName, uint32_t dwStyle, int X, int Y, int nWidth, int nHeight, void* hWndParent, void* hMenu, void* hInstance, void* lpParam);
int SetWindowPos_(void* hWnd, void* hWndInsertAfter, int X, int Y, int cx, int cy, unsigned int uFlags);
int ShowCursor_(int bShow);
int SendMessageA_(void* hWnd, unsigned int Msg, unsigned int wParam, long lParam);
int MessageBoxA_(void* hWnd, char* lpText, char* lpCaption, unsigned int uType);
int DestroyWindow_(void* hWnd);
HARNESS_NORETURN void ExitProcess_(unsigned int uExitCode);
void TranslateMessage_(MSG_* lpMsg);
void DispatchMessageA_(MSG_* lpMsg);
int PeekMessageA_(MSG_* lpMsg, void* hWnd, unsigned int wMsgFilterMin, unsigned int wMsgFilterMax, unsigned int wRemoveMsg);
int GetMessageA_(MSG_* lpMsg, void* hWnd, unsigned int wMsgFilterMin, unsigned int wMsgFilterMax);
void Sleep_(uint32_t dwMilliseconds);
void DirectDraw_CreateSurface(int width, int height);
void DirectDrawDevice_SetPaletteEntries(PALETTEENTRY_* palette, int pFirst_colour, int pCount);
void DirectInputDevice_GetDeviceState(unsigned int keys, uint8_t* buffer);
void _splitpath_(char* path, char* drive, char* dir, char* fname, char* ext);
int _CrtDbgReport_(int reportType, const char* filename, int linenumber, const char* moduleName, const char* format, ...);
#endif

View File

@ -1,74 +0,0 @@
#ifndef WIN95_POLYFILL_TYPES_H
#define WIN95_POLYFILL_TYPES_H
#include <stddef.h>
#include <stdint.h>
typedef void* HANDLE_;
#define GENERIC_READ 0x80000000
#define OPEN_EXISTING 3
#define FILE_ATTRIBUTE_NORMAL 0x80
#define INVALID_HANDLE_VALUE ((HANDLE_*)-1)
#define INVALID_FILE_ATTRIBUTES -1
#define FILE_ATTRIBUTE_READONLY 0x01
#define FILE_ATTRIBUTE_NORMAL 0x80
#define HWND_BROADCAST ((void*)0xffff)
#define _CRT_ASSERT 2
#define WM_QUIT 0x0012
#define MB_ICONERROR 0x00000010
typedef struct _MEMORYSTATUS_ {
uint32_t dwLength;
uint32_t dwMemoryLoad;
size_t dwTotalPhys;
size_t dwAvailPhys;
size_t dwTotalPageFile;
size_t dwAvailPageFile;
size_t dwTotalVirtual;
size_t dwAvailVirtual;
} MEMORYSTATUS_;
typedef struct tagPOINT_ {
long x;
long y;
} POINT_;
#pragma pack(push, 1)
typedef struct tagPALETTEENTRY_ {
uint8_t peRed;
uint8_t peGreen;
uint8_t peBlue;
uint8_t peFlags;
} PALETTEENTRY_;
#pragma pack(pop)
typedef struct _WIN32_FIND_DATA_ {
// uint32_t dwFileAttributes;
// FILETIME ftCreationTime;
// FILETIME ftLastAccessTime;
// FILETIME ftLastWriteTime;
// uint32_t nFileSizeHigh;
// uint32_t nFileSizeLow;
// uint32_t dwReserved0;
// uint32_t dwReserved1;
char cFileName[1024];
// char cAlternateFileName[14];
} WIN32_FIND_DATAA_;
typedef struct tagMSG_ {
void* hwnd;
unsigned int message;
int wParam;
long lParam;
uint32_t time;
POINT_ pt;
uint32_t lPrivate;
} MSG_;
#endif

View File

@ -1,52 +0,0 @@
/*
* Inspiration taken from https://github.com/TheAssemblyArmada/Vanilla-Conquer/blob/vanilla/common/sockets.h
*/
#ifndef HARNESS_WINSOCK_H
#define HARNESS_WINSOCK_H
#include <assert.h>
#ifdef _WIN32
#define _WINSOCK_DEPRECATED_NO_WARNINGS
#include <winsock2.h>
#include <ws2tcpip.h>
#else /* Assume posix style sockets on non-windows */
#include <arpa/inet.h>
#include <errno.h>
#include <fcntl.h>
#include <netdb.h> // for getaddrinfo() and freeaddrinfo()
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <unistd.h> // for close()
#define WSAEISCONN EISCONN
#define WSAEINPROGRESS EINPROGRESS
#define WSAEALREADY EALREADY
#define WSAEADDRINUSE EADDRINUSE
#define WSAEADDRNOTAVAIL EADDRNOTAVAIL
#define WSAEBADF EBADF
#define WSAECONNREFUSED ECONNREFUSED
#define WSAEINTR EINTR
#define WSAENOTSOCK ENOTSOCK
#define WSAEWOULDBLOCK EWOULDBLOCK
#define WSAEINVAL EINVAL
#define WSAETIMEDOUT ETIMEDOUT
#define MAKEWORD(x, y) ((y) << 8 | (x))
typedef struct WSADATA {
} WSADATA;
int WSAStartup(int version, WSADATA* data);
int WSAGetLastError(void);
int WSACleanup(void);
int ioctlsocket(int handle, long cmd, unsigned long* argp);
int closesocket(int handle);
#endif /* _WIN32 */
#endif

View File

@ -7,20 +7,20 @@ static int null_set_window_pos(void* hWnd, int x, int y, int nWidth, int nHeight
return 0;
}
static void null_destroy_window(void* hWnd) {
static void null_destroy_window(void) {
null_time += 1;
}
static int null_show_error_message(void* window, char* text, char* caption) {
static int null_show_error_message(char* title, char* text) {
null_time += 1;
return 0;
}
static void null_get_and_handle_message(MSG_* msg) {
static void null_get_and_handle_message(void) {
null_time += 1;
}
static void null_get_keyboard_state(unsigned int count, uint8_t* buffer) {
static void null_get_keyboard_state(uint32_t* buffer) {
null_time += 1;
}
@ -39,7 +39,7 @@ static int null_show_cursor(int show) {
return 0;
}
static void null_set_palette(PALETTEENTRY_* palette) {
static void null_set_palette(br_colour* palette) {
null_time += 1;
}

View File

@ -15,7 +15,10 @@ static br_pixelmap* last_screen_src;
static Uint32 last_frame_time;
static uint8_t directinput_key_state[SDLK_LAST];
static void (*gKeyHandler_func)(void);
// 32 bytes, 1 bit per key. Matches dos executable behavior
static uint32_t key_state[8];
static struct {
int x, y;
@ -24,25 +27,24 @@ static struct {
// Callbacks back into original game code
extern void QuitGame(void);
extern uint32_t gKeyboard_bits[8];
extern br_pixelmap* gBack_screen;
static int window_width, window_height;
#ifdef DETHRACE_SDL_DYNAMIC
#ifdef _WIN32
static const char * const possible_locations[] = {
static const char* const possible_locations[] = {
"SDL.dll",
};
#elif defined(__APPLE__)
#define SHARED_OBJECT_NAME "libSDL"
#define SDL1_LIBNAME "libSDL.dylib"
static const char * const possible_locations[] = {
"@loader_path/" SDL1_LIBNAME, /* MyApp.app/Contents/MacOS/libSDL2_dylib */
static const char* const possible_locations[] = {
"@loader_path/" SDL1_LIBNAME, /* MyApp.app/Contents/MacOS/libSDL2_dylib */
"@executable_path/" SDL1_LIBNAME, /* MyApp.app/Contents/MacOS/libSDL2_dylib */
SDL1_LIBNAME /* oh well, anywhere the system can see the .dylib (/usr/local/lib or whatever) */
SDL1_LIBNAME /* oh well, anywhere the system can see the .dylib (/usr/local/lib or whatever) */
};
#else
static const char * const possible_locations[] = {
static const char* const possible_locations[] = {
"libSDL-1.2.so.0",
"libSDL-1.2.so",
};
@ -50,7 +52,7 @@ static const char * const possible_locations[] = {
#endif
#ifdef DETHRACE_SDL_DYNAMIC
static void *sdl1_so;
static void* sdl1_so;
#endif
#define OBJECT_NAME sdl1_so
@ -128,7 +130,7 @@ static int SDL1_Harness_SetWindowPos(void* hWnd, int x, int y, int nWidth, int n
return 0;
}
static void SDL1_Harness_DestroyWindow(void* hWnd) {
static void SDL1_Harness_DestroyWindow(void) {
SDL1_FreeSurface(screen);
SDL1_Quit();
screen = NULL;
@ -140,9 +142,9 @@ static int is_only_key_modifier(int modifier_flags, int flag_check) {
return (modifier_flags & flag_check) && (modifier_flags & (KMOD_CTRL | KMOD_SHIFT | KMOD_ALT | KMOD_META)) == (modifier_flags & flag_check);
}
static void SDL1_Harness_ProcessWindowMessages(MSG_* msg) {
static void SDL1_Harness_ProcessWindowMessages(void) {
SDL_Event event;
int dinput_key;
int dethrace_scancode;
while (SDL1_PollEvent(&event)) {
switch (event.type) {
@ -161,21 +163,18 @@ static void SDL1_Harness_ProcessWindowMessages(MSG_* msg) {
}
}
// Map incoming SDL scancode to DirectInput DIK_* key code.
// https://github.com/DanielGibson/Snippets/blob/master/sdl2_scancode_to_dinput.h
dinput_key = sdl1KeyToDirectInputKeyNum[event.key.keysym.sym];
if (dinput_key == 0) {
// Map incoming SDL key to PC scan code as used by game code
dethrace_scancode = sdl1KeyToDirectInputKeyNum[event.key.keysym.sym];
if (dethrace_scancode == 0) {
LOG_WARN("unexpected key \"%s\" (0x%x)", SDL1_GetKeyName(event.key.keysym.sym), event.key.keysym.sym);
return;
}
// DInput expects high bit to be set if key is down
// https://learn.microsoft.com/en-us/previous-versions/windows/desktop/ee418261(v=vs.85)
directinput_key_state[dinput_key] = (event.type == SDL_KEYDOWN ? 0x80 : 0);
if (event.type == SDL_KEYDOWN) {
gKeyboard_bits[dinput_key >> 5] |= (1 << (dinput_key & 0x1F));
key_state[dethrace_scancode >> 5] |= (1 << (dethrace_scancode & 0x1F));
} else {
gKeyboard_bits[dinput_key >> 5] &= ~(1 << (dinput_key & 0x1F));
key_state[dethrace_scancode >> 5] &= ~(1 << (dethrace_scancode & 0x1F));
}
gKeyHandler_func();
break;
case SDL_VIDEORESIZE:
@ -190,18 +189,22 @@ static void SDL1_Harness_ProcessWindowMessages(MSG_* msg) {
return;
}
static void get_keyboard_state(unsigned int count, uint8_t* buffer) {
memcpy(buffer, directinput_key_state, count);
static void SDL1_Harness_SetKeyHandler(void (*handler_func)(void)) {
gKeyHandler_func = handler_func;
}
static int get_mouse_buttons(int* pButton1, int* pButton2) {
static void SDL1_Harness_GetKeyboardState(uint32_t* buffer) {
memcpy(buffer, key_state, sizeof(key_state));
}
static int SDL1_Harness_GetMouseButtons(int* pButton1, int* pButton2) {
int state = SDL1_GetMouseState(NULL, NULL);
*pButton1 = state & SDL_BUTTON_LMASK;
*pButton2 = state & SDL_BUTTON_RMASK;
return 0;
}
static int get_mouse_position(int* pX, int* pY) {
static int SDL1_Harness_GetMousePosition(int* pX, int* pY) {
SDL1_GetMouseState(pX, pY);
return 0;
}
@ -246,7 +249,7 @@ static void SDL1_Renderer_Present(br_pixelmap* src) {
static void SDL1_Harness_Swap(br_pixelmap* back_buffer) {
SDL1_Harness_ProcessWindowMessages(NULL);
SDL1_Harness_ProcessWindowMessages();
if (0) {
SDL1_GL_SwapBuffers();
@ -268,7 +271,7 @@ static void SDL1_Harness_PaletteChanged(br_colour entries[256]) {
}
}
static int SDL1_Harness_ShowErrorMessage(void* window, char* text, char* caption) {
static int SDL1_Harness_ShowErrorMessage(char* text, char* caption) {
fprintf(stderr, "%s", text);
#ifdef _WIN32
MessageBoxA(NULL, text, caption, MB_ICONERROR);
@ -293,9 +296,10 @@ static int SDL1_Harness_Platform_Init(tHarness_platform* platform) {
platform->ShowCursor = SDL1_ShowCursor;
platform->SetWindowPos = SDL1_Harness_SetWindowPos;
platform->DestroyWindow = SDL1_Harness_DestroyWindow;
platform->GetKeyboardState = get_keyboard_state;
platform->GetMousePosition = get_mouse_position;
platform->GetMouseButtons = get_mouse_buttons;
platform->SetKeyHandler = SDL1_Harness_SetKeyHandler;
platform->GetKeyboardState = SDL1_Harness_GetKeyboardState;
platform->GetMousePosition = SDL1_Harness_GetMousePosition;
platform->GetMouseButtons = SDL1_Harness_GetMouseButtons;
platform->ShowErrorMessage = SDL1_Harness_ShowErrorMessage;
platform->CreateWindow_ = SDL1_Harness_CreateWindow;
@ -312,4 +316,3 @@ const tPlatform_bootstrap SDL1_bootstrap = {
ePlatform_cap_software,
SDL1_Harness_Platform_Init,
};

View File

@ -4,8 +4,8 @@
#include "harness/config.h"
#include "harness/hooks.h"
#include "harness/trace.h"
#include "sdl2_scancode_to_dinput.h"
#include "sdl2_syms.h"
#include "sdl_scancode_map.h"
SDL_COMPILE_TIME_ASSERT(sdl2_platform_requires_SDL2, SDL_MAJOR_VERSION == 2);
@ -21,7 +21,10 @@ static int render_width, render_height;
static Uint32 last_frame_time;
static uint8_t directinput_key_state[SDL_NUM_SCANCODES];
void (*gKeyHandler_func)(void);
// 32 bytes, 1 bit per key. Matches dos executable behavior
static uint32_t key_state[8];
static struct {
int x, y;
@ -30,29 +33,28 @@ static struct {
// Callbacks back into original game code
extern void QuitGame(void);
extern uint32_t gKeyboard_bits[8];
extern br_pixelmap* gBack_screen;
#ifdef DETHRACE_SDL_DYNAMIC
#ifdef _WIN32
static const char * const possible_locations[] = {
static const char* const possible_locations[] = {
"SDL2.dll",
};
#elif defined(__APPLE__)
#define SHARED_OBJECT_NAME "libSDL2"
#define SDL2_LIBNAME "libSDL2.dylib"
#define SDL2_FRAMEWORK "SDL2.framework/Versions/A/SDL2"
static const char * const possible_locations[] = {
"@loader_path/" SDL2_LIBNAME, /* MyApp.app/Contents/MacOS/libSDL2_dylib */
"@loader_path/../Frameworks/" SDL2_FRAMEWORK, /* MyApp.app/Contents/Frameworks/SDL2_framework */
"@executable_path/" SDL2_LIBNAME, /* MyApp.app/Contents/MacOS/libSDL2_dylib */
static const char* const possible_locations[] = {
"@loader_path/" SDL2_LIBNAME, /* MyApp.app/Contents/MacOS/libSDL2_dylib */
"@loader_path/../Frameworks/" SDL2_FRAMEWORK, /* MyApp.app/Contents/Frameworks/SDL2_framework */
"@executable_path/" SDL2_LIBNAME, /* MyApp.app/Contents/MacOS/libSDL2_dylib */
"@executable_path/../Frameworks/" SDL2_FRAMEWORK, /* MyApp.app/Contents/Frameworks/SDL2_framework */
NULL, /* /Users/username/Library/Frameworks/SDL2_framework */
"/Library/Frameworks" SDL2_FRAMEWORK, /* /Library/Frameworks/SDL2_framework */
SDL2_LIBNAME /* oh well, anywhere the system can see the .dylib (/usr/local/lib or whatever) */
NULL, /* /Users/username/Library/Frameworks/SDL2_framework */
"/Library/Frameworks" SDL2_FRAMEWORK, /* /Library/Frameworks/SDL2_framework */
SDL2_LIBNAME /* oh well, anywhere the system can see the .dylib (/usr/local/lib or whatever) */
};
#else
static const char * const possible_locations[] = {
static const char* const possible_locations[] = {
"libSDL2-2.0.so.0",
"libSDL2-2.0.so",
};
@ -60,7 +62,7 @@ static const char * const possible_locations[] = {
#endif
#ifdef DETHRACE_SDL_DYNAMIC
static void *sdl2_so;
static void* sdl2_so;
#endif
#define OBJECT_NAME sdl2_so
@ -102,9 +104,11 @@ static int SDL2_Harness_SetWindowPos(void* hWnd, int x, int y, int nWidth, int n
return 0;
}
static void SDL2_Harness_DestroyWindow(void* hWnd) {
static void SDL2_Harness_DestroyWindow(void) {
// SDL2_GL_DeleteContext(context);
SDL2_DestroyWindow(window);
if (window != NULL) {
SDL2_DestroyWindow(window);
}
SDL2_Quit();
window = NULL;
}
@ -115,9 +119,8 @@ static int is_only_key_modifier(int modifier_flags, int flag_check) {
return (modifier_flags & flag_check) && (modifier_flags & (KMOD_CTRL | KMOD_SHIFT | KMOD_ALT | KMOD_GUI)) == (modifier_flags & flag_check);
}
static void SDL2_Harness_ProcessWindowMessages(MSG_* msg) {
static void SDL2_Harness_ProcessWindowMessages(void) {
SDL_Event event;
int dinput_key;
while (SDL2_PollEvent(&event)) {
switch (event.type) {
@ -139,21 +142,19 @@ static void SDL2_Harness_ProcessWindowMessages(MSG_* msg) {
}
}
// Map incoming SDL scancode to DirectInput DIK_* key code.
// https://github.com/DanielGibson/Snippets/blob/master/sdl2_scancode_to_dinput.h
dinput_key = sdlScanCodeToDirectInputKeyNum[event.key.keysym.scancode];
if (dinput_key == 0) {
// Map incoming SDL scancode to PC scan code as used by game code
int dethrace_scancode = sdl_scancode_map[event.key.keysym.scancode];
if (dethrace_scancode == 0) {
LOG_WARN("unexpected scan code %s (%d)", SDL2_GetScancodeName(event.key.keysym.scancode), event.key.keysym.scancode);
return;
}
// DInput expects high bit to be set if key is down
// https://learn.microsoft.com/en-us/previous-versions/windows/desktop/ee418261(v=vs.85)
directinput_key_state[dinput_key] = (event.type == SDL_KEYDOWN ? 0x80 : 0);
if (event.type == SDL_KEYDOWN) {
gKeyboard_bits[dinput_key >> 5] |= (1 << (dinput_key & 0x1F));
key_state[dethrace_scancode >> 5] |= (1 << (dethrace_scancode & 0x1F));
} else {
gKeyboard_bits[dinput_key >> 5] &= ~(1 << (dinput_key & 0x1F));
key_state[dethrace_scancode >> 5] &= ~(1 << (dethrace_scancode & 0x1F));
}
gKeyHandler_func();
break;
case SDL_WINDOWEVENT:
@ -168,8 +169,12 @@ static void SDL2_Harness_ProcessWindowMessages(MSG_* msg) {
}
}
static void SDL2_Harness_GetKeyboardState(unsigned int count, uint8_t* buffer) {
memcpy(buffer, directinput_key_state, count);
static void SDL2_Harness_SetKeyHandler(void (*handler_func)(void)) {
gKeyHandler_func = handler_func;
}
static void SDL2_Harness_GetKeyboardState(uint32_t* buffer) {
memcpy(buffer, key_state, sizeof(key_state));
}
static int SDL2_Harness_GetMouseButtons(int* pButton1, int* pButton2) {
@ -223,9 +228,9 @@ static void limit_fps(void) {
last_frame_time = SDL2_GetTicks();
}
static int SDL2_Harness_ShowErrorMessage(void* window, char* text, char* caption) {
fprintf(stderr, "%s", text);
SDL2_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, caption, text, window);
static int SDL2_Harness_ShowErrorMessage(char* title, char* message) {
fprintf(stderr, "%s", message);
SDL2_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, title, message, window);
return 0;
}
@ -319,7 +324,7 @@ static void SDL2_Harness_CreateWindow(const char* title, int width, int height,
static void SDL2_Harness_Swap(br_pixelmap* back_buffer) {
SDL2_Harness_ProcessWindowMessages(NULL);
SDL2_Harness_ProcessWindowMessages();
if (gl_context != NULL) {
SDL2_GL_SwapWindow(window);
@ -372,6 +377,7 @@ static int SDL2_Harness_Platform_Init(tHarness_platform* platform) {
platform->ShowCursor = SDL2_ShowCursor;
platform->SetWindowPos = SDL2_Harness_SetWindowPos;
platform->DestroyWindow = SDL2_Harness_DestroyWindow;
platform->SetKeyHandler = SDL2_Harness_SetKeyHandler;
platform->GetKeyboardState = SDL2_Harness_GetKeyboardState;
platform->GetMousePosition = SDL2_Harness_GetMousePosition;
platform->GetMouseButtons = SDL2_Harness_GetMouseButtons;

View File

@ -1,390 +0,0 @@
/*
* Maps SDL2 scancodes to directinput keynums/scancodes.
* Useful if you're porting a game that uses dinput scancodes internally
* (for key bindings etc) or any other lib (like CEGUI) that uses them.
*
* (C) 2015 Daniel Gibson
*
* Homepage: https://github.com/DanielGibson/Snippets/
*
* License:
* This software is dual-licensed to the public domain and under the following
* license: you are granted a perpetual, irrevocable license to copy, modify,
* publish, and distribute this file as you see fit.
* No warranty implied; use at your own risk.
*
* So you can do whatever you want with this code, including copying it
* (or parts of it) into your own source.
* No need to mention me or this "license" in your code or docs, even though
* it would be appreciated, of course.
*
*/
#include <SDL.h>
#if 0 // Usage Example:
#include "sdl2_scancode_to_dinput.h"
static int SDLScanCodeToKeyNum(SDL_Scancode sc)
{
int idx = (int)sc;
assert(idx >= 0 && idx < SDL_NUM_SCANCODES);
return scanCodeToKeyNum[idx];
}
static SDL_Scancode KeyNumToSDLScanCode( int keyNum )
{
if( keyNum >= 0 && keyNum < 0xEF )
{
for(int i = 0; i < SDL_NUM_SCANCODES; ++i)
{
if(scanCodeToKeyNum[i] == keyNum) return (SDL_Scancode)i;
}
}
return SDL_SCANCODE_UNKNOWN;
}
#endif // 0
#ifndef _SDL2_SCANCODE_TO_DINPUT_H_
#define _SDL2_SCANCODE_TO_DINPUT_H_
// TODO: map the following keys, if possible:
// #define DIK_UNDERLINE 0x93 /* (NEC PC98) */
// #define DIK_KANJI 0x94 /* (Japanese keyboard) */
// #define DIK_AX 0x96 /* (Japan AX) */
// #define DIK_UNLABELED 0x97 /* (J3100) */
//
// #define DIK_WAKE 0xE3 /* System Wake */
//
// (#define DIK_ABNT_C2 0x7E /* Numpad . on Brazilian keyboard */ - system should map this to KP_COMMA or something,
// according to USB doc, so probably it doesn't need mapping here)
// maps SDL2 scancodes to directinput keynums/scancodes - dinput_key = sdlScanCodeToDirectInputKeyNum[(int)your_sdl2_scancode];
static int sdlScanCodeToDirectInputKeyNum[SDL_NUM_SCANCODES] = {
0x0, // SDL_SCANCODE_UNKNOWN = 0, => 0 should also work for dinput codes as "not assigned/unknown"
0x0, // // 1 (unused)
0x0, // // 2 (unused)
0x0, // // 3 (unused)
0x1E, // SDL_SCANCODE_A = 4, - DIK_A
0x30, // SDL_SCANCODE_B = 5, - DIK_B
0x2E, // SDL_SCANCODE_C = 6, - DIK_C
0x20, // SDL_SCANCODE_D = 7, - DIK_D
0x12, // SDL_SCANCODE_E = 8, - DIK_E
0x21, // SDL_SCANCODE_F = 9, - DIK_F
0x22, // SDL_SCANCODE_G = 10, - DIK_G
0x23, // SDL_SCANCODE_H = 11, - DIK_H
0x17, // SDL_SCANCODE_I = 12, - DIK_I
0x24, // SDL_SCANCODE_J = 13, - DIK_J
0x25, // SDL_SCANCODE_K = 14, - DIK_K
0x26, // SDL_SCANCODE_L = 15, - DIK_L
0x32, // SDL_SCANCODE_M = 16, - DIK_M
0x31, // SDL_SCANCODE_N = 17, - DIK_N
0x18, // SDL_SCANCODE_O = 18, - DIK_O
0x19, // SDL_SCANCODE_P = 19, - DIK_P
0x10, // SDL_SCANCODE_Q = 20, - DIK_Q
0x13, // SDL_SCANCODE_R = 21, - DIK_R
0x1F, // SDL_SCANCODE_S = 22, - DIK_S
0x14, // SDL_SCANCODE_T = 23, - DIK_T
0x16, // SDL_SCANCODE_U = 24, - DIK_U
0x2F, // SDL_SCANCODE_V = 25, - DIK_V
0x11, // SDL_SCANCODE_W = 26, - DIK_W
0x2D, // SDL_SCANCODE_X = 27, - DIK_X
0x15, // SDL_SCANCODE_Y = 28, - DIK_Y
0x2C, // SDL_SCANCODE_Z = 29, - DIK_Z
0x02, // SDL_SCANCODE_1 = 30, - DIK_1
0x03, // SDL_SCANCODE_2 = 31, - DIK_2
0x04, // SDL_SCANCODE_3 = 32, - DIK_3
0x05, // SDL_SCANCODE_4 = 33, - DIK_4
0x06, // SDL_SCANCODE_5 = 34, - DIK_5
0x07, // SDL_SCANCODE_6 = 35, - DIK_6
0x08, // SDL_SCANCODE_7 = 36, - DIK_7
0x09, // SDL_SCANCODE_8 = 37, - DIK_8
0x0A, // SDL_SCANCODE_9 = 38, - DIK_9
0x0B, // SDL_SCANCODE_0 = 39, - DIK_0
0x1C, // SDL_SCANCODE_RETURN = 40, - DIK_RETURN
0x01, // SDL_SCANCODE_ESCAPE = 41, - DIK_ESCAPE
0x0E, // SDL_SCANCODE_BACKSPACE = 42, - DIK_BACK
0x0F, // SDL_SCANCODE_TAB = 43, - DIK_TAB
0x39, // SDL_SCANCODE_SPACE = 44, - DIK_SPACE
0x0C, // SDL_SCANCODE_MINUS = 45, - DIK_MINUS
0x0D, // SDL_SCANCODE_EQUALS = 46, - DIK_EQUALS
0x1A, // SDL_SCANCODE_LEFTBRACKET = 47, - DIK_LBRACKET
0x1B, // SDL_SCANCODE_RIGHTBRACKET = 48, - DIK_RBRACKET
0x2B, // SDL_SCANCODE_BACKSLASH = 49, // next to enter, US: [\|] DE: [#'] UK: [#~] - DIK_BACKSLASH
0x2B, // SDL_SCANCODE_NONUSHASH = 50, // same key as before actually on some layouts, systems should map this to SDL_SCANCODE_BACKSLASH - DIK_BACKSLASH
0x27, // SDL_SCANCODE_SEMICOLON = 51, - DIK_SEMICOLON
0x28, // SDL_SCANCODE_APOSTROPHE = 52, - DIK_APOSTROPHE
0x29, // SDL_SCANCODE_GRAVE = 53, // "quake/doom3 console key" - DIK_GRAVE
0x33, // SDL_SCANCODE_COMMA = 54, - DIK_COMMA
0x34, // SDL_SCANCODE_PERIOD = 55, - DIK_PERIOD
0x35, // SDL_SCANCODE_SLASH = 56, - DIK_SLASH
0x3A, // SDL_SCANCODE_CAPSLOCK = 57, - DIK_CAPITAL
0x3B, // SDL_SCANCODE_F1 = 58, - DIK_F1
0x3C, // SDL_SCANCODE_F2 = 59, - DIK_F2
0x3D, // SDL_SCANCODE_F3 = 60, - DIK_F3
0x3E, // SDL_SCANCODE_F4 = 61, - DIK_F4
0x3F, // SDL_SCANCODE_F5 = 62, - DIK_F5
0x40, // SDL_SCANCODE_F6 = 63, - DIK_F6
0x41, // SDL_SCANCODE_F7 = 64, - DIK_F7
0x42, // SDL_SCANCODE_F8 = 65, - DIK_F8
0x43, // SDL_SCANCODE_F9 = 66, - DIK_F9
0x44, // SDL_SCANCODE_F10 = 67, - DIK_F10
0x57, // SDL_SCANCODE_F11 = 68, - DIK_F11
0x58, // SDL_SCANCODE_F12 = 69, - DIK_F12
0xB7, // SDL_SCANCODE_PRINTSCREEN = 70, // - DIK_SYSRQ; SDL_SCANCODE_SYSREQ also maps to this!
0x46, // SDL_SCANCODE_SCROLLLOCK = 71, - DIK_SCROLL
0xC5, // SDL_SCANCODE_PAUSE = 72, - DIK_PAUSE
0xD2, // SDL_SCANCODE_INSERT = 73, // insert on PC, help on some Mac keyboards (but does send code 73, not 117) - DIK_INSERT
0xC7, // SDL_SCANCODE_HOME = 74, - DIK_HOME
0xC9, // SDL_SCANCODE_PAGEUP = 75, - DIK_PRIOR
0xD3, // SDL_SCANCODE_DELETE = 76, - DIK_DELETE
0xCF, // SDL_SCANCODE_END = 77, - DIK_END
0xD1, // SDL_SCANCODE_PAGEDOWN = 78, - DIK_NEXT
0xCD, // SDL_SCANCODE_RIGHT = 79, - DIK_RIGHT
0xCB, // SDL_SCANCODE_LEFT = 80, - DIK_LEFT
0xD0, // SDL_SCANCODE_DOWN = 81, - DIK_DOWN
0xC8, // SDL_SCANCODE_UP = 82, - DIK_UP
0x45, // SDL_SCANCODE_NUMLOCKCLEAR = 83, // num lock on PC, clear on Mac keyboards - DIK_NUMLOCK
0xB5, // SDL_SCANCODE_KP_DIVIDE = 84, - DIK_DIVIDE
0x37, // SDL_SCANCODE_KP_MULTIPLY = 85, - DIK_MULTIPLY
0x4A, // SDL_SCANCODE_KP_MINUS = 86, - DIK_SUBTRACT
0x4E, // SDL_SCANCODE_KP_PLUS = 87, - DIK_ADD
0x9C, // SDL_SCANCODE_KP_ENTER = 88, - DIK_NUMPADENTER
0x4F, // SDL_SCANCODE_KP_1 = 89, - DIK_NUMPAD1
0x50, // SDL_SCANCODE_KP_2 = 90, - DIK_NUMPAD2
0x51, // SDL_SCANCODE_KP_3 = 91, - DIK_NUMPAD3
0x4B, // SDL_SCANCODE_KP_4 = 92, - DIK_NUMPAD4
0x4C, // SDL_SCANCODE_KP_5 = 93, - DIK_NUMPAD5
0x4D, // SDL_SCANCODE_KP_6 = 94, - DIK_NUMPAD6
0x47, // SDL_SCANCODE_KP_7 = 95, - DIK_NUMPAD7
0x48, // SDL_SCANCODE_KP_8 = 96, - DIK_NUMPAD8
0x49, // SDL_SCANCODE_KP_9 = 97, - DIK_NUMPAD9
0x52, // SDL_SCANCODE_KP_0 = 98, - DIK_NUMPAD0
0x53, // SDL_SCANCODE_KP_PERIOD = 99, - DIK_DECIMAL
0x56, // SDL_SCANCODE_NONUSBACKSLASH = 100, // [<>|] on german keyboard, next to left shift - DIK_OEM_102
0xDD, // SDL_SCANCODE_APPLICATION = 101, // windows contextual menu, compose - DIK_APPS
0xDE, // SDL_SCANCODE_POWER = 102, // should be a status flag, but some mac keyboards have a power key - DIK_POWER
0x8D, // SDL_SCANCODE_KP_EQUALS = 103, - DIK_NUMPADEQUALS
0x64, // SDL_SCANCODE_F13 = 104, - DIK_F13
0x65, // SDL_SCANCODE_F14 = 105, - DIK_F14
0x66, // SDL_SCANCODE_F15 = 106, - DIK_F15
0x67, // SDL_SCANCODE_F16 = 107, // TODO: F16 and up don't have DIK_ constants! is this right?
0x68, // SDL_SCANCODE_F17 = 108, // (at least 0x67-0x6F have no DIK_constants at all)
0x69, // SDL_SCANCODE_F18 = 109,
0x6A, // SDL_SCANCODE_F19 = 110,
0x6B, // SDL_SCANCODE_F20 = 111,
0x6C, // SDL_SCANCODE_F21 = 112,
0x6D, // SDL_SCANCODE_F22 = 113,
0x6E, // SDL_SCANCODE_F23 = 114,
0x6F, // SDL_SCANCODE_F24 = 115,
0x0, // SDL_SCANCODE_EXECUTE = 116,
0x0, // SDL_SCANCODE_HELP = 117,
0x0, // SDL_SCANCODE_MENU = 118,
0x0, // SDL_SCANCODE_SELECT = 119,
0x95, // SDL_SCANCODE_STOP = 120, - DIK_STOP
0x0, // SDL_SCANCODE_AGAIN = 121, // redo
0x0, // SDL_SCANCODE_UNDO = 122,
0x0, // SDL_SCANCODE_CUT = 123,
0x0, // SDL_SCANCODE_COPY = 124,
0x0, // SDL_SCANCODE_PASTE = 125,
0x0, // SDL_SCANCODE_FIND = 126,
0x0, // SDL_SCANCODE_MUTE = 127,
0xB0, // SDL_SCANCODE_VOLUMEUP = 128, - DIK_VOLUMEUP
0xAE, // SDL_SCANCODE_VOLUMEDOWN = 129, - DIK_VOLUMEDOWN
// /* not sure whether there's a reason to enable these */
0x0, // /* SDL_SCANCODE_LOCKINGCAPSLOCK = 130, */
0x0, // /* SDL_SCANCODE_LOCKINGNUMLOCK = 131, */
0x0, // /* SDL_SCANCODE_LOCKINGSCROLLLOCK = 132, */
0xB3, // SDL_SCANCODE_KP_COMMA = 133, - DIK_NUMPADCOMMA
0x0, // SDL_SCANCODE_KP_EQUALSAS400 = 134,
0x73, // SDL_SCANCODE_INTERNATIONAL1 = 135, // this is really brazilian / and ? - DIK_ABNT_C1
0x0, // SDL_SCANCODE_INTERNATIONAL2 = 136, // TODO: Hut1_12v2.pdf page 60, footnote 16
0x7D, // SDL_SCANCODE_INTERNATIONAL3 = 137, - DIK_YEN
0x79, // SDL_SCANCODE_INTERNATIONAL4 = 138, // Japan: XFER/"convert kana -> kanji", right of space - DIK_CONVERT
0x7B, // SDL_SCANCODE_INTERNATIONAL5 = 139, // Japan: NFER/"don't convert kana -> kanji", left of space - DIK_NOCONVERT
0x0, // SDL_SCANCODE_INTERNATIONAL6 = 140, // TODO: Hut1_12v2.pdf page 60, footnote 20
0x0, // SDL_SCANCODE_INTERNATIONAL7 = 141, // Toggle Double-Byte/Single-Byte mode.
0x0, // SDL_SCANCODE_INTERNATIONAL8 = 142, // Undefined, available for other Front End Language Processors
0x0, // SDL_SCANCODE_INTERNATIONAL9 = 143, // Undefined, available for other Front End Language Processors
0x0, // SDL_SCANCODE_LANG1 = 144, // Hangul/English toggle (Korea)
0x0, // SDL_SCANCODE_LANG2 = 145, // Hanja conversion (Korea)
0x70, // SDL_SCANCODE_LANG3 = 146, // Katakana (Japan) - DIK_KANA
0x0, // SDL_SCANCODE_LANG4 = 147, // Hiragana (Japan)
0x0, // SDL_SCANCODE_LANG5 = 148, // Zenkaku/Hankaku (Japan)
0x0, // SDL_SCANCODE_LANG6 = 149, // reserved
0x0, // SDL_SCANCODE_LANG7 = 150, // reserved
0x0, // SDL_SCANCODE_LANG8 = 151, // reserved
0x0, // SDL_SCANCODE_LANG9 = 152, // reserved
0x0, // SDL_SCANCODE_ALTERASE = 153, // Erase-Eaze
0xB7, // SDL_SCANCODE_SYSREQ = 154, - DIK_SYSRQ; SDL_SCANCODE_PRINTSCREEN also maps to this!
0x0, // SDL_SCANCODE_CANCEL = 155,
0x0, // SDL_SCANCODE_CLEAR = 156,
0x0, // SDL_SCANCODE_PRIOR = 157,
0x0, // SDL_SCANCODE_RETURN2 = 158,
0x0, // SDL_SCANCODE_SEPARATOR = 159,
0x0, // SDL_SCANCODE_OUT = 160,
0x0, // SDL_SCANCODE_OPER = 161,
0x0, // SDL_SCANCODE_CLEARAGAIN = 162,
0x0, // SDL_SCANCODE_CRSEL = 163,
0x0, // SDL_SCANCODE_EXSEL = 164,
0x0, // 165 (unused)
0x0, // 166 (unused)
0x0, // 167 (unused)
0x0, // 168 (unused)
0x0, // 169 (unused)
0x0, // 170 (unused)
0x0, // 171 (unused)
0x0, // 172 (unused)
0x0, // 173 (unused)
0x0, // 174 (unused)
0x0, // 175 (unused)
0x0, // SDL_SCANCODE_KP_00 = 176,
0x0, // SDL_SCANCODE_KP_000 = 177,
0x0, // SDL_SCANCODE_THOUSANDSSEPARATOR = 178,
0x0, // SDL_SCANCODE_DECIMALSEPARATOR = 179,
0x0, // SDL_SCANCODE_CURRENCYUNIT = 180,
0x0, // SDL_SCANCODE_CURRENCYSUBUNIT = 181,
0x0, // SDL_SCANCODE_KP_LEFTPAREN = 182,
0x0, // SDL_SCANCODE_KP_RIGHTPAREN = 183,
0x0, // SDL_SCANCODE_KP_LEFTBRACE = 184,
0x0, // SDL_SCANCODE_KP_RIGHTBRACE = 185,
0x0, // SDL_SCANCODE_KP_TAB = 186,
0x0, // SDL_SCANCODE_KP_BACKSPACE = 187,
0x0, // SDL_SCANCODE_KP_A = 188,
0x0, // SDL_SCANCODE_KP_B = 189,
0x0, // SDL_SCANCODE_KP_C = 190,
0x0, // SDL_SCANCODE_KP_D = 191,
0x0, // SDL_SCANCODE_KP_E = 192,
0x0, // SDL_SCANCODE_KP_F = 193,
0x0, // SDL_SCANCODE_KP_XOR = 194,
0x0, // SDL_SCANCODE_KP_POWER = 195,
0x0, // SDL_SCANCODE_KP_PERCENT = 196,
0x0, // SDL_SCANCODE_KP_LESS = 197,
0x0, // SDL_SCANCODE_KP_GREATER = 198,
0x0, // SDL_SCANCODE_KP_AMPERSAND = 199,
0x0, // SDL_SCANCODE_KP_DBLAMPERSAND = 200,
0x0, // SDL_SCANCODE_KP_VERTICALBAR = 201,
0x0, // SDL_SCANCODE_KP_DBLVERTICALBAR = 202,
0x92, // SDL_SCANCODE_KP_COLON = 203, - DIK_COLON
0x0, // SDL_SCANCODE_KP_HASH = 204,
0x0, // SDL_SCANCODE_KP_SPACE = 205,
0x91, // SDL_SCANCODE_KP_AT = 206, - DIK_AT
0x0, // SDL_SCANCODE_KP_EXCLAM = 207,
0x0, // SDL_SCANCODE_KP_MEMSTORE = 208,
0x0, // SDL_SCANCODE_KP_MEMRECALL = 209,
0x0, // SDL_SCANCODE_KP_MEMCLEAR = 210,
0x0, // SDL_SCANCODE_KP_MEMADD = 211,
0x0, // SDL_SCANCODE_KP_MEMSUBTRACT = 212,
0x0, // SDL_SCANCODE_KP_MEMMULTIPLY = 213,
0x0, // SDL_SCANCODE_KP_MEMDIVIDE = 214,
0x0, // SDL_SCANCODE_KP_PLUSMINUS = 215,
0x0, // SDL_SCANCODE_KP_CLEAR = 216,
0x0, // SDL_SCANCODE_KP_CLEARENTRY = 217,
0x0, // SDL_SCANCODE_KP_BINARY = 218,
0x0, // SDL_SCANCODE_KP_OCTAL = 219,
0x0, // SDL_SCANCODE_KP_DECIMAL = 220,
0x0, // SDL_SCANCODE_KP_HEXADECIMAL = 221,
0x0, // 222 (unused)
0x0, // 223 (unused)
0x1D, // SDL_SCANCODE_LCTRL = 224, - DIK_LCONTROL
0x2A, // SDL_SCANCODE_LSHIFT = 225, - DIK_LSHIFT
0x38, // SDL_SCANCODE_LALT = 226, // left Alt, option - DIK_LMENU
0xDB, // SDL_SCANCODE_LGUI = 227, // left windows, command (apple), meta - DIK_LWIN
0x9D, // SDL_SCANCODE_RCTRL = 228, - DIK_RCONTROL
0x36, // SDL_SCANCODE_RSHIFT = 229, - DIK_RSHIFT
0xB8, // SDL_SCANCODE_RALT = 230, // right Alt/AltGr, option - DIK_RMENU, also used for SDL_SCANCODE_MODE!
0xDC, // SDL_SCANCODE_RGUI = 231, // left windows, command (apple), meta - DIK_RWIN
// 232 - 256 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, // 232 - 240 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 241-250 unused
0, 0, 0, 0, 0, 0, // 251-256 unused
0xB8, // SDL_SCANCODE_MODE = 257, // this seems to be the AltGr Key? - DIK_RMENU (right alt)
// These values are mapped from usage page 0x0C (USB consumer page).
0x99, // SDL_SCANCODE_AUDIONEXT = 258, - DIK_NEXTTRACK
0x90, // SDL_SCANCODE_AUDIOPREV = 259, - DIK_PREVTRACK, which is DIK_CIRCUMFLEX on japanese keyboards
0xA4, // SDL_SCANCODE_AUDIOSTOP = 260, - DIK_MEDIASTOP
0xA2, // SDL_SCANCODE_AUDIOPLAY = 261, - DIK_PLAYPAUSE
0xA0, // SDL_SCANCODE_AUDIOMUTE = 262, - DIK_MUTE
0xED, // SDL_SCANCODE_MEDIASELECT = 263, - DIK_MEDIASELECT
0x0, // SDL_SCANCODE_WWW = 264,
0xEC, // SDL_SCANCODE_MAIL = 265, - DIK_MAIL
0xA1, // SDL_SCANCODE_CALCULATOR = 266, - DIK_CALCULATOR
0xEB, // SDL_SCANCODE_COMPUTER = 267, - DIK_MYCOMPUTER
0xE5, // SDL_SCANCODE_AC_SEARCH = 268, - DIK_WEBSEARCH
0xB2, // SDL_SCANCODE_AC_HOME = 269, - DIK_WEBHOME
0xEA, // SDL_SCANCODE_AC_BACK = 270, - DIK_WEBBACK
0xE9, // SDL_SCANCODE_AC_FORWARD = 271, - DIK_WEBFORWARD
0xE8, // SDL_SCANCODE_AC_STOP = 272, - DIK_WEBSTOP
0xE7, // SDL_SCANCODE_AC_REFRESH = 273, - DIK_WEBREFRESH
0xE6, // SDL_SCANCODE_AC_BOOKMARKS = 274, - DIK_WEBFAVORITES
// These are values that Christian Walther added (for mac keyboard?).
0x0, // SDL_SCANCODE_BRIGHTNESSDOWN = 275,
0x0, // SDL_SCANCODE_BRIGHTNESSUP = 276,
0x0, // SDL_SCANCODE_DISPLAYSWITCH = 277, // display mirroring/dual display switch, video mode switch
0x0, // SDL_SCANCODE_KBDILLUMTOGGLE = 278,
0x0, // SDL_SCANCODE_KBDILLUMDOWN = 279,
0x0, // SDL_SCANCODE_KBDILLUMUP = 280,
0x0, // SDL_SCANCODE_EJECT = 281,
0xDF, // SDL_SCANCODE_SLEEP = 282, - DIK_SLEEP
0x0, // SDL_SCANCODE_APP1 = 283,
0x0, // SDL_SCANCODE_APP2 = 284,
// end of Walther-keys
// the rest up to 511 are currently not named in SDL
0, 0, 0, 0, 0, 0, // 285-290 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 291-300 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 301-320 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 321-340 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 341-360 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 361-380 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 381-400 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 401-420 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 421-440 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 441-460 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 461-480 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 481-500 unused
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 // 501-511 unused
};
#endif /* _SDL2_SCANCODE_TO_DINPUT_H_ */

View File

@ -0,0 +1,111 @@
#ifndef SDL_SCANCODE_MAP_H
#define SDL_SCANCODE_MAP_H
#include "dethrace_scancodes.h"
#include <SDL.h>
int sdl_scancode_map[SDL_NUM_SCANCODES] = {
[SDL_SCANCODE_ESCAPE] = SCANCODE_ESCAPE,
[SDL_SCANCODE_1] = SCANCODE_1,
[SDL_SCANCODE_2] = SCANCODE_2,
[SDL_SCANCODE_3] = SCANCODE_3,
[SDL_SCANCODE_4] = SCANCODE_4,
[SDL_SCANCODE_5] = SCANCODE_5,
[SDL_SCANCODE_6] = SCANCODE_6,
[SDL_SCANCODE_7] = SCANCODE_7,
[SDL_SCANCODE_8] = SCANCODE_8,
[SDL_SCANCODE_9] = SCANCODE_9,
[SDL_SCANCODE_0] = SCANCODE_0,
[SDL_SCANCODE_MINUS] = SCANCODE_MINUS,
[SDL_SCANCODE_EQUALS] = SCANCODE_EQUALS,
[SDL_SCANCODE_BACKSPACE] = SCANCODE_BACK,
[SDL_SCANCODE_TAB] = SCANCODE_TAB,
[SDL_SCANCODE_Q] = SCANCODE_Q,
[SDL_SCANCODE_W] = SCANCODE_W,
[SDL_SCANCODE_E] = SCANCODE_E,
[SDL_SCANCODE_R] = SCANCODE_R,
[SDL_SCANCODE_T] = SCANCODE_T,
[SDL_SCANCODE_Y] = SCANCODE_Y,
[SDL_SCANCODE_U] = SCANCODE_U,
[SDL_SCANCODE_I] = SCANCODE_I,
[SDL_SCANCODE_O] = SCANCODE_O,
[SDL_SCANCODE_P] = SCANCODE_P,
[SDL_SCANCODE_LEFTBRACKET] = SCANCODE_LBRACKET,
[SDL_SCANCODE_RIGHTBRACKET] = SCANCODE_RBRACKET,
[SDL_SCANCODE_RETURN] = SCANCODE_RETURN,
[SDL_SCANCODE_LCTRL] = SCANCODE_LCONTROL,
[SDL_SCANCODE_A] = SCANCODE_A,
[SDL_SCANCODE_S] = SCANCODE_S,
[SDL_SCANCODE_D] = SCANCODE_D,
[SDL_SCANCODE_F] = SCANCODE_F,
[SDL_SCANCODE_G] = SCANCODE_G,
[SDL_SCANCODE_H] = SCANCODE_H,
[SDL_SCANCODE_J] = SCANCODE_J,
[SDL_SCANCODE_K] = SCANCODE_K,
[SDL_SCANCODE_L] = SCANCODE_L,
[SDL_SCANCODE_SEMICOLON] = SCANCODE_SEMICOLON,
[SDL_SCANCODE_APOSTROPHE] = SCANCODE_APOSTROPHE,
[SDL_SCANCODE_GRAVE] = SCANCODE_GRAVE,
[SDL_SCANCODE_LSHIFT] = SCANCODE_LSHIFT,
[SDL_SCANCODE_BACKSLASH] = SCANCODE_BACKSLASH,
[SDL_SCANCODE_Z] = SCANCODE_Z,
[SDL_SCANCODE_X] = SCANCODE_X,
[SDL_SCANCODE_C] = SCANCODE_C,
[SDL_SCANCODE_V] = SCANCODE_V,
[SDL_SCANCODE_B] = SCANCODE_B,
[SDL_SCANCODE_N] = SCANCODE_N,
[SDL_SCANCODE_M] = SCANCODE_M,
[SDL_SCANCODE_COMMA] = SCANCODE_COMMA,
[SDL_SCANCODE_PERIOD] = SCANCODE_PERIOD,
[SDL_SCANCODE_SLASH] = SCANCODE_SLASH,
[SDL_SCANCODE_RSHIFT] = SCANCODE_RSHIFT,
[SDL_SCANCODE_KP_MULTIPLY] = SCANCODE_MULTIPLY,
[SDL_SCANCODE_LALT] = SCANCODE_LALT,
[SDL_SCANCODE_SPACE] = SCANCODE_SPACE,
[SDL_SCANCODE_CAPSLOCK] = SCANCODE_CAPITAL,
[SDL_SCANCODE_F1] = SCANCODE_F1,
[SDL_SCANCODE_F2] = SCANCODE_F2,
[SDL_SCANCODE_F3] = SCANCODE_F3,
[SDL_SCANCODE_F4] = SCANCODE_F4,
[SDL_SCANCODE_F5] = SCANCODE_F5,
[SDL_SCANCODE_F6] = SCANCODE_F6,
[SDL_SCANCODE_F7] = SCANCODE_F7,
[SDL_SCANCODE_F8] = SCANCODE_F8,
[SDL_SCANCODE_F9] = SCANCODE_F9,
[SDL_SCANCODE_F10] = SCANCODE_F10,
[SDL_SCANCODE_NUMLOCKCLEAR] = SCANCODE_NUMLOCK,
[SDL_SCANCODE_SCROLLLOCK] = SCANCODE_SCROLL,
[SDL_SCANCODE_KP_7] = SCANCODE_NUMPAD7,
[SDL_SCANCODE_KP_8] = SCANCODE_NUMPAD8,
[SDL_SCANCODE_KP_9] = SCANCODE_NUMPAD9,
[SDL_SCANCODE_KP_MINUS] = SCANCODE_SUBTRACT,
[SDL_SCANCODE_KP_4] = SCANCODE_NUMPAD4,
[SDL_SCANCODE_KP_5] = SCANCODE_NUMPAD5,
[SDL_SCANCODE_KP_6] = SCANCODE_NUMPAD6,
[SDL_SCANCODE_KP_PLUS] = SCANCODE_ADD,
[SDL_SCANCODE_KP_1] = SCANCODE_NUMPAD1,
[SDL_SCANCODE_KP_2] = SCANCODE_NUMPAD2,
[SDL_SCANCODE_KP_3] = SCANCODE_NUMPAD3,
[SDL_SCANCODE_KP_0] = SCANCODE_NUMPAD0,
[SDL_SCANCODE_KP_PERIOD] = SCANCODE_DECIMAL,
[SDL_SCANCODE_NONUSBACKSLASH] = SCANCODE_OEM_102,
[SDL_SCANCODE_F11] = SCANCODE_F11,
[SDL_SCANCODE_F12] = SCANCODE_F12,
[SDL_SCANCODE_KP_ENTER] = SCANCODE_NUMPADENTER,
[SDL_SCANCODE_RCTRL] = SCANCODE_RCONTROL,
[SDL_SCANCODE_KP_DIVIDE] = SCANCODE_DIVIDE,
[SDL_SCANCODE_RALT] = SCANCODE_RALT,
[SDL_SCANCODE_PAUSE] = SCANCODE_PAUSE,
[SDL_SCANCODE_HOME] = SCANCODE_HOME,
[SDL_SCANCODE_UP] = SCANCODE_UP,
[SDL_SCANCODE_PAGEUP] = SCANCODE_PGUP,
[SDL_SCANCODE_LEFT] = SCANCODE_LEFT,
[SDL_SCANCODE_RIGHT] = SCANCODE_RIGHT,
[SDL_SCANCODE_END] = SCANCODE_END,
[SDL_SCANCODE_DOWN] = SCANCODE_DOWN,
[SDL_SCANCODE_PAGEDOWN] = SCANCODE_PGDN,
[SDL_SCANCODE_INSERT] = SCANCODE_INSERT,
[SDL_SCANCODE_DELETE] = SCANCODE_DELETE,
};
#endif /* _SDL2_SCANCODE_TO_DINPUT_H_ */

View File

@ -1,254 +0,0 @@
#if 0
#include "harness/hooks.h"
#include "harness/os.h"
#include "harness/win95_polyfill.h"
#include <assert.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#if defined(_WIN32) || defined(_WIN64)
#include <direct.h>
#include <windows.h>
// https://learn.microsoft.com/en-us/cpp/c-runtime-library/reference/getcwd-wgetcwd?view=msvc-170
#define getcwd _getcwd
#define chdir _chdir
#else
#include <dirent.h>
#include <libgen.h>
#include <unistd.h>
#endif
// All functions have a "_" suffix to avoid collisions with <windows.h>-defined types
uint32_t GetFileAttributesA_(char* lpFileName) {
FILE* f = fopen(lpFileName, "r");
if (f == NULL) {
return INVALID_FILE_ATTRIBUTES;
}
fclose(f);
return FILE_ATTRIBUTE_NORMAL;
}
int SetFileAttributesA_(char* lpFileName, uint32_t dwFileAttributes) {
// no-op for now
return 0;
}
void* CreateFileA_(char* lpFileName, uint32_t dwDesiredAccess, uint32_t dwShareMode, void* lpSecurityAttributes, uint32_t dwCreationDisposition, uint32_t dwFlagsAndAttributes, void* hTemplateFile) {
assert(dwDesiredAccess == GENERIC_READ);
assert(lpSecurityAttributes == NULL);
assert(dwCreationDisposition == OPEN_EXISTING);
FILE* f = fopen(lpFileName, "r");
if (!f) {
return INVALID_HANDLE_VALUE;
}
return f;
}
uint32_t GetFileSize_(void* hFile, uint32_t* lpFileSizeHigh) {
assert(lpFileSizeHigh == NULL);
long current_offset = ftell(hFile);
fseek(hFile, 0, SEEK_END);
long size = ftell(hFile);
fseek(hFile, current_offset, SEEK_SET);
return size;
}
int CloseHandle_(void* hObject) {
fclose(hObject);
return 0;
}
void GlobalMemoryStatus_(MEMORYSTATUS_* lpBuffer) {
lpBuffer->dwTotalPhys = 64000000;
lpBuffer->dwAvailPhys = 64000000; // pretend we have a whole 64mb of ram!
lpBuffer->dwAvailPageFile = 0;
lpBuffer->dwTotalVirtual = 0;
lpBuffer->dwAvailVirtual = 0;
lpBuffer->dwMemoryLoad = 0;
lpBuffer->dwTotalPageFile = 0;
}
int GetCursorPos_(POINT_* lpPoint) {
int x, y;
gHarness_platform.GetMousePosition(&x, &y);
lpPoint->x = x;
lpPoint->y = y;
return 0;
}
int ScreenToClient_(void* hWnd, POINT_* lpPoint) {
// no-op, we assume the point is already relative to client
return 0;
}
uint32_t timeGetTime_(void) {
return gHarness_platform.GetTicks();
}
uint32_t GetCurrentDirectoryA_(uint32_t nBufferLength, char* lpBuffer) {
char* ret = getcwd(lpBuffer, nBufferLength);
if (ret == NULL) {
return 0;
}
return strlen(lpBuffer);
}
int SetCurrentDirectoryA_(char* lpPathName) {
int ret = chdir(lpPathName);
// chdir returning zero means success, SetCurrentDirectory returning non-zero means success
if (ret == 0) {
return 1;
} else {
return 0;
}
}
HANDLE_ FindFirstFileA_(char* lpFileName, WIN32_FIND_DATAA_* lpFindFileData) {
assert(strcmp(lpFileName, "*.???") == 0);
#if defined(_WIN32) || defined(_WIN64)
WIN32_FIND_DATA fd;
void* hFile = FindFirstFile(lpFileName, &fd);
if (hFile != INVALID_HANDLE_VALUE) {
strcpy(lpFindFileData->cFileName, fd.cFileName);
}
return hFile;
#else
DIR* dir;
strcpy(lpFileName, ".");
dir = opendir(lpFileName);
if (dir == NULL) {
return INVALID_HANDLE_VALUE;
}
if (FindNextFileA_(dir, lpFindFileData)) {
return dir;
} else {
closedir(dir);
return INVALID_HANDLE_VALUE;
}
#endif
}
int FindNextFileA_(HANDLE_ hFindFile, WIN32_FIND_DATAA_* lpFindFileData) {
#if defined(_WIN32) || defined(_WIN64)
WIN32_FIND_DATA fd;
int result = FindNextFile(hFindFile, &fd);
if (result) {
strcpy(lpFindFileData->cFileName, fd.cFileName);
}
return result;
#else
struct dirent* entry;
if (hFindFile == NULL) {
return 0;
}
while ((entry = readdir(hFindFile)) != NULL) {
if (entry->d_type == DT_REG) {
strcpy(lpFindFileData->cFileName, entry->d_name);
return 1;
}
}
return 0;
#endif
}
int FindClose_(HANDLE_ hFindFile) {
#if defined(_WIN32) || defined(_WIN64)
return FindClose(hFindFile);
#else
return closedir(hFindFile);
#endif
}
void* CreateWindowExA_(uint32_t dwExStyle, char* lpClassName, char* lpWindowName, uint32_t dwStyle, int X, int Y, int nWidth, int nHeight, void* hWndParent, void* hMenu, void* hInstance, void* lpParam) {
gHarness_platform.CreateWindow_(lpWindowName, nWidth, nHeight, eWindow_type_software);
return NULL;
}
int SetWindowPos_(void* hWnd, void* hWndInsertAfter, int X, int Y, int cx, int cy, unsigned int uFlags) {
return gHarness_platform.SetWindowPos(hWnd, X, Y, cx, cy);
}
int ShowCursor_(int bShow) {
gHarness_platform.ShowCursor(bShow);
return 0;
}
int SendMessageA_(void* hWnd, unsigned int Msg, unsigned int wParam, long lParam) {
return 0;
}
int MessageBoxA_(void* hWnd, char* lpText, char* lpCaption, unsigned int uType) {
// only ever used for errors
assert(uType == MB_ICONERROR);
return gHarness_platform.ShowErrorMessage(hWnd, lpText, lpCaption);
}
int DestroyWindow_(void* hWnd) {
gHarness_platform.DestroyWindow(hWnd);
return 0;
}
void ExitProcess_(unsigned int uExitCode) {
exit(uExitCode);
}
void TranslateMessage_(MSG_* lpMsg) {
// no-op
}
void DispatchMessageA_(MSG_* lpMsg) {
// no-op
}
int PeekMessageA_(MSG_* lpMsg, void* hWnd, unsigned int wMsgFilterMin, unsigned int wMsgFilterMax, unsigned int wRemoveMsg) {
return gHarness_platform.ProcessWindowMessages(lpMsg);
}
int GetMessageA_(MSG_* lpMsg, void* hWnd, unsigned int wMsgFilterMin, unsigned int wMsgFilterMax) {
return gHarness_platform.ProcessWindowMessages(lpMsg);
}
void Sleep_(uint32_t dwMilliseconds) {
gHarness_platform.Sleep(dwMilliseconds);
}
void DirectDraw_CreateSurface(int width, int height) {
// no-op
}
void DirectInputDevice_GetDeviceState(unsigned int count, uint8_t* buffer) {
gHarness_platform.GetKeyboardState(count, buffer);
}
void DirectDrawDevice_SetPaletteEntries(PALETTEENTRY_* palette, int pFirst_colour, int pCount) {
assert(pFirst_colour == 0);
assert(pCount == 256);
gHarness_platform.Renderer_SetPalette(palette);
}
void _splitpath_(char* path, char* drive, char* dir, char* fname, char* ext) {
assert(dir == NULL);
assert(fname != NULL);
char* result = OS_Basename(path);
strcpy(fname, result);
}
int _CrtDbgReport_(int reportType, const char* filename, int linenumber, const char* moduleName, const char* format, ...) {
printf("_CrtDbgReport: (TODO)\n");
return 1;
}
#endif

View File

@ -1,31 +0,0 @@
#include "harness/winsock.h"
#ifndef _WIN32
int WSAStartup(int version, WSADATA* data) {
// very minimal, we don't care about the arguments
return 0;
}
int WSAGetLastError(void) {
return errno;
}
int WSACleanup(void) {
return 0;
}
// Only implement non-blocking call for now
int ioctlsocket(int handle, long cmd, unsigned long* argp) {
assert(cmd == FIONBIO);
int flags = fcntl(handle, F_GETFL);
flags |= O_NONBLOCK;
return fcntl(handle, F_SETFL, flags);
}
int closesocket(int handle) {
return close(handle);
}
#endif