From 9759bb3d127108bd809a5ce6f36c66609a3d7703 Mon Sep 17 00:00:00 2001 From: g-cont Date: Sat, 19 Jul 2008 00:00:00 +0400 Subject: [PATCH] 19 Jul 2008 --- engine/client/cl_cmds.c | 6 +- engine/client/cl_edict.h | 2 + engine/client/cl_menu.c | 1 + engine/client/cl_progs.c | 1 + engine/client/ui_edict.h | 2 + engine/server/sv_edict.h | 2 + engine/server/sv_progs.c | 3 +- imglib/img_dds.c | 105 +++-- launch/common/filesystem.c | 6 +- public/basefiles.h | 2 + public/dllapi.h | 1 + render/r_backend.c | 2 +- ripper/conv_main.c | 46 ++- ripper/conv_pcximage.c | 4 +- ripper/conv_wadlumps.c | 3 +- todo.log | 2 +- vprogs/pr_decomp.c | 794 +++++++++++++++++++++++++++++++++++++ vprogs/pr_edict.c | 94 +++-- vprogs/pr_local.h | 12 + vprogs/pr_main.c | 80 +++- vprogs/pr_utils.c | 16 +- vprogs/vprogs.dsp | 4 + vprogs/vprogs.h | 6 +- 23 files changed, 1046 insertions(+), 148 deletions(-) create mode 100644 vprogs/pr_decomp.c diff --git a/engine/client/cl_cmds.c b/engine/client/cl_cmds.c index c9d1fd11..09af5c1d 100644 --- a/engine/client/cl_cmds.c +++ b/engine/client/cl_cmds.c @@ -39,7 +39,7 @@ void CL_ScreenshotGetName( int lastnum, char *filename ) if(lastnum < 0 || lastnum > 9999) { // bound - com.sprintf( filename, "scrshots/%s/shot9999.dds", cl.configstrings[CS_NAME] ); + com.sprintf( filename, "scrshots/%s/shot9999.tga", cl.configstrings[CS_NAME] ); return; } @@ -51,7 +51,7 @@ void CL_ScreenshotGetName( int lastnum, char *filename ) lastnum -= c * 10; d = lastnum; - com.sprintf( filename, "scrshots/%s/shot%i%i%i%i.dds", cl.configstrings[CS_NAME], a, b, c, d ); + com.sprintf( filename, "scrshots/%s/shot%i%i%i%i.tga", cl.configstrings[CS_NAME], a, b, c, d ); } /* @@ -96,7 +96,7 @@ void CL_LevelShot_f( void ) char checkname[MAX_OSPATH]; // check for exist - com.sprintf( checkname, "gfx/background/%s.dds", cl.configstrings[CS_NAME] ); + com.sprintf( checkname, "gfx/background/%s.tga", cl.configstrings[CS_NAME] ); if(!FS_FileExists( checkname )) re->ScrShot( checkname, true ); else Msg("levelshot for this map already created\nFirst remove old image if you wants do it again\n" ); } diff --git a/engine/client/cl_edict.h b/engine/client/cl_edict.h index fd42bbde..feaeb3b2 100644 --- a/engine/client/cl_edict.h +++ b/engine/client/cl_edict.h @@ -90,4 +90,6 @@ static fields_t cl_reqfields[] = {16, 2, "flags"} }; +#define PROG_CRC_CLIENT 9488 + #endif//CL_EDICT_H \ No newline at end of file diff --git a/engine/client/cl_menu.c b/engine/client/cl_menu.c index cd066334..09432594 100644 --- a/engine/client/cl_menu.c +++ b/engine/client/cl_menu.c @@ -738,6 +738,7 @@ void UI_Init( void ) prog->init_cmd = VM_Cmd_Init; prog->reset_cmd = VM_Cmd_Reset; prog->error_cmd = VM_Error; + prog->filecrc = PROG_CRC_UIMENU; PRVM_LoadProgs( GI->uimenu_prog, 0, NULL, UI_NUM_REQFIELDS, ui_reqfields ); *prog->time = cls.realtime * 0.001f; diff --git a/engine/client/cl_progs.c b/engine/client/cl_progs.c index b78376fc..2a5cb08d 100644 --- a/engine/client/cl_progs.c +++ b/engine/client/cl_progs.c @@ -609,6 +609,7 @@ void CL_InitClientProgs( void ) prog->free_edict = CL_FreeEdict; prog->count_edicts = CL_CountEdicts; prog->load_edict = CL_LoadEdict; + prog->filecrc = PROG_CRC_CLIENT; // using default builtins prog->init_cmd = VM_Cmd_Init; diff --git a/engine/client/ui_edict.h b/engine/client/ui_edict.h index 47d4fbab..b148d827 100644 --- a/engine/client/ui_edict.h +++ b/engine/client/ui_edict.h @@ -108,4 +108,6 @@ static fields_t ui_reqfields[] = {93, 2, "find2"} }; +#define PROG_CRC_UIMENU 2460 + #endif//UI_EDICT_H \ No newline at end of file diff --git a/engine/server/sv_edict.h b/engine/server/sv_edict.h index 047efe5d..264241b6 100644 --- a/engine/server/sv_edict.h +++ b/engine/server/sv_edict.h @@ -294,4 +294,6 @@ static fields_t sv_reqfields[] = {264, 1, "oldmodel"} }; +#define PROG_CRC_SERVER 1320 + #endif//SV_EDICT_H \ No newline at end of file diff --git a/engine/server/sv_progs.c b/engine/server/sv_progs.c index 68169d05..aca75338 100644 --- a/engine/server/sv_progs.c +++ b/engine/server/sv_progs.c @@ -2463,7 +2463,8 @@ void SV_InitServerProgs( void ) prog->free_edict = SV_FreeEdict; prog->count_edicts = SV_CountEdicts; prog->load_edict = SV_LoadEdict; - + prog->filecrc = PROG_CRC_SERVER; + // using default builtins prog->init_cmd = VM_Cmd_Init; prog->reset_cmd = VM_Cmd_Reset; diff --git a/imglib/img_dds.c b/imglib/img_dds.c index ff92216f..19f0b5b7 100644 --- a/imglib/img_dds.c +++ b/imglib/img_dds.c @@ -139,19 +139,15 @@ static void Image_BaseColorSearch( byte *blkaddr, byte srccolors[4][4][4], byte if( nrcolor[0] == 0 ) nrcolor[0] = 1; if( nrcolor[1] == 0 ) nrcolor[1] = 1; - - for( i = 0; i < 3; i++ ) + for( j = 0; j < 2; j++ ) { - if((testcolor[0][i] + blockerrlin[0][i] / nrcolor[0]) <= 0) - testcolor[0][i] = 0; - else testcolor[0][i] = (testcolor[0][i] + blockerrlin[0][i] / nrcolor[0]); - } - - for( i = 0; i < 3; i++ ) - { - if((testcolor[1][i] + blockerrlin[1][i] / nrcolor[1]) >= 255) - testcolor[1][i] = 255; - else testcolor[1][i] = (testcolor[1][i] + blockerrlin[1][i] / nrcolor[1]); + for( i = 0; i < 3; i++ ) + { + int newvalue = testcolor[j][i] + blockerrlin[j][i] / nrcolor[j]; + if( newvalue <= 0 ) testcolor[j][i] = 0; + else if( newvalue >= 255 ) testcolor[j][i] = 255; + else testcolor[j][i] = newvalue; + } } if((abs(testcolor[0][0] - testcolor[1][0]) < 8) && (abs(testcolor[0][1] - testcolor[1][1]) < 4) && (abs(testcolor[0][2] - testcolor[1][2]) < 8)) @@ -259,8 +255,12 @@ static void Image_StoreBlock( byte *blkaddr, byte srccolors[4][4][4], byte *best if( color0 < color1 ) { - tempcolor = color0; color0 = color1; color1 = tempcolor; - colorptr = bestcolor[0]; bestcolor[0] = bestcolor[1]; bestcolor[1] = colorptr; + tempcolor = color0; + color0 = color1; + color1 = tempcolor; + colorptr = bestcolor[0]; + bestcolor[0] = bestcolor[1]; + bestcolor[1] = colorptr; } for( i = 0; i < 3; i++ ) @@ -372,7 +372,7 @@ static void Image_StoreBlock( byte *blkaddr, byte srccolors[4][4][4], byte *best } } -static void Image_EncodeColorBlock( byte *blkaddr, byte srccolors[4][4][4], int numxpixels, int numypixels, uint type ) +static void Image_EncodeColorBlock( byte *blkaddr, byte srccolors[4][4][4], int numxpixels, int numypixels, uint type, int flags ) { // simplistic approach. We need two base colors, simply use the "highest" and the "lowest" color // present in the picture as base colors @@ -413,6 +413,13 @@ static void Image_EncodeColorBlock( byte *blkaddr, byte srccolors[4][4][4], int } } + if( type != PF_DXT1 ) + { + // manually set alpha for DXT3 or DXT5 + if( flags & IMAGE_HAS_ALPHA ) haveAlpha = true; + else haveAlpha = false; + } + // make sure the original color values won't get touched... for( j = 0; j < 2; j++ ) { @@ -431,6 +438,18 @@ static void Image_EncodeColorBlock( byte *blkaddr, byte srccolors[4][4][4], int Image_StoreBlock( blkaddr, srccolors, bestcolor, numxpixels, numypixels, type, haveAlpha ); } +static void Image_StoreAlphaBlock( byte *blkaddr, byte alphabase1, byte alphabase2, byte alphaenc[16] ) +{ + *blkaddr++ = alphabase1; + *blkaddr++ = alphabase2; + *blkaddr++ = alphaenc[0] | (alphaenc[1] << 3) | ((alphaenc[2] & 3) << 6); + *blkaddr++ = (alphaenc[2] >> 2) | (alphaenc[3] << 1) | (alphaenc[4] << 4) | ((alphaenc[5] & 1) << 7); + *blkaddr++ = (alphaenc[5] >> 1) | (alphaenc[6] << 2) | (alphaenc[7] << 5); + *blkaddr++ = alphaenc[8] | (alphaenc[9] << 3) | ((alphaenc[10] & 3) << 6); + *blkaddr++ = (alphaenc[10] >> 2) | (alphaenc[11] << 1) | (alphaenc[12] << 4) | ((alphaenc[13] & 1) << 7); + *blkaddr++ = (alphaenc[13] >> 1) | (alphaenc[14] << 2) | (alphaenc[15] << 5); +} + static void Image_EncodeDXT5alpha( byte *blkaddr, byte srccolors[4][4][4], int numxpixels, int numypixels ) { byte alphabase[2], alphause[2]; @@ -486,8 +505,8 @@ static void Image_EncodeDXT5alpha( byte *blkaddr, byte srccolors[4][4][4], int n // find best encoding for alpha0 > alpha1 // it's possible this encoding is better even if both alphaabsmin and alphaabsmax are true alphablockerror1 = 0x0; - alphablockerror2 = 0xFFFFFF; - alphablockerror3 = 0xFFFFFF; + alphablockerror2 = 0xffffffff; + alphablockerror3 = 0xffffffff; if( alphaabsmin ) alphause[0] = 0; else alphause[0] = alphabase[0]; @@ -788,38 +807,10 @@ static void Image_EncodeDXT5alpha( byte *blkaddr, byte srccolors[4][4][4], int n // write the alpha values and encoding back. if((alphablockerror1 <= alphablockerror2) && (alphablockerror1 <= alphablockerror3)) - { - *blkaddr++ = alphause[1]; - *blkaddr++ = alphause[0]; - *blkaddr++ = alphaenc1[0] | (alphaenc1[1] << 3) | ((alphaenc1[2] & 3) << 6); - *blkaddr++ = (alphaenc1[2] >> 2) | (alphaenc1[3] << 1) | (alphaenc1[4] << 4) | ((alphaenc1[5] & 1) << 7); - *blkaddr++ = (alphaenc1[5] >> 1) | (alphaenc1[6] << 2) | (alphaenc1[7] << 5); - *blkaddr++ = alphaenc1[8] | (alphaenc1[9] << 3) | ((alphaenc1[10] & 3) << 6); - *blkaddr++ = (alphaenc1[10] >> 2) | (alphaenc1[11] << 1) | (alphaenc1[12] << 4) | ((alphaenc1[13] & 1) << 7); - *blkaddr++ = (alphaenc1[13] >> 1) | (alphaenc1[14] << 2) | (alphaenc1[15] << 5); - } + Image_StoreAlphaBlock( blkaddr, alphause[1], alphause[0], alphaenc1 ); else if( alphablockerror2 <= alphablockerror3 ) - { - *blkaddr++ = alphabase[0]; - *blkaddr++ = alphabase[1]; - *blkaddr++ = alphaenc2[0] | (alphaenc2[1] << 3) | ((alphaenc2[2] & 3) << 6); - *blkaddr++ = (alphaenc2[2] >> 2) | (alphaenc2[3] << 1) | (alphaenc2[4] << 4) | ((alphaenc2[5] & 1) << 7); - *blkaddr++ = (alphaenc2[5] >> 1) | (alphaenc2[6] << 2) | (alphaenc2[7] << 5); - *blkaddr++ = alphaenc2[8] | (alphaenc2[9] << 3) | ((alphaenc2[10] & 3) << 6); - *blkaddr++ = (alphaenc2[10] >> 2) | (alphaenc2[11] << 1) | (alphaenc2[12] << 4) | ((alphaenc2[13] & 1) << 7); - *blkaddr++ = (alphaenc2[13] >> 1) | (alphaenc2[14] << 2) | (alphaenc2[15] << 5); - } - else - { - *blkaddr++ = alphatest[0]; - *blkaddr++ = alphatest[1]; - *blkaddr++ = alphaenc3[0] | (alphaenc3[1] << 3) | ((alphaenc3[2] & 3) << 6); - *blkaddr++ = (alphaenc3[2] >> 2) | (alphaenc3[3] << 1) | (alphaenc3[4] << 4) | ((alphaenc3[5] & 1) << 7); - *blkaddr++ = (alphaenc3[5] >> 1) | (alphaenc3[6] << 2) | (alphaenc3[7] << 5); - *blkaddr++ = alphaenc3[8] | (alphaenc3[9] << 3) | ((alphaenc3[10] & 3) << 6); - *blkaddr++ = (alphaenc3[10] >> 2) | (alphaenc3[11] << 1) | (alphaenc3[12] << 4) | ((alphaenc3[13] & 1) << 7); - *blkaddr++ = (alphaenc3[13] >> 1) | (alphaenc3[14] << 2) | (alphaenc3[15] << 5); - } + Image_StoreAlphaBlock( blkaddr, alphabase[0], alphabase[1], alphaenc2 ); + else Image_StoreAlphaBlock( blkaddr, (byte)alphatest[0], (byte)alphatest[1], alphaenc3 ); } static void Image_ExtractColors( byte srcpixels[4][4][4], const byte *srcaddr, int srcRowStride, int numxpixels, int numypixels, int comps ) @@ -1509,9 +1500,9 @@ size_t Image_CompressDXT( vfile_t *f, int saveformat, rgbdata_t *pix ) { byte srcpixels[4][4][4]; int numxpixels, numypixels; + byte *blkaddr, *dest, *flip = NULL; int i, j, width, height; const byte *srcaddr; - byte *blkaddr, *dest; size_t dst_size; int srccomps; @@ -1528,14 +1519,13 @@ size_t Image_CompressDXT( vfile_t *f, int saveformat, rgbdata_t *pix ) int x, y, c; byte *in = pix->buffer; uint line = pix->width * srccomps; - byte *out = Mem_Alloc( zonepool, pix->size ); // alloc src image size - + + flip = Mem_Alloc( zonepool, pix->size ); // alloc src image size for( y = pix->height - 1; y >= 0; y-- ) for( x = 0; x < pix->width; x++ ) for( c = 0; c < srccomps; c++, in++) - pix->buffer[y*line+x*srccomps+c] = *in; - //FIXME: Mem_Free( pix->buffer ); - pix->buffer = out; + flip[y*line+x*srccomps+c] = *in; + pix->buffer = flip; } blkaddr = dest = Mem_Alloc( zonepool, dst_size ); // alloc dst image size @@ -1553,7 +1543,7 @@ size_t Image_CompressDXT( vfile_t *f, int saveformat, rgbdata_t *pix ) if( width > i + 3 ) numxpixels = 4; else numxpixels = width - i; Image_ExtractColors( srcpixels, srcaddr, width, numxpixels, numypixels, srccomps ); - Image_EncodeColorBlock( blkaddr, srcpixels, numxpixels, numypixels, saveformat ); + Image_EncodeColorBlock( blkaddr, srcpixels, numxpixels, numypixels, saveformat, pix->flags ); srcaddr += srccomps * numxpixels; blkaddr += 8; } @@ -1579,7 +1569,7 @@ size_t Image_CompressDXT( vfile_t *f, int saveformat, rgbdata_t *pix ) *blkaddr++ = (srcpixels[2][2][3] >> 4) | (srcpixels[2][3][3] & 0xf0); *blkaddr++ = (srcpixels[3][0][3] >> 4) | (srcpixels[3][1][3] & 0xf0); *blkaddr++ = (srcpixels[3][2][3] >> 4) | (srcpixels[3][3][3] & 0xf0); - Image_EncodeColorBlock( blkaddr, srcpixels, numxpixels, numypixels, saveformat ); + Image_EncodeColorBlock( blkaddr, srcpixels, numxpixels, numypixels, saveformat, pix->flags ); srcaddr += srccomps * numxpixels; blkaddr += 8; } @@ -1599,7 +1589,7 @@ size_t Image_CompressDXT( vfile_t *f, int saveformat, rgbdata_t *pix ) Image_ExtractColors( srcpixels, srcaddr, width, numxpixels, numypixels, srccomps ); Image_EncodeDXT5alpha( blkaddr, srcpixels, numxpixels, numypixels ); - Image_EncodeColorBlock( blkaddr + 8, srcpixels, numxpixels, numypixels, saveformat ); + Image_EncodeColorBlock( blkaddr + 8, srcpixels, numxpixels, numypixels, saveformat, pix->flags ); srcaddr += srccomps * numxpixels; blkaddr += 16; } @@ -1612,6 +1602,7 @@ size_t Image_CompressDXT( vfile_t *f, int saveformat, rgbdata_t *pix ) } dst_size = VFS_Write( f, dest, dst_size ); if( dest ) Mem_Free( dest ); + if( flip ) Mem_Free( flip ); return dst_size; } diff --git a/launch/common/filesystem.c b/launch/common/filesystem.c index ca009be4..b1eb330b 100644 --- a/launch/common/filesystem.c +++ b/launch/common/filesystem.c @@ -1393,9 +1393,9 @@ void FS_CreateGameInfo( const char *filename ) com_strncat(buffer, va("gamemode\t\t\"singleplayer\"\rgamekey\t\t\"%s\"", GI.key), MAX_SYSPATH ); com_strncat(buffer, "\nstartmap\t\t\"newmap\"\n\n", MAX_SYSPATH ); com_strncat(buffer, "// name or each prog (\"\" - ignore to load)", MAX_SYSPATH ); - com_strncat(buffer, "\nserver\t\t\"server.dat\"", MAX_SYSPATH ); - com_strncat(buffer, "\nclient\t\t\"client.dat\"", MAX_SYSPATH ); - com_strncat(buffer, "\nuimenu\t\t\"uimenu.dat\"", MAX_SYSPATH ); + com_strncat(buffer, "\nserver\t\t\"vprogs/server.dat\"", MAX_SYSPATH ); + com_strncat(buffer, "\nclient\t\t\"vprogs/client.dat\"", MAX_SYSPATH ); + com_strncat(buffer, "\nuimenu\t\t\"vrpogs/uimenu.dat\"", MAX_SYSPATH ); FS_WriteFile( filename, buffer, com_strlen(buffer)); Mem_Free( buffer ); diff --git a/public/basefiles.h b/public/basefiles.h index 15a2b9d7..d0ec39cc 100644 --- a/public/basefiles.h +++ b/public/basefiles.h @@ -309,6 +309,7 @@ enum PRVM_SERVERPROG = 0, PRVM_CLIENTPROG, PRVM_MENUPROG, + PRVM_DECOMPILED, PRVM_MAXPROGS, // must be last }; @@ -561,6 +562,7 @@ typedef struct prvm_prog_s ddef_t *fielddefs; ddef_t *globaldefs; dstatement_t *statements; + includeddatafile_t *sources; // debug version include packed source files int *linenums; // debug versions only type_t *types; int edict_size; // in bytes diff --git a/public/dllapi.h b/public/dllapi.h index ff8c5586..c655edb6 100644 --- a/public/dllapi.h +++ b/public/dllapi.h @@ -423,6 +423,7 @@ typedef struct vprogs_exp_s // compiler functions void ( *PrepareDAT )( const char *dir, const char *name ); void ( *CompileDAT )( void ); + bool ( *DecompileDAT )( void ); // edict operations void (*WriteGlobals)( vfile_t *f ); diff --git a/render/r_backend.c b/render/r_backend.c index 38018a66..4c389503 100644 --- a/render/r_backend.c +++ b/render/r_backend.c @@ -570,7 +570,7 @@ bool VID_ScreenShot( const char *filename, bool levelshot ) r_shot->width = r_width->integer; r_shot->height = r_height->integer; r_shot->type = PF_RGB_24_FLIP; - r_shot->hint = PF_DXT3; // save format + r_shot->hint = PF_RGB_24; // save format r_shot->size = r_shot->width * r_shot->height * 3; r_shot->numLayers = 1; r_shot->numMips = 1; diff --git a/ripper/conv_main.c b/ripper/conv_main.c index 523d0e0e..dd8c1a27 100644 --- a/ripper/conv_main.c +++ b/ripper/conv_main.c @@ -7,7 +7,9 @@ #include "pal_utils.h" dll_info_t imglib_dll = { "imglib.dll", NULL, "CreateAPI", NULL, NULL, true, sizeof(imglib_exp_t) }; +dll_info_t vprogs_dll = { "vprogs.dll", NULL, "CreateAPI", NULL, NULL, true, sizeof(vprogs_exp_t) }; imglib_exp_t *Image; +vprogs_exp_t *PRVM; stdlib_api_t com; byte *basepool; byte *zonepool; @@ -112,8 +114,9 @@ so do it manually */ void InitConvertor ( uint funcname, int argc, char **argv ) { - launch_t CreateImglib; - + launch_t CreateImglib, CreateVprogs; + string source, gamedir; + // init pools basepool = Mem_AllocPool( "Temp" ); zonepool = Mem_AllocPool( "Zone" ); @@ -123,13 +126,34 @@ void InitConvertor ( uint funcname, int argc, char **argv ) CreateImglib = (void *)imglib_dll.main; Image = CreateImglib( &com, NULL ); // second interface not allowed - FS_InitRootDir("."); - Image->Init( funcname ); // initialize image support + switch( funcname ) + { + case RIPP_QCCDEC: + Sys_LoadLibrary( &vprogs_dll ); // load qcclib + CreateVprogs = (void *)vprogs_dll.main; + PRVM = CreateVprogs( &com, NULL ); // second interface not allowed + + PRVM->Init( funcname, argc, argv ); + + if(!FS_GetParmFromCmdLine("-dir", gamedir )) + com.strncpy( gamedir, ".", sizeof(gamedir)); + if(!FS_GetParmFromCmdLine("+dat", source )) + com.strncpy( source, "progs.dat", sizeof(source)); + + start = Sys_DoubleTime(); + PRVM->PrepareDAT( gamedir, source ); + break; + default: + FS_InitRootDir("."); + Image->Init( funcname ); // initialize image support + break; + } + start = Sys_DoubleTime(); Msg("Converting ...\n\n"); } -void RunConvertor ( void ) +void RunConvertor( void ) { search_t *search; string errorstring; @@ -183,9 +207,13 @@ void RunConvertor ( void ) AddMask( "*.snd" ); AddMask( "*.mus" ); break; - case RIPP_BSPDEC: case RIPP_QCCDEC: - Sys_Break(" not implemented\n"); + if(PRVM->DecompileDAT()) + numConvertedRes++; + break; + case RIPP_BSPDEC: + Sys_Break(" not implemented\n"); + break; case HOST_OFFLINE: default: return; } @@ -197,7 +225,7 @@ void RunConvertor ( void ) } // directory to extract - com.strncpy(gs_gamedir, "tmpQuArK", sizeof(gs_gamedir)); + com.strncpy( gs_gamedir, "tmpQuArK", sizeof(gs_gamedir)); // search by mask for( i = 0; i < num_searchmask; i++) @@ -214,7 +242,7 @@ void RunConvertor ( void ) } Mem_Free( search ); } - if(numConvertedRes == 0) + if( numConvertedRes == 0 ) { for(j = 0; j < 16; j++) { diff --git a/ripper/conv_pcximage.c b/ripper/conv_pcximage.c index bd9d737b..351a7f35 100644 --- a/ripper/conv_pcximage.c +++ b/ripper/conv_pcximage.c @@ -44,7 +44,7 @@ bool PCX_ConvertImage( const char *name, char *buffer, int filesize ) MsgDev( D_ERROR, "ConvPCX: (%s) have illegal pixel size '%d'\n", name, pcx.bits_per_pixel ); return false; } - if(pic.width > 640 || pic.height > 640 || pic.width <= 0 || pic.height <= 0) + if(pic.width >= 640 || pic.height >= 480 || pic.width <= 0 || pic.height <= 0) { MsgDev( D_ERROR, "ConvPCX: (%s) dimensions out of range [%dx%d]\n", name, pic.width, pic.height ); return false; @@ -89,7 +89,7 @@ bool PCX_ConvertImage( const char *name, char *buffer, int filesize ) for (i = 0; i < s; i++) { p = pbuf[i]; - if (p == 255) + if( p == 255 ) { pic.flags |= IMAGE_HAS_ALPHA; // found alpha channel ((byte *)&trans[i])[0] = ((byte *)&d_currentpal[0])[0]; diff --git a/ripper/conv_wadlumps.c b/ripper/conv_wadlumps.c index 53691ef3..9063c5c1 100644 --- a/ripper/conv_wadlumps.c +++ b/ripper/conv_wadlumps.c @@ -282,6 +282,7 @@ bool ConvLMP( const char *name, char *buffer, int filesize ) pic.buffer = (byte *)Mem_Alloc(zonepool, pic.size ); pic.numLayers = 1; pic.type = PF_RGBA_32; + pic.hint = PF_RGBA_32; // half-life 1.0.0.1 lmp version with palette if( filesize > (int)sizeof(lmp) + pixels ) @@ -301,7 +302,7 @@ bool ConvLMP( const char *name, char *buffer, int filesize ) FS_StripExtension((char *)name ); Conv_GetPaletteLMP( pal, LUMP_NORMAL ); Conv_Copy8bitRGBA( fin, pic.buffer, pixels ); - Image->SaveImage(va("%s/gfx/%s.tga", gs_gamedir, name ), &pic ); // save converted image + Image->SaveImage(va("%s/%s.tga", gs_gamedir, name ), &pic ); // save converted image Mem_Free( pic.buffer ); // release buffer Msg("%s.lmp\n", name ); // echo to console about current image diff --git a/todo.log b/todo.log index a73be16c..4fcfb1e0 100644 --- a/todo.log +++ b/todo.log @@ -45,7 +45,7 @@ fopen NEW RENDERER -1. Доделать поддержку DXT-форматов +1. Доделать поддержку DXT-форматов OK 2. Нормальная линковка OpenGL32.dll diff --git a/vprogs/pr_decomp.c b/vprogs/pr_decomp.c new file mode 100644 index 00000000..c91544b7 --- /dev/null +++ b/vprogs/pr_decomp.c @@ -0,0 +1,794 @@ +//======================================================================= +// Copyright XashXT Group 2007 © +// pr_decomp.c - progs decompiler +//======================================================================= + +#include "vprogs.h" +#include "mathlib.h" + +type_t **ofstype; +byte *ofsflags; +file_t *file; + +char *PR_VarAtOfs( int ofs ) +{ + static char buf[MAX_INPUTLINE]; + int typen; + ddef_t *def; + + if( ofsflags[ofs] & 8 ) def = PRVM_ED_GlobalAtOfs( ofs ); + else def = NULL; + + if( !def ) + { + if( ofsflags[ofs] & 3 ) + { + if( ofstype[ofs] ) com.sprintf( buf, "_v_%s_%i", ofstype[ofs]->name, ofs ); + else com.sprintf( buf, "_v_%i", ofs ); + } + else + { + if( ofstype[ofs] ) + { + typen = ofstype[ofs]->type; + goto evaluate_immediate; + } + else com.sprintf( buf, "_c_%i", ofs ); + } + return buf; + } + + if(!PRVM_GetString( def->s_name ) || !com.strcmp(PRVM_GetString( def->s_name ), "IMMEDIATE" )) + { + if( vm.prog->types ) typen = vm.prog->types[def->type & ~DEF_SHARED].type; + else typen = def->type & ~(DEF_SHARED|DEF_SAVEGLOBAL); + +evaluate_immediate: + switch( typen ) + { + case ev_float: + com.sprintf( buf, "%f", PRVM_G_FLOAT(ofs)); + return buf; + case ev_vector: + com.sprintf( buf, "\'%f %f %f\'", PRVM_G_FLOAT(ofs+0), PRVM_G_FLOAT(ofs+1), PRVM_G_FLOAT(ofs+2)); + return buf; + case ev_string: + { + char *s, *s2; + + s = buf; + *s++ = '\"'; + s2 = vm.prog->strings + PRVM_G_INT( ofs ); + + if( s2 ) + { + while( *s2 ) + { + if( *s2 == '\n' ) + { + *s++ = '\\'; + *s++ = 'n'; + s2++; + } + else if( *s2 == '\"' ) + { + *s++ = '\\'; + *s++ = '\"'; + s2++; + } + else if( *s2 == '\t' ) + { + *s++ = '\\'; + *s++ = 't'; + s2++; + } + else *s++ = *s2++; + } + *s++ = '\"'; + *s++ = '\0'; + } + } + return buf; + case ev_pointer: + com.sprintf( buf, "_c_pointer_%i", ofs ); + return buf; + default: + com.sprintf( buf, "_c_%i", ofs ); + return buf; + } + } + return (char *)PRVM_GetString( def->s_name ); +} + +int PR_ImmediateReadLater( uint ofs, int firstst ) +{ + dstatement_t *st; + + + if( ofsflags[ofs] & 8 ) return false; // this is a global/local/pramater, not a temp + if(!(ofsflags[ofs] & 3)) return false; // this is a constant. + + for( st = &((dstatement_t*)vm.prog->statements)[firstst]; ; st++, firstst++ ) + { + // if written, return false, if read, return true. + if( st->op >= OP_CALL0 && st->op <= OP_CALL8 ) + { + if( ofs == OFS_RETURN ) return false; + if( ofs < OFS_PARM0 + 3*((uint)st->op - OP_CALL0 )) + return true; + } + else if( pr_opcodes[st->op].associative == ASSOC_RIGHT ) + { + if( ofs == st->b ) return false; + if( ofs == st->a ) return true; + } + else + { + if( st->a == ofs ) return true; + if( st->b == ofs ) return true; + if( st->c == ofs ) return false; + } + + // we missed our chance. (return/done ends any code coherancy). + if( st->op == OP_DONE || st->op == OP_RETURN ) + return false; + } + return false; +} + +int PR_ProductReadLater( int stnum ) +{ + dstatement_t *st = &((dstatement_t*)vm.prog->statements)[stnum]; + + if( pr_opcodes[st->op].priority == -1 ) + { + if( st->op >= OP_CALL0 && st->op <= OP_CALL7 ) + return PR_ImmediateReadLater( OFS_RETURN, stnum + 1 ); + return false; // these don't have products... + } + + if( pr_opcodes[st->op].associative == ASSOC_RIGHT ) + return PR_ImmediateReadLater( st->b, stnum + 1 ); + else return PR_ImmediateReadLater( st->c, stnum + 1 ); +} + +/* +======================= +PR_WriteStatementProducingOfs + +recursive, works backwards +======================= +*/ +void PR_WriteStatementProducingOfs( int lastnum, int firstpossible, int ofs ) +{ + dstatement_t *st; + ddef_t *def; + int i; + + if( ofs == 0 ) longjmp( pr_parse_abort, 1 ); + + for( ; lastnum >= firstpossible; lastnum-- ) + { + st = &((dstatement_t*)vm.prog->statements)[lastnum]; + if( st->op >= OP_CALL0 && st->op < OP_CALL7 ) + { + if( ofs != OFS_RETURN ) continue; + PR_WriteStatementProducingOfs( lastnum - 1, firstpossible, st->a ); + FS_Printf( file, "(" ); + for( i = 0; i < st->op - OP_CALL0; i++ ) + { + PR_WriteStatementProducingOfs( lastnum-1, firstpossible, OFS_PARM0 + i*3 ); + if( i != st->op - OP_CALL0 - 1 ) FS_Printf( file, ", " ); + } + FS_Printf( file, ")" ); + return; + } + else if( pr_opcodes[st->op].associative == ASSOC_RIGHT ) + { + if( st->b != ofs ) continue; + if(!PR_ImmediateReadLater( st->b, lastnum + 1 )) + { + FS_Printf( file, "(" ); + PR_WriteStatementProducingOfs( lastnum - 1, firstpossible, st->b ); + FS_Printf( file, " " ); + FS_Printf( file, pr_opcodes[st->op].name ); + FS_Printf( file, " "); + PR_WriteStatementProducingOfs( lastnum - 1, firstpossible, st->a ); + FS_Printf( file, ")" ); + return; + } + PR_WriteStatementProducingOfs( lastnum - 1, firstpossible, st->a ); + return; + } + else + { + if( st->c != ofs ) continue; + + if(!PR_ImmediateReadLater( st->c, lastnum + 1 )) + { + PR_WriteStatementProducingOfs( lastnum - 1, firstpossible, st->c ); + FS_Printf( file, " = " ); + } + FS_Printf( file, "(" ); + PR_WriteStatementProducingOfs( lastnum-1, firstpossible, st->a ); + + if( !com.strcmp( pr_opcodes[st->op].name, "." )) + FS_Printf( file, pr_opcodes[st->op].name ); // extra spaces around .s are ugly. + else + { + FS_Printf( file, " " ); + FS_Printf( file, pr_opcodes[st->op].name); + FS_Printf( file, " " ); + } + PR_WriteStatementProducingOfs( lastnum-1, firstpossible, st->b ); + FS_Printf( file, ")" ); + return; + } + } + + def = PRVM_ED_GlobalAtOfs( ofs ); + if( def ) + { + if(!com.strcmp( PRVM_GetString( def->s_name ), "IMMEDIATE" )) + FS_Printf( file, "%s", PR_VarAtOfs( ofs )); + else FS_Printf( file, "%s", PRVM_GetString( def->s_name )); + } + else FS_Printf( file, "%s", PR_VarAtOfs( ofs )); +} + +int PR_WriteStatement( int stnum, int firstpossible ) +{ + int count, skip; + dstatement_t *st = &((dstatement_t*)vm.prog->statements)[stnum]; + + switch( st->op ) + { + case OP_IFNOT: + count = (signed short)st->b; + FS_Printf(file, "if ("); + PR_WriteStatementProducingOfs( stnum, firstpossible, st->a ); + FS_Printf( file, ")\r\n" ); + FS_Printf( file, "{\r\n" ); + firstpossible = stnum + 1; + count--; + stnum++; + while( count ) + { + if(PR_ProductReadLater( stnum )) + { + count--; + stnum++; + continue; + } + skip = PR_WriteStatement( stnum, firstpossible ); + count -= skip; + stnum += skip; + } + FS_Printf( file, "}\r\n" ); + st = &((dstatement_t*)vm.prog->statements)[stnum]; + if( st->op == OP_GOTO ) + { + count = (signed short)st->b; + count--; + stnum++; + + FS_Printf( file, "else\r\n" ); + FS_Printf( file, "{\r\n" ); + while( count ) + { + if( PR_ProductReadLater( stnum )) + { + count--; + stnum++; + continue; + } + skip = PR_WriteStatement( stnum, firstpossible ); + count -= skip; + stnum += skip; + } + FS_Printf( file, "}\r\n" ); + } + break; + case OP_IF: + longjmp( pr_parse_abort, 1 ); + break; + case OP_GOTO: + longjmp( pr_parse_abort, 1 ); + break; + case OP_RETURN: + case OP_DONE: + if( st->a ) PR_WriteStatementProducingOfs( stnum - 1, firstpossible, st->a ); + break; + case OP_CALL0: + case OP_CALL1: + case OP_CALL2: + case OP_CALL3: + case OP_CALL4: + case OP_CALL5: + case OP_CALL6: + case OP_CALL7: + PR_WriteStatementProducingOfs( stnum, firstpossible, OFS_RETURN ); + FS_Printf( file, ";\r\n" ); + break; + default: + if( pr_opcodes[st->op].associative == ASSOC_RIGHT ) + PR_WriteStatementProducingOfs( stnum, firstpossible, st->b ); + else PR_WriteStatementProducingOfs( stnum, firstpossible, st->c ); + FS_Printf( file, ";\r\n" ); + break; + } + return 1; +} + +void PR_WriteAsmStatements( file_t *f, int num, const char *functionname ) +{ + int stn = vm.prog->functions[num].first_statement; + int fileofs, ofs, i; + dstatement_t *st = NULL; + ddef_t *def; + opcode_t *op; + prvm_eval_t *v; + + // we wrote this one... + if( !functionname && stn < 0 ) return; + + if( stn >= 0 ) + { + for( stn = vm.prog->functions[num].first_statement; stn < (signed int)vm.prog->progs->numstatements; stn++ ) + { + st = &((dstatement_t*)vm.prog->statements)[stn]; + if( st->op == OP_DONE || st->op == OP_RETURN ) + { + if( !st->a ) FS_Printf(f, "void("); + else if( ofstype[st->a] ) + { + FS_Printf( f, "%s", ofstype[st->a]->name ); + FS_Printf( f, "(" ); + } + else FS_Printf( f, "function(" ); + break; + } + } + st = NULL; + stn = vm.prog->functions[num].first_statement; + } + else FS_Printf( f, "function(" ); + for( ofs = vm.prog->functions[num].parm_start, i = 0; i < vm.prog->functions[num].numparms; i++, ofs += vm.prog->functions[num].parm_size[i] ) + { + ofsflags[ofs] |= 4; + + def = PRVM_ED_GlobalAtOfs( ofs ); + if( def && stn >= 0 ) + { + if( st ) FS_Printf( f, ", " ); + st = (void *)0xffff; + + if( !PRVM_GetString( def->s_name )) + { + char mem[64]; + com.sprintf( mem, "_p_%i", def->ofs ); + def->s_name = PRVM_SetTempString( mem ); + } + + if( vm.prog->types ) + { + FS_Printf( f, "%s %s", vm.prog->types[def->type&~(DEF_SHARED|DEF_SAVEGLOBAL)].name, PRVM_GetString( def->s_name )); + } + else + switch( def->type&~(DEF_SHARED|DEF_SAVEGLOBAL)) + { + case ev_string: + FS_Printf( f, "%s %s", "string", PRVM_GetString( def->s_name )); + break; + case ev_float: + FS_Printf(f, "%s %s", "float", PRVM_GetString( def->s_name )); + break; + case ev_entity: + FS_Printf(f, "%s %s", "entity", PRVM_GetString( def->s_name )); + break; + case ev_vector: + FS_Printf(f, "%s %s", "vector", PRVM_GetString( def->s_name )); + break; + default: + FS_Printf(f, "%s %s", "unknown", PRVM_GetString( def->s_name )); + break; + } + } + } + for( ofs = vm.prog->functions[num].parm_start + vm.prog->functions[num].numparms, i = vm.prog->functions[num].numparms; i < vm.prog->functions[num].locals; i++, ofs++ ) + ofsflags[ofs] |= 4; + + if( !PRVM_GetString( vm.prog->functions[num].s_name )) + { + if( !functionname ) + { + char mem[64]; + com.sprintf( mem, "_bi_%i", num ); + vm.prog->functions[num].s_name = PRVM_SetTempString( mem ); + } + else vm.prog->functions[num].s_name = PRVM_SetTempString( functionname ); + } + + FS_Printf( f, ") %s", PRVM_GetString( vm.prog->functions[num].s_name )); + + if( stn < 0 ) + { + stn *= -1; + FS_Printf( f, " = #%i;\r\n", stn ); + return; + } + + if( functionname ) + { + // parsing defs + FS_Printf(f, ";\r\n"); + return; + } + + fileofs = FS_Seek( f, 0, SEEK_CUR ); + if( setjmp(pr_parse_abort)) + { + FS_Printf( f, "*/\r\n" ); + FS_Printf( f, " = asm {\r\n" ); + + stn = vm.prog->functions[num].first_statement; + for( ofs = vm.prog->functions[num].parm_start + vm.prog->functions[num].numparms, i = vm.prog->functions[num].numparms; i < vm.prog->functions[num].locals; i++, ofs++ ) + { + def = PRVM_ED_GlobalAtOfs( ofs ); + if( def ) + { + v = (prvm_eval_t *)&((int *)vm.prog->globals.gp)[def->ofs]; + if( vm.prog->types ) + FS_Printf( f, "\tlocal %s %s;\r\n", vm.prog->types[def->type&~(DEF_SHARED|DEF_SAVEGLOBAL)].name, PRVM_GetString( def->s_name )); + else + { + if(!PRVM_GetString( def->s_name )) + { + char mem[64]; + com.sprintf( mem, "_l_%i", def->ofs ); + def->s_name = PRVM_SetTempString( mem ); + } + + switch( def->type&~(DEF_SHARED|DEF_SAVEGLOBAL)) + { + case ev_string: + FS_Printf( f, "\tlocal %s %s;\r\n", "string", PRVM_GetString( def->s_name )); + break; + case ev_float: + FS_Printf(f, "\tlocal %s %s;\r\n", "float", PRVM_GetString( def->s_name )); + break; + case ev_entity: + FS_Printf(f, "\tlocal %s %s;\r\n", "entity", PRVM_GetString( def->s_name )); + break; + case ev_vector: + if(!VectorIsNull( v->vector )) + FS_Printf( f, "\tlocal vector %s = '%f %f %f';\r\n", PRVM_GetString( def->s_name ), v->vector[0], v->vector[1], v->vector[2] ); + else FS_Printf( f, "\tlocal %s %s;\r\n", "vector", PRVM_GetString( def->s_name )); + ofs += 2; // skip floats; + break; + default: + FS_Printf( f, "\tlocal %s %s;\r\n", "unknown", PRVM_GetString( def->s_name )); + break; + } + } + } + } + + while( 1 ) + { + st = &((dstatement_t*)vm.prog->statements)[stn]; + if( !st->op ) break; // end of function statement! + + op = &pr_opcodes[st->op]; + FS_Printf( f, "\t%s", op->opname ); + + if( op->priority == -1 && op->associative == ASSOC_RIGHT ) + { + // last param is a goto + if( op->type_b == &type_void ) + { + if( st->a ) FS_Printf( f, " %i", (signed short)st->a ); + } + else if( op->type_c == &type_void ) + { + if( st->a ) FS_Printf( f, " %s", PR_VarAtOfs(st->a)); + if( st->b ) FS_Printf( f, " %i", (signed short)st->b ); + } + else + { + if( st->a ) FS_Printf( f, " %s", PR_VarAtOfs(st->a)); + if( st->b ) FS_Printf( f, " %s", PR_VarAtOfs(st->b)); + if( st->c ) FS_Printf( f, " %i", (signed short)st->c ); // rightness means it uses a as c + } + } + else + { + if( st->a ) + { + if( op->type_a == NULL ) FS_Printf( f, " %i", (signed short)st->a ); + else FS_Printf(f, " %s", PR_VarAtOfs(st->a)); + } + if( st->b ) + { + if( op->type_b == NULL ) FS_Printf( f, " %i", (signed short)st->b ); + else FS_Printf( f, " %s", PR_VarAtOfs(st->b)); + } + if( st->c && op->associative != ASSOC_RIGHT ) + { + // rightness means it uses a as c + if( op->type_c == NULL ) FS_Printf( f, " %i", (signed short)st->c ); + else FS_Printf( f, " %s", PR_VarAtOfs(st->c)); + } + } + FS_Printf( f, ";\r\n" ); + stn++; + } + } + else + { + if( !com.strcmp(PRVM_GetString( vm.prog->functions[num].s_name ), "SUB_Remove" )) + file = NULL; + file = f; + FS_Printf( f, "/*\r\n" ); + + FS_Printf( f, " =\r\n{\r\n" ); + + for( ofs = vm.prog->functions[num].parm_start + vm.prog->functions[num].numparms, i = vm.prog->functions[num].numparms; i < vm.prog->functions[num].locals; i++, ofs++ ) + { + def = PRVM_ED_GlobalAtOfs( ofs ); + if( def ) + { + v = (prvm_eval_t *)&((int *)vm.prog->globals.gp)[def->ofs]; + if( vm.prog->types) FS_Printf( f, "\tlocal %s %s;\r\n", vm.prog->types[def->type&~(DEF_SHARED|DEF_SAVEGLOBAL)].name, PRVM_GetString( def->s_name )); + else + { + if(!PRVM_GetString( def->s_name )) + { + char mem[64]; + com.sprintf( mem, "_l_%i", def->ofs ); + def->s_name = PRVM_SetTempString( mem ); + } + + switch( def->type&~(DEF_SHARED|DEF_SAVEGLOBAL)) + { + case ev_string: + FS_Printf( f, "\tlocal %s %s;\r\n", "string", PRVM_GetString( def->s_name )); + break; + case ev_float: + FS_Printf( f, "\tlocal %s %s;\r\n", "float", PRVM_GetString( def->s_name )); + break; + case ev_entity: + FS_Printf( f, "\tlocal %s %s;\r\n", "entity", PRVM_GetString( def->s_name )); + break; + case ev_vector: + if(!VectorIsNull( v->vector )) + FS_Printf( f, "\tlocal vector %s = '%f %f %f';\r\n", PRVM_GetString( def->s_name ), v->vector[0], v->vector[1], v->vector[2] ); + else FS_Printf( f, "\tlocal %s %s;\r\n", "vector", PRVM_GetString( def->s_name )); + ofs += 2; // skip floats; + break; + default: + FS_Printf( f, "\tlocal %s %s;\r\n", "unknown", PRVM_GetString( def->s_name )); + break; + } + } + } + } + + for( stn = vm.prog->functions[num].first_statement; stn < (signed int)vm.prog->progs->numstatements; stn++ ) + { + if( PR_ProductReadLater( stn )) continue; + st = &((dstatement_t*)vm.prog->statements)[stn]; + if( !st->op ) break; + PR_WriteStatement( stn, vm.prog->functions[num].first_statement ); + } + longjmp( pr_parse_abort, 1 ); + } + FS_Printf( f, "};\r\n" ); +} + + +void PR_FigureOutTypes( void ) +{ + ddef_t *def; + opcode_t *op; + uint i, p; + dstatement_t *st; + int parmofs[MAX_PARMS]; + + ofstype = Qalloc(sizeof(*ofstype ) * 65535); + ofsflags = Qalloc(sizeof(*ofsflags) * 65535); + + maxtypeinfos = 256; + qcc_typeinfo = (void *)Qalloc( sizeof(type_t) * maxtypeinfos ); + numtypeinfos = 0; + + memset( ofstype, 0, sizeof(*ofstype)*65535); + memset( ofsflags, 0, sizeof(*ofsflags)*65535); + + type_void = PR_NewType( "void", ev_void ); + type_string = PR_NewType( "string", ev_string ); + type_float = PR_NewType( "float", ev_float ); + type_vector = PR_NewType( "vector", ev_vector ); + type_entity = PR_NewType( "entity", ev_entity ); + type_field = PR_NewType( "field", ev_field ); + type_function = PR_NewType( "function", ev_function ); + type_pointer = PR_NewType( "pointer", ev_pointer ); + type_integer = PR_NewType( "integer", ev_integer ); + type_floatfield = PR_NewType("fieldfloat", ev_field); + type_floatfield->aux_type = type_float; + type_pointer->aux_type = PR_NewType( "pointeraux", ev_float ); + type_function->aux_type = type_void; + + for( i = 0, st = vm.prog->statements; i < vm.prog->progs->numstatements; i++, st++ ) + { + op = &pr_opcodes[st->op]; + if( st->op >= OP_CALL1 && st->op <= OP_CALL8 ) + { + for( p = 0; p < (uint)st->op - OP_CALL0; p++ ) + ofstype[parmofs[p]] = ofstype[OFS_PARM0 + p * 3]; + } + else if( op->associative == ASSOC_RIGHT ) + { + // assignment + ofsflags[st->b] |= 1; + if( st->b >= OFS_PARM0 && st->b < RESERVED_OFS ) + parmofs[(st->b-OFS_PARM0)/3] = st->a; + + if( op->type_c && op->type_c != &type_void ) + ofstype[st->a] = *op->type_c; + if( op->type_b && op->type_b != &type_void ) + ofstype[st->b] = *op->type_b; + } + else if( op->type_c ) + { + ofsflags[st->c] |= 2; + + if( st->c >= OFS_PARM0 && st->b < RESERVED_OFS ) // too complicated + parmofs[(st->b-OFS_PARM0)/3] = 0; + if( op->type_a && op->type_a != &type_void ) + ofstype[st->a] = *op->type_a; + if( op->type_b && op->type_b != &type_void ) + ofstype[st->b] = *op->type_b; + if( op->type_c && op->type_c != &type_void ) + ofstype[st->c] = *op->type_c; + } + } + for( i = 0; i < vm.prog->progs->numglobaldefs; i++ ) + { + def = &vm.prog->globaldefs[i]; + ofsflags[def->ofs] |= 8; + switch( def->type ) + { + case ev_float: + ofstype[def->ofs] = type_float; + break; + case ev_string: + ofstype[def->ofs] = type_string; + break; + case ev_vector: + ofstype[def->ofs] = type_vector; + break; + default: break; + } + } +} + +bool PR_Decompile( void ) +{ + uint i, fld = 0; + int type; + prvm_eval_t *v; + file_t *f; + + if(!FS_FileExists( sourcefilename )) + return false; + + PRVM_LoadProgs( sourcefilename, 0, NULL, 0, NULL ); + f = FS_Open( "qcdtest/defs.qc", "w" ); + FS_Print( f, "// decompiled code can contain little type info.\r\n" ); + + PR_FigureOutTypes(); + + for( i = 1; i < vm.prog->progs->numglobaldefs; i++ ) + { + if( !com.strcmp(PRVM_GetString( vm.prog->globaldefs[i].s_name ), "IMMEDIATE" )) + continue; + + if( ofsflags[vm.prog->globaldefs[i].ofs] & 4 ) + continue; // this is a local. + + if( vm.prog->types ) + type = vm.prog->types[vm.prog->globaldefs[i].type & ~(DEF_SHARED|DEF_SAVEGLOBAL)].type; + else type = vm.prog->globaldefs[i].type & ~(DEF_SHARED|DEF_SAVEGLOBAL); + v = (prvm_eval_t *)&((int *)vm.prog->globals.gp)[vm.prog->globaldefs[i].ofs]; + + if(!PRVM_GetString( vm.prog->globaldefs[i].s_name )) + { + char mem[64]; + if( ofsflags[vm.prog->globaldefs[i].ofs] & 3 ) + { + ofsflags[vm.prog->globaldefs[i].ofs] &= ~8; + continue; // this is a constant... + } + + com.sprintf( mem, "_g_%i", vm.prog->globaldefs[i].ofs ); + vm.prog->globaldefs[i].s_name = PRVM_SetTempString( mem ); + } + + switch( type ) + { + case ev_void: + FS_Printf( f, "void %s;\r\n", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_string: + if( v->string && *(vm.prog->strings + v->_int )) + FS_Printf( f, "string %s = \"%s\";\r\n", PRVM_GetString(vm.prog->globaldefs[i].s_name ), PRVM_GetString( v->_int )); + else FS_Printf( f, "string %s;\r\n", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_float: + if( v->_float ) FS_Printf( f, "float %s = %f;\r\n", PRVM_GetString( vm.prog->globaldefs[i].s_name ), v->_float); + else FS_Printf( f, "float %s;\r\n", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_vector: + if(!VectorIsNull( v->vector )) + FS_Printf( f, "vector %s = '%f %f %f';\r\n", PRVM_GetString(vm.prog->globaldefs[i].s_name ), v->vector[0], v->vector[1], v->vector[2]); + else FS_Printf( f, "vector %s;\r\n", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + i += 3; // skip the floats + break; + case ev_entity: + FS_Printf( f, "entity %s;\r\n", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_field: + fld++; // wierd + if( !v->_int ) FS_Printf( f, "var " ); + switch( vm.prog->fielddefs[fld].type ) + { + case ev_string: + FS_Printf(f, ".string %s;", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_float: + FS_Printf(f, ".float %s;", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_vector: + FS_Printf(f, ".float %s;", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_entity: + FS_Printf(f, ".float %s;", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_function: + FS_Printf(f, ".void() %s;", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + default: + FS_Printf(f, "field %s;", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + } + if( v->_int ) FS_Printf( f, "/* %i */", v->_int ); + FS_Printf( f, "\r\n" ); + break; + case ev_function: + // wierd + PR_WriteAsmStatements( f, ((int *)vm.prog->globals.gp)[vm.prog->globaldefs[i].ofs], PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_pointer: + FS_Printf( f, "pointer %s;\r\n", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_integer: + FS_Printf( f, "integer %s;\r\n", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_union: + FS_Printf(f, "union %s;\r\n", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + case ev_struct: + FS_Printf(f, "struct %s;\r\n", PRVM_GetString(vm.prog->globaldefs[i].s_name )); + break; + default: break; + } + } + for( i = 0; i < vm.prog->progs->numfunctions; i++ ) + { + PR_WriteAsmStatements( f, i, NULL ); + } + FS_Close( f ); + + return true; +} \ No newline at end of file diff --git a/vprogs/pr_edict.c b/vprogs/pr_edict.c index 574172fd..1cb3154d 100644 --- a/vprogs/pr_edict.c +++ b/vprogs/pr_edict.c @@ -259,15 +259,15 @@ void PRVM_ED_Free (edict_t *ed) PRVM_ED_GlobalAtOfs ============ */ -ddef_t *PRVM_ED_GlobalAtOfs (int ofs) +ddef_t *PRVM_ED_GlobalAtOfs( int ofs ) { ddef_t *def; int i; - for (i=0 ; iprogs->numglobaldefs ; i++) + for( i = 0; i < vm.prog->progs->numglobaldefs; i++ ) { def = &vm.prog->globaldefs[i]; - if (def->ofs == ofs) + if( def->ofs == ofs ) return def; } return NULL; @@ -1244,7 +1244,7 @@ void PRVM_LoadLNO( const char *progname ) PRVM_LoadProgs =============== */ -void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int numedfields, fields_t *ed_field) +void PRVM_LoadProgs( const char *filename, int numedfunc, char **ed_func, int numedfields, fields_t *ed_field ) { dstatement_t *st; ddef_t *infielddefs; @@ -1259,16 +1259,13 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu } if( vm.prog->progs ) Mem_Free( vm.prog->progs ); // release progs file - vm.prog->progs = (dprograms_t *)FS_LoadFile(va("vprogs/%s", filename ), &filesize); + vm.prog->progs = (dprograms_t *)FS_LoadFile(va("%s", filename ), &filesize); if (vm.prog->progs == NULL || filesize < (fs_offset_t)sizeof(dprograms_t)) PRVM_ERROR("PRVM_LoadProgs: couldn't load %s for %s\n", filename, PRVM_NAME); MsgDev(D_INFO, "%s programs occupy %iK.\n", PRVM_NAME, filesize/1024); - vm.prog->filecrc = CRC_Block((byte *)vm.prog->progs, filesize); - - // byte swap the header - SwapBlock((int *)vm.prog->progs, sizeof(*vm.prog->progs)); + SwapBlock((int *)vm.prog->progs, sizeof(*vm.prog->progs)); // byte swap the header switch( vm.prog->progs->version ) { @@ -1276,29 +1273,27 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu vm.prog->intsize = 16; break; case FPROGS_VERSION: - if(vm.prog->progs->ident == VPROGSHEADER16) + if( vm.prog->progs->ident == VPROGSHEADER16 ) vm.prog->intsize = 16; - if(vm.prog->progs->ident == VPROGSHEADER32) + if( vm.prog->progs->ident == VPROGSHEADER32 ) vm.prog->intsize = 32; break; case VPROGS_VERSION: default: - PRVM_ERROR ("%s: %s has wrong version number (%i should be %i)", PRVM_NAME, filename, vm.prog->progs->version, VPROGS_VERSION); + PRVM_ERROR( "%s: %s has wrong version number (%i should be %i)", PRVM_NAME, filename, vm.prog->progs->version, VPROGS_VERSION); break; } - + // try to recognize progs.dat by crc - switch(vm.prog->progs->crc) + if( PRVM_GetProgNr() == PRVM_DECOMPILED ) { - case PROG_CRC_SERVER: - case PROG_CRC_CLIENT: - case PROG_CRC_UIMENU: - break; - default: - PRVM_ERROR("%s: %s system vars have been modified, progdefs.h is out of date", PRVM_NAME, filename); - break; + MsgDev(D_INFO, "Prepare %s [CRC %d]\n", filename, vm.prog->progs->crc ); } - MsgDev(D_INFO, "Loading %s [CRC %d]\n", filename, vm.prog->progs->crc ); + else if( vm.prog->progs->crc != vm.prog->filecrc ) + { + PRVM_ERROR("%s: %s system vars have been modified, progdefs.h is out of date %d\n", PRVM_NAME, filename ); + } + else MsgDev(D_INFO, "Loading %s [CRC %d]\n", filename, vm.prog->progs->crc ); // set initial pointers vm.prog->statements = (dstatement_t *)((byte *)vm.prog->progs + vm.prog->progs->ofs_statements); @@ -1308,12 +1303,19 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu vm.prog->strings = (char *)vm.prog->progs + vm.prog->progs->ofs_strings; vm.prog->globals.gp = (float *)((byte *)vm.prog->progs + vm.prog->progs->ofs_globals); - // debug info - if(vm.prog->progs->ofslinenums) vm.prog->linenums = (int *)((byte *)vm.prog->progs + vm.prog->progs->ofslinenums); - if(vm.prog->progs->ofs_types) vm.prog->types = (type_t *)((byte *)vm.prog->progs + vm.prog->progs->ofs_types); + if( vm.prog->progs->version >= FPROGS_VERSION ) + { + // debug info + if( vm.prog->progs->ofsfiles ) + vm.prog->sources = (includeddatafile_t*)((byte *)vm.prog->progs + vm.prog->progs->ofsfiles); + if( vm.prog->progs->ofslinenums ) + vm.prog->linenums = (int *)((byte *)vm.prog->progs + vm.prog->progs->ofslinenums); + if( vm.prog->progs->ofs_types ) + vm.prog->types = (type_t *)((byte *)vm.prog->progs + vm.prog->progs->ofs_types); + } // decompress progs if needed - if (vm.prog->progs->blockscompressed & COMP_STATEMENTS) + if( vm.prog->progs->blockscompressed & COMP_STATEMENTS ) { switch(vm.prog->intsize) { @@ -1334,7 +1336,7 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu filesize += len - complen - sizeof(int); //merge filesize } - if (vm.prog->progs->blockscompressed & COMP_DEFS) + if( vm.prog->progs->blockscompressed & COMP_DEFS ) { switch(vm.prog->intsize) { @@ -1355,7 +1357,7 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu filesize += len - complen - sizeof(int); //merge filesize } - if (vm.prog->progs->blockscompressed & COMP_FIELDS) + if( vm.prog->progs->blockscompressed & COMP_FIELDS ) { switch(vm.prog->intsize) { @@ -1376,7 +1378,7 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu filesize += len - complen - sizeof(int); //merge filesize } - if (vm.prog->progs->blockscompressed & COMP_FUNCTIONS) + if( vm.prog->progs->blockscompressed & COMP_FUNCTIONS ) { len = sizeof(dfunction_t) * vm.prog->progs->numfunctions; complen = LittleLong(*(int*)dfunctions); @@ -1388,7 +1390,7 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu filesize += len - complen - sizeof(int); //merge filesize } - if (vm.prog->progs->blockscompressed & COMP_STRINGS) + if( vm.prog->progs->blockscompressed & COMP_STRINGS ) { len = sizeof(char) * vm.prog->progs->numstrings; complen = LittleLong(*(int*)vm.prog->strings); @@ -1402,7 +1404,7 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu filesize += len - complen - sizeof(int); //merge filesize } - if (vm.prog->progs->blockscompressed & COMP_GLOBALS) + if( vm.prog->progs->blockscompressed & COMP_GLOBALS ) { len = sizeof(float) * vm.prog->progs->numglobals; complen = LittleLong(*(int*)vm.prog->globals.gp); @@ -1414,7 +1416,19 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu filesize += len - complen - sizeof(int); //merge filesize } - if (vm.prog->linenums && vm.prog->progs->blockscompressed & COMP_LINENUMS) + if( vm.prog->sources ) // source always are packed + { + int i, numsources = LittleLong(*(int*)vm.prog->sources); + includeddatafile_t *src = (includeddatafile_t *)(((int *)vm.prog->sources)+1); + + for( i = 0; i < numsources; i++, src++ ) + { + Msg("Source: %s\n", src->filename ); + Msg("Ofs, size: %d, %d\n", src->ofs, src->size ); + } + } + + if( vm.prog->linenums && vm.prog->progs->blockscompressed & COMP_LINENUMS ) { len = sizeof(int) * vm.prog->progs->numstatements; complen = LittleLong(*(int*)vm.prog->linenums); @@ -1426,7 +1440,7 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu filesize += len - complen - sizeof(int); //merge filesize } - if (vm.prog->types && vm.prog->progs->blockscompressed & COMP_TYPES) + if( vm.prog->types && vm.prog->progs->blockscompressed & COMP_TYPES ) { len = sizeof(type_t) * vm.prog->progs->numtypes; complen = LittleLong(*(int*)vm.prog->types); @@ -1440,9 +1454,9 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu vm.prog->stringssize = 0; - for (i = 0; vm.prog->stringssize < vm.prog->progs->numstrings; i++) + for( i = 0; vm.prog->stringssize < vm.prog->progs->numstrings; i++ ) { - if (vm.prog->progs->ofs_strings + vm.prog->stringssize >= (int)filesize) + if( vm.prog->progs->ofs_strings + vm.prog->stringssize >= (int)filesize ) PRVM_ERROR ("%s: %s strings go past end of file", PRVM_NAME, filename); vm.prog->stringssize += (int)com.strlen(vm.prog->strings + vm.prog->stringssize) + 1; } @@ -1495,16 +1509,16 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu } // append the ed fields - for (i = 0; i < (int)numedfields; i++) + for( i = 0; i < (int)numedfields; i++ ) { vm.prog->fielddefs[vm.prog->progs->numfielddefs].type = ed_field[i].type; vm.prog->fielddefs[vm.prog->progs->numfielddefs].ofs = ed_field[i].ofs; - vm.prog->fielddefs[vm.prog->progs->numfielddefs].s_name = PRVM_SetEngineString(ed_field[i].name); + vm.prog->fielddefs[vm.prog->progs->numfielddefs].s_name = PRVM_SetEngineString( ed_field[i].name ); } // check ed functions - for(i=0 ; i < numedfunc ; i++) - if(PRVM_ED_FindFunction(ed_func[i]) == 0) + for( i = 0; i < numedfunc; i++ ) + if( PRVM_ED_FindFunction( ed_func[i] ) == 0 ) PRVM_ERROR("%s: %s not found in %s",PRVM_NAME, ed_func[i], filename); for (i=0 ; iprogs->numglobals ; i++) @@ -1669,7 +1683,7 @@ void PRVM_LoadProgs (const char *filename, int numedfunc, char **ed_func, int nu // set flags & ddef_ts in prog vm.prog->flag = 0; - vm.prog->pev = PRVM_ED_FindGlobal("pev"); // critical stuff + vm.prog->pev = PRVM_ED_FindGlobal( "pev" ); // critical stuff if( PRVM_ED_FindGlobal("time") && PRVM_ED_FindGlobal("time")->type & ev_float ) vm.prog->time = &PRVM_G_FLOAT(PRVM_ED_FindGlobal("time")->ofs); diff --git a/vprogs/pr_local.h b/vprogs/pr_local.h index 4adef359..a27bcbb4 100644 --- a/vprogs/pr_local.h +++ b/vprogs/pr_local.h @@ -563,6 +563,13 @@ extern int numtypeinfos; extern int maxtypeinfos; extern int numtemps; +// +// pr_main.c +// +void PR_InitCompile( const char *name ); +void PR_InitDecompile( const char *name ); +bool PRVM_DecompileProgs( void ); + // // pr_utils.c // @@ -660,4 +667,9 @@ void PR_BeginCompilation ( void ); bool PR_ContinueCompile ( void ); void PR_FinishCompilation ( void ); +// +// pr_decomp.c +// +bool PR_Decompile( void ); + #endif//PR_LOCAL_H \ No newline at end of file diff --git a/vprogs/pr_main.c b/vprogs/pr_main.c index c22bc775..4d2a4f27 100644 --- a/vprogs/pr_main.c +++ b/vprogs/pr_main.c @@ -35,18 +35,19 @@ int *statement_linenums; char sourcedir[MAX_SYSPATH]; cachedsourcefile_t *sourcefile; dfunction_t *functions; -int numfunctions; -ddef_t *qcc_globals; -int numglobaldefs; -ddef_t *fields; -int numfielddefs; -bool pr_warning[WARN_MAX]; -int target_version; -bool bodylessfuncs; -type_t *qcc_typeinfo; -int numtypeinfos; -int maxtypeinfos; -int prvm_developer; +int numfunctions; +ddef_t *qcc_globals; +int numglobaldefs; +ddef_t *fields; +int numfielddefs; +bool pr_warning[WARN_MAX]; +int target_version; +bool bodylessfuncs; +type_t *qcc_typeinfo; +int numtypeinfos; +int maxtypeinfos; +int prvm_developer; +int host_instance; vprogs_exp_t vm; hashtable_t compconstantstable; @@ -61,7 +62,7 @@ cvar_t *prvm_traceqc; cvar_t *prvm_boundscheck; cvar_t *prvm_statementprofiling; -void PR_SetDefaultProperties (void) +void PR_SetDefaultProperties( void ) { const_t *cnst; int i, j; @@ -158,7 +159,7 @@ PR_Init initialize compiler and hash tables =================== */ -void PR_Init( const char *name ) +void PR_InitCompile( const char *name ) { static char parmname[12][MAX_PARMS]; static temp_t ret_temp; @@ -245,6 +246,28 @@ void PR_Init( const char *name ) } } +void PR_InitDecompile( const char *name ) +{ + string progsname; + + com.strncpy( sourcefilename, name, sizeof(sourcefilename)); + FS_FileBase( name, progsname ); + + PRVM_InitProg( PRVM_DECOMPILED ); + + vm.prog->reserved_edicts = 1; + vm.prog->loadintoworld = true; + vm.prog->name = copystring( progsname ); + vm.prog->builtins = NULL; + vm.prog->numbuiltins = 0; + vm.prog->max_edicts = 4096; + vm.prog->limit_edicts = 4096; + vm.prog->edictprivate_size = sizeof(vm_edict_t); + vm.prog->error_cmd = VM_Error; + vm.prog->flag |= PRVM_OP_STATE; // enable op_state feature + vm.prog->progs_mempool = qccpool; +} + void PRVM_Init( uint funcname, int argc, char **argv ) { char dev_level[4]; @@ -253,6 +276,7 @@ void PRVM_Init( uint funcname, int argc, char **argv ) com_argv = argv; qccpool = Mem_AllocPool( "VM progs" ); + host_instance = funcname; if(FS_GetParmFromCmdLine("-dev", dev_level )) prvm_developer = com.atoi(dev_level); @@ -274,7 +298,7 @@ void PRVM_Init( uint funcname, int argc, char **argv ) prvm_statementprofiling = Cvar_Get ("prvm_statementprofiling", "0", 0, "counts how many times each QC statement has been executed" ); prvm_maxedicts = Cvar_Get( "prvm_maxedicts", "4096", CVAR_SYSTEMINFO, "user limit edicts number fof server, client and renderer, absolute limit 65535" ); - if( funcname == HOST_NORMAL || funcname == HOST_DEDICATED ) + if( host_instance == HOST_NORMAL || host_instance == HOST_DEDICATED ) { // dump internal copies of progs into hdd if missing if(!FS_FileExists("vprogs/server.dat")) FS_WriteFile( "vprogs/server.dat", server_dat, sizeof(server_dat)); @@ -290,8 +314,24 @@ void PRVM_Shutdown( void ) void PRVM_PrepareProgs( const char *dir, const char *name ) { - FS_InitRootDir((char *)dir); - PR_Init( name ); + switch( host_instance ) + { + case COMP_QCCLIB: + FS_InitRootDir((char *)dir); + PR_InitCompile( name ); + break; + case RIPP_QCCDEC: + FS_InitRootDir((char *)dir); + PR_InitDecompile( name ); + break; + case HOST_NORMAL: + case HOST_DEDICATED: + PR_InitCompile( name ); + break; + default: + Sys_Break("PRVM_PrepareProgs: can't prepare progs for instance %d\n", host_instance ); + break; + } } void PRVM_CompileProgs( void ) @@ -301,6 +341,11 @@ void PRVM_CompileProgs( void ) PR_FinishCompilation(); } +bool PRVM_DecompileProgs( void ) +{ + return PR_Decompile(); +} + vprogs_exp_t DLLEXPORT *CreateAPI( stdlib_api_t *input, void *unused ) { com = *input; @@ -312,6 +357,7 @@ vprogs_exp_t DLLEXPORT *CreateAPI( stdlib_api_t *input, void *unused ) vm.Free = PRVM_Shutdown; vm.PrepareDAT = PRVM_PrepareProgs; vm.CompileDAT = PRVM_CompileProgs; + vm.DecompileDAT = PRVM_DecompileProgs; vm.WriteGlobals = PRVM_ED_WriteGlobals; vm.ParseGlobals = PRVM_ED_ParseGlobals; diff --git a/vprogs/pr_utils.c b/vprogs/pr_utils.c index 9f20a4ee..df6776d3 100644 --- a/vprogs/pr_utils.c +++ b/vprogs/pr_utils.c @@ -294,11 +294,11 @@ int PR_WriteSourceFiles(file_t *h, dprograms_t *progs, bool sourceaswell) if (!num) return 0; idf = Qalloc(sizeof(includeddatafile_t) * num); - for (f = sourcefile, num = 0; f; f = f->next) + for( f = sourcefile, num = 0; f; f = f->next ) { - if (f->type == FT_CODE && !sourceaswell) + if( f->type == FT_CODE && !sourceaswell ) continue; - com.strcpy(idf[num].filename, f->filename); + com.strcpy( idf[num].filename, f->filename ); idf[num].size = f->size; idf[num].compmethod = CMPW_DEFLATE; idf[num].ofs = FS_Tell(h); @@ -306,8 +306,8 @@ int PR_WriteSourceFiles(file_t *h, dprograms_t *progs, bool sourceaswell) num++; } ofs = FS_Tell(h); - FS_Write(h, &num, sizeof(int)); - FS_Write(h, idf, sizeof(includeddatafile_t)*num); + FS_Write( h, &num, sizeof(int)); + FS_Write( h, idf, sizeof(includeddatafile_t) * num ); sourcefile = NULL; return ofs; @@ -538,15 +538,15 @@ word PR_WriteProgdefs (char *filename) PR_Message("Quake1 unmodified progs.dat\n"); if(!com.strcmp(progsoutname, "unknown.dat")) com.strcpy(progsoutname, "progs.dat"); break; - case PROG_CRC_SERVER: + case 1320: PR_Message("Xash3D unmodified server.dat\n"); if(!com.strcmp(progsoutname, "unknown.dat")) com.strcpy(progsoutname, "server.dat"); break; - case PROG_CRC_CLIENT: + case 9488: PR_Message("Xash3D unmodified client.dat\n"); if(!com.strcmp(progsoutname, "unknown.dat")) com.strcpy(progsoutname, "client.dat"); break; - case PROG_CRC_UIMENU: + case 2460: PR_Message("Xash3D unmodified uimenu.dat\n"); if(!com.strcmp(progsoutname, "unknown.dat")) com.strcpy(progsoutname, "uimenu.dat"); break; diff --git a/vprogs/vprogs.dsp b/vprogs/vprogs.dsp index 24623cfb..fa68b5d3 100644 --- a/vprogs/vprogs.dsp +++ b/vprogs/vprogs.dsp @@ -117,6 +117,10 @@ SOURCE=.\pr_comp.c # End Source File # Begin Source File +SOURCE=.\pr_decomp.c +# End Source File +# Begin Source File + SOURCE=.\pr_edict.c # End Source File # Begin Source File diff --git a/vprogs/vprogs.h b/vprogs/vprogs.h index fad224ad..6ba041db 100644 --- a/vprogs/vprogs.h +++ b/vprogs/vprogs.h @@ -23,10 +23,6 @@ extern int prvm_developer; #define Host_Error com.error -#define PROG_CRC_SERVER 1320 -#define PROG_CRC_CLIENT 9488 -#define PROG_CRC_UIMENU 2460 - enum op_state { OP_DONE, // 0 @@ -357,7 +353,7 @@ void PRVM_MEM_IncreaseEdicts(void); edict_t *PRVM_ED_Alloc (void); void PRVM_ED_Free (edict_t *ed); void PRVM_ED_ClearEdict (edict_t *e); - +ddef_t *PRVM_ED_GlobalAtOfs( int ofs ); void PRVM_PrintFunctionStatements (const char *name); void PRVM_ED_Print(edict_t *ed); void PRVM_ED_Write (vfile_t *f, edict_t *ed);