diff --git a/polymer/build/include/baselayer.h b/polymer/build/include/baselayer.h index e070ab7da..ddef088cf 100644 --- a/polymer/build/include/baselayer.h +++ b/polymer/build/include/baselayer.h @@ -132,6 +132,8 @@ void wm_setapptitle(char *name); // baselayer.c int baselayer_init(); +void makeasmwriteable(void); + #ifdef __cplusplus } #endif diff --git a/polymer/build/src/a.masm b/polymer/build/src/a.masm index bd9ece295..6b1e03cac 100644 --- a/polymer/build/src/a.masm +++ b/polymer/build/src/a.masm @@ -111,9 +111,12 @@ CDECLENDSET MACRO numparams:REQ CDECLEND numparams ENDM -CODE SEGMENT PUBLIC USE32 'DATA' +CODE SEGMENT PUBLIC USE32 'CODE' ASSUME cs:CODE,ds:CODE +PUBLIC _dep_begin +_dep_begin: + ALIGN 16 PUBLIC _sethlinesizes _sethlinesizes: @@ -2660,5 +2663,7 @@ pentiumpro: pop ebx ;JBF ret +PUBLIC _dep_end +_dep_end: CODE ENDS END diff --git a/polymer/build/src/a.nasm b/polymer/build/src/a.nasm index 9ac5dbb21..7faa3f2e2 100644 --- a/polymer/build/src/a.nasm +++ b/polymer/build/src/a.nasm @@ -7,7 +7,7 @@ ;CPU 586 -SECTION .data +SECTION .text %ifdef UNDERSCORES %define asm1 _asm1 @@ -79,6 +79,8 @@ SECTION .data %define stretchhline _stretchhline %define mmxoverlay _mmxoverlay +%define dep_begin _dep_begin +%define dep_end _dep_end %endif ; Some macros to help make cdecl calling easier to manage @@ -225,6 +227,10 @@ SECTION .data GLOBAL stretchhline GLOBAL mmxoverlay + GLOBAL dep_begin + GLOBAL dep_end + +dep_begin: ALIGN 16 sethlinesizes: @@ -2749,3 +2755,4 @@ pentiumpro: pop ebx ;JBF ret +dep_end: diff --git a/polymer/build/src/a.wasm b/polymer/build/src/a.wasm index 6b68da6d2..dd8f4c234 100644 --- a/polymer/build/src/a.wasm +++ b/polymer/build/src/a.wasm @@ -39,9 +39,12 @@ EXTRN _espbak : dword EXTRN _pow2char : near EXTRN _pow2long : near -CODE SEGMENT PUBLIC USE32 'DATA' +CODE SEGMENT PUBLIC USE32 'CODE' ASSUME cs:CODE,ds:CODE +PUBLIC _dep_begin +_dep_begin: + ALIGN 16 PUBLIC sethlinesizes_ sethlinesizes_: @@ -2416,5 +2419,7 @@ pentiumpro: ret +PUBLIC _dep_end +_dep_end: CODE ENDS END diff --git a/polymer/build/src/engine.c b/polymer/build/src/engine.c index e03116982..351a799ca 100644 --- a/polymer/build/src/engine.c +++ b/polymer/build/src/engine.c @@ -5543,6 +5543,8 @@ int preinitengine(void) Bfree(spritesmooth); spritesmooth = Bcalloc(MAXSPRITES+MAXUNIQHUDID,sizeof(spritesmoothtype)); + makeasmwriteable(); + if ((e = Bgetenv("BUILD_NOP6")) != NULL) if (!Bstrcasecmp(e, "TRUE")) { Bprintf("Disabling P6 optimizations.\n"); diff --git a/polymer/build/src/sdlayer.c b/polymer/build/src/sdlayer.c index 8ecab37ad..08e518ce0 100644 --- a/polymer/build/src/sdlayer.c +++ b/polymer/build/src/sdlayer.c @@ -1669,3 +1669,39 @@ static int buildkeytranslationtable(void) return 0; } + +#if defined _WIN32 +# define WIN32_LEAN_AND_MEAN +# include +#elif defined __linux || defined __FreeBSD__ || defined __NetBSD__ || defined __OpenBSD__ +# include +#endif + +void makeasmwriteable(void) +{ +#ifndef ENGINE_USING_A_C + extern int dep_begin, dep_end; +# if defined _WIN32 + DWORD oldprot; + if (!VirtualProtect((LPVOID)&dep_begin, (SIZE_T)&dep_end - (SIZE_T)&dep_begin, PAGE_EXECUTE_READWRITE, &oldprot)) { + initprint("Error making code writeable\n"); + return; + } +# elif defined __linux || defined __FreeBSD__ || defined __NetBSD__ || defined __OpenBSD__ + int pagesize; + size_t dep_begin_page; + pagesize = sysconf(_SC_PAGE_SIZE); + if (pagesize == -1) { + initprintf("Error getting system page size\n"); + return; + } + dep_begin_page = ((size_t)&dep_begin) & ~(pagesize-1); + if (mprotect((const void *)dep_begin_page, (size_t)&dep_end - dep_begin_page, PROT_READ|PROT_WRITE) < 0) { + initprintf("Error making code writeable (errno=%d)\n", errno); + return; + } +# else +# error Don't know how to unprotect the self-modifying assembly on this platform! +# endif +#endif +} diff --git a/polymer/build/src/winlayer.c b/polymer/build/src/winlayer.c index bb1fff45f..b46830239 100644 --- a/polymer/build/src/winlayer.c +++ b/polymer/build/src/winlayer.c @@ -3802,3 +3802,17 @@ static LPTSTR GetWindowsErrorMsg(DWORD code) return lpMsgBuf; } +// +// makeasmwriteable() -- removes write protection from the self-modifying assembly code +// +void makeasmwriteable(void) +{ +#ifndef ENGINE_USING_A_C + extern int dep_begin, dep_end; + DWORD oldprot; + + if (!VirtualProtect((LPVOID)&dep_begin, (SIZE_T)&dep_end - (SIZE_T)&dep_begin, PAGE_EXECUTE_READWRITE, &oldprot)) { + ShowErrorBox("Problem making code writeable"); + } +#endif +} \ No newline at end of file diff --git a/polymer/eduke32/source/duke3d.h b/polymer/eduke32/source/duke3d.h index 7fd7145d4..2f1b4a900 100644 --- a/polymer/eduke32/source/duke3d.h +++ b/polymer/eduke32/source/duke3d.h @@ -825,7 +825,8 @@ enum spriteflags { SPRITE_FLAG_NOSHADE = 4, SPRITE_FLAG_PROJECTILE = 8, SPRITE_FLAG_DECAL = 16, - SPRITE_FLAG_BADGUY = 32 + SPRITE_FLAG_BADGUY = 32, + SPRITE_FLAG_NOPAL = 64 }; extern short spritecache[MAXTILES][3]; diff --git a/polymer/eduke32/source/game.c b/polymer/eduke32/source/game.c index 55554345b..9773d1d63 100644 --- a/polymer/eduke32/source/game.c +++ b/polymer/eduke32/source/game.c @@ -6719,7 +6719,7 @@ void animatesprites(long x,long y,int a,long smoothratio) PALONLY: - if (sector[sect].floorpal && sector[sect].floorpal < g_NumPalettes) + if (sector[sect].floorpal && sector[sect].floorpal < g_NumPalettes && !checkspriteflags(t->owner,SPRITE_FLAG_NOPAL)) t->pal = sector[sect].floorpal; if (s->owner == -1) continue; @@ -6760,7 +6760,7 @@ PALONLY: else t->picnum += T1; t->shade -= 6; - if (sector[sect].floorpal && sector[sect].floorpal < g_NumPalettes) + if (sector[sect].floorpal && sector[sect].floorpal < g_NumPalettes && !checkspriteflags(t->owner,SPRITE_FLAG_NOPAL)) t->pal = sector[sect].floorpal; break; @@ -6771,7 +6771,7 @@ PALONLY: break; } default: - if (sector[sect].floorpal && sector[sect].floorpal < g_NumPalettes) + if (sector[sect].floorpal && sector[sect].floorpal < g_NumPalettes && !checkspriteflags(t->owner,SPRITE_FLAG_NOPAL)) t->pal = sector[sect].floorpal; break; } diff --git a/polymer/eduke32/source/gamedef.c b/polymer/eduke32/source/gamedef.c index 3fcba10ae..3c0127995 100644 --- a/polymer/eduke32/source/gamedef.c +++ b/polymer/eduke32/source/gamedef.c @@ -436,6 +436,8 @@ static const char *keyw[] = "headspritesect", // 306 "prevspritesect", // 307 "nextspritesect", // 308 + "spritenopal", // 309 + "getkeyname", // 310 "" }; @@ -3300,6 +3302,7 @@ static int parsecommand(void) return 0; case CON_DRAGPOINT: + case CON_GETKEYNAME: transmultvars(3); return 0; @@ -3372,6 +3375,7 @@ static int parsecommand(void) case CON_SPRITESHADOW: case CON_SPRITENVG: case CON_SPRITENOSHADE: + case CON_SPRITENOPAL: case CON_PRECACHE: { if (parsing_state || parsing_actor) @@ -3403,6 +3407,9 @@ static int parsecommand(void) case CON_SPRITENOSHADE: spriteflags[*scriptptr] |= SPRITE_FLAG_NOSHADE; break; + case CON_SPRITENOPAL: + spriteflags[*scriptptr] |= SPRITE_FLAG_NOPAL; + break; case CON_PRECACHE: spritecache[*scriptptr][0] = j; transnum(LABEL_DEFINE); diff --git a/polymer/eduke32/source/gamedef.h b/polymer/eduke32/source/gamedef.h index 34a814348..582bcee54 100644 --- a/polymer/eduke32/source/gamedef.h +++ b/polymer/eduke32/source/gamedef.h @@ -788,5 +788,7 @@ enum keywords CON_HEADSPRITESECT, // 306 CON_PREVSPRITESECT, // 307 CON_NEXTSPRITESECT, // 308 + CON_SPRITENOPAL, // 309 + CON_GETKEYNAME, // 310 END }; diff --git a/polymer/eduke32/source/gameexec.c b/polymer/eduke32/source/gameexec.c index acced587b..973d21fe0 100644 --- a/polymer/eduke32/source/gameexec.c +++ b/polymer/eduke32/source/gameexec.c @@ -4385,6 +4385,19 @@ static int parse(void) break; } + case CON_GETKEYNAME: + insptr++; + { + int i = GetGameVarID(*insptr++, g_i, g_p), f=GetGameVarID(*insptr++, g_i, g_p); + + j=GetGameVarID(*insptr++, g_i, g_p); + + if (fta_quotes[i] != NULL && f < NUMGAMEFUNCTIONS && j < 2) + Bstrcpy(fta_quotes[i], KB_ScanCodeToString(ud.config.KeyboardKeys[f][j])); + + break; + } + case CON_MYOSX: case CON_MYOSPALX: case CON_MYOS: