diff --git a/harbour/ChangeLog b/harbour/ChangeLog index 953be76564..0de3931a8f 100644 --- a/harbour/ChangeLog +++ b/harbour/ChangeLog @@ -8,6 +8,12 @@ 2008-12-31 13:59 UTC+0100 Foo Bar (foo.bar foobar.org) */ +2008-10-08 20:33 UTC+0200 Viktor Szakats (harbour.01 syenar hu) + * contrib/examples/hscript/hscript.prg + * source/compiler/gencobj.c + * source/compiler/genobj32.c + * Formatting, minor cleanups. + 2008-10-08 15:19 UTC+0200 Viktor Szakats (harbour.01 syenar hu) * make_gnu.bat ! HARBOURDIR -> HB_INSTALL_PREFIX diff --git a/harbour/contrib/examples/hscript/hscript.prg b/harbour/contrib/examples/hscript/hscript.prg index d2e410534a..d2c1691d35 100644 --- a/harbour/contrib/examples/hscript/hscript.prg +++ b/harbour/contrib/examples/hscript/hscript.prg @@ -6,7 +6,6 @@ * hscript.prg * HarbourScript translation engine * - * * Copyright (C) 1999 Felipe Coury * www - http://www.harbour-project.org * @@ -49,10 +48,6 @@ * whether to permit this exception to apply to your modifications. * If you do not wish that, delete this exception notice. * - * 1999/06/13 First implementation. - * 1999/06/24 Enhanced tag matching routines. - * 1999/07/26 Corrections to CGI output, QOut() -> OutStd(). - * */ #include "hbextern.ch" @@ -60,18 +55,18 @@ #define IF_BUFFER 65535 -FUNCTION Main( cScript ) +PROCEDURE Main( cScript ) LOCAL aHRSHandle := {} // Handle for script lines LOCAL aResult := {} // Handle for transl'd lines LOCAL cLocation // Location of scripts - LOCAL cHarbourDir := GetEnv( "HARBOURDIR" ) // Harbour.exe dir with '\' - LOCAL cHost := StrTran( alltrim( ; // Random (not et al) + LOCAL cHarbourDir := GetEnv( "HARBOURDIR" ) // harbour executable dir with '\' + LOCAL cHost := StrTran( AllTrim( ; // Random (not et al) Str( Seconds() ) ), '.' ) // file name LOCAL cScriptName, cFile, cLine, cTrans, c LOCAL hFile, i, lOpen, nLen - WHILE .T. + DO WHILE .T. IF Empty( GetEnv( "SERVER_NAME" ) ) cScriptName := cScript @@ -113,7 +108,7 @@ FUNCTION Main( cScript ) lOpen := .f. ft_FUse( cScriptName ) - WHILE !ft_FEof() + DO WHILE !ft_FEof() cLine := AllTrim( ft_FReadLn() ) cTrans := "" @@ -127,7 +122,7 @@ FUNCTION Main( cScript ) c := SubStr( cLine, i, 1 ) - IF c == "%" .AND. substr( cLine, i + 1, 1 ) == ">" + IF c == "%" .AND. SubStr( cLine, i + 1, 1 ) == ">" IF lOpen // Error - Already in htm mode ELSE @@ -144,7 +139,7 @@ FUNCTION Main( cScript ) ENDIF i++ - ELSEIF c == "<" .AND. substr( cLine, i + 1, 1 ) == "%" + ELSEIF c == "<" .AND. SubStr( cLine, i + 1, 1 ) == "%" IF !lOpen // Error - Not in htm mode ELSE @@ -164,8 +159,8 @@ FUNCTION Main( cScript ) ENDIF NEXT - IF lOpen .AND. !( substr( cLine, nLen - 1, 2 ) == "%>" ) - cTrans += "' + chr(10) )" + IF lOpen .AND. !( SubStr( cLine, nLen - 1, 2 ) == "%>" ) + cTrans += "' + Chr(10) )" ENDIF AAdd( aResult, cTrans ) @@ -182,8 +177,8 @@ FUNCTION Main( cScript ) NEXT FClose( hFile ) - // Creates the temporary HRB, erases the PRG - hb_Run( cHarbourDir + "harbour.exe " + cFile + " /q /n /gh /o" + Left( cHarbourDir, Len( cHarbourDir ) - 1 ) + iif( !Empty( Left( cHarbourDir, Len( cHarbourDir ) - 1 ) ), "\", "" ) ) + // Creates the temporary .hrb, erases the .prg + hb_Run( cHarbourDir + "harbour " + cFile + " -q -n -gh -o" + Left( cHarbourDir, Len( cHarbourDir ) - 1 ) + iif( !Empty( Left( cHarbourDir, Len( cHarbourDir ) - 1 ) ), "\", "" ) ) FErase( cFile ) // Runs using Tugboat @@ -197,28 +192,28 @@ FUNCTION Main( cScript ) ENDDO - RETURN NIL + RETURN FUNCTION ParseString( cString, cDelim, nRet ) LOCAL cBuf, aElem, nPosFim, nSize, i - nSize := len( cString ) - len( StrTran( cString, cDelim, '' ) ) + 1 - aElem := array( nSize ) + nSize := Len( cString ) - Len( StrTran( cString, cDelim, '' ) ) + 1 + aElem := Array( nSize ) cBuf := cString - i := 1 + FOR i := 1 TO nSize - nPosFim := at( cDelim, cBuf ) + nPosFim := At( cDelim, cBuf ) IF nPosFim > 0 - aElem[i] := substr( cBuf, 1, nPosFim - 1 ) + aElem[i] := SubStr( cBuf, 1, nPosFim - 1 ) ELSE aElem[i] := cBuf ENDIF - cBuf := substr( cBuf, nPosFim + 1, len( cBuf ) ) + cBuf := SubStr( cBuf, nPosFim + 1, Len( cBuf ) ) - NEXT i + NEXT - RETURN( aElem[ nRet ] ) + RETURN aElem[ nRet ] diff --git a/harbour/source/compiler/gencobj.c b/harbour/source/compiler/gencobj.c index e99f4bc7a3..8335ba0b50 100644 --- a/harbour/source/compiler/gencobj.c +++ b/harbour/source/compiler/gencobj.c @@ -228,8 +228,9 @@ void hb_compGenCObj( HB_COMP_DECL, PHB_FNAME pFileName ) } fclose( filecfg ); - - } else { + } + else + { snprintf( buffer, sizeof( buffer ), "\nError: Can't find %s file in %s.\n" "%s should be a text file that contains:\n" diff --git a/harbour/source/compiler/genobj32.c b/harbour/source/compiler/genobj32.c index 06c1807931..2c07552bc0 100644 --- a/harbour/source/compiler/genobj32.c +++ b/harbour/source/compiler/genobj32.c @@ -28,39 +28,589 @@ #include "hbcomp.h" -static ULONG GetSymbolsSize( HB_COMP_DECL ); -static PCOMSYMBOL GetFirstSymbol( HB_COMP_DECL ); -static char * GetSymbolName( HB_COMP_DECL, ULONG ulPos ); -static ULONG GetPCodesSize( HB_COMP_DECL ); -static ULONG GetSymbolsAmount( HB_COMP_DECL ); -static BOOL IsExternal( HB_COMP_DECL, ULONG ulSymbol ); -static USHORT GetExternalPos( char * szExternal ); -static void GenerateLocalNames( FILE * hObjFile ); -static void GenerateSymbolsSegment( HB_COMP_DECL, FILE * hObjFile ); -static void GenerateDataSegment( HB_COMP_DECL, FILE * hObjFile ); -static void GenerateCodeSegment( HB_COMP_DECL, FILE * hObjFile ); -static void GenerateExternals( HB_COMP_DECL, FILE * hObjFile ); -static void putbyte( BYTE b, FILE * hObjFile, BYTE * pbChecksum ); -static void putword( USHORT w, FILE * hObjFile, BYTE * pbChecksum ); -static void CompiledFileName( FILE * hObjFile, char * szFileName ); -static void CompilerVersion( FILE * hObjFile, char * szVersion ); -static void LocalNames( FILE * hObjFile, char * szNames[] ); -static void ExternalNames( FILE * hObjFile, char * szNames[] ); -static void CodeSegment( HB_COMP_DECL, FILE * hObjFile, BYTE * prgCode, ULONG ulPrgLen, USHORT wFunctions ); -static void DataSegment( HB_COMP_DECL, FILE * hObjFile, BYTE * symbol, ULONG wSymLen, ULONG wSymbols, ULONG ulTotalSize ); -static void DefineSegment( FILE * hObjFile, BYTE bName, BYTE bClass, USHORT wLen ); -static void PubDef( FILE * hObjFile, char * szName, USHORT wSegment, USHORT wOffset ); -static void Fixup( FILE * hObjFile, BYTE bType, USHORT wOffset, BYTE bFlags, BYTE bSymbol ); -static void EnumeratedData( FILE * hObjFile, BYTE bSegment, BYTE * pData, USHORT wLen, USHORT wOffset ); -static void End( FILE * hObjFile ); -static void GroupDef( FILE * hObjFile, BYTE bName, BYTE * aSegs ); +static BYTE s_prgFunction[] = { 0x68, 0x00, 0x00, 0x00, 0x00, 0x68, 0x00, 0x00, 0x00, + 0x00, 0xE8, 0x00, 0x00, 0x00, 0x00, 0x83, 0xC4, 0x08, 0xC3 }; -static BYTE prgFunction[] = { 0x68, 0x00, 0x00, 0x00, 0x00, 0x68, 0x00, 0x00, 0x00, - 0x00, 0xE8, 0x00, 0x00, 0x00, 0x00, 0x83, 0xC4, 0x08, 0xC3 }; +static char * * s_externNames = NULL; +static USHORT s_wExternals = 1; /* _hb_vmExecute is always added */ +static const char * s_szPrefix = "_HB_FUN_"; -static char * * externNames = NULL; -static USHORT wExternals = 1; /* _hb_vmExecute is always added */ -static const char * szPrefix = "_HB_FUN_"; +static USHORT hb_compFunctionGetPos( HB_COMP_DECL, char * szFunctionName ) /* return 0 if not found or order + 1 */ +{ + PFUNCTION pFunc = HB_COMP_PARAM->functions.pFirst; + USHORT wFunction = HB_COMP_PARAM->fStartProc ? 1 : 0; + + while( pFunc ) + { + if( ! strcmp( pFunc->szName, szFunctionName ) && pFunc != HB_COMP_PARAM->functions.pFirst ) + return wFunction; + wFunction++; + pFunc = pFunc->pNext; + } + return 0; +} + +static ULONG GetSymbolsSize( HB_COMP_DECL ) +{ + return HB_COMP_PARAM->symbols.iCount * sizeof( HB_SYMB ); +} + +static PCOMSYMBOL GetFirstSymbol( HB_COMP_DECL ) +{ + PCOMSYMBOL pSymbol = HB_COMP_PARAM->symbols.pFirst; + return pSymbol; +} + +static char * GetSymbolName( HB_COMP_DECL, ULONG ulPos ) +{ + PCOMSYMBOL pSymbol = GetFirstSymbol( HB_COMP_PARAM ); + ULONG ul = 0; + + while( pSymbol && ( ul++ < ulPos ) ) + pSymbol = pSymbol->pNext; + + return pSymbol->szName; +} + +static ULONG GetPCodesSize( HB_COMP_DECL ) +{ + ULONG ulTotal = 0; + PFUNCTION pFunction = HB_COMP_PARAM->functions.pFirst; + + if( ! HB_COMP_PARAM->fStartProc ) + pFunction = pFunction->pNext; + + while( pFunction ) + { + ulTotal += pFunction->lPCodePos; + pFunction = pFunction->pNext; + } + return ulTotal; +} + +static ULONG GetSymbolsAmount( HB_COMP_DECL ) +{ + PCOMSYMBOL pSymbol = GetFirstSymbol( HB_COMP_PARAM ); + ULONG ulAmount = 1; + + while( pSymbol->pNext ) + { + ulAmount++; + pSymbol = pSymbol->pNext; + } + return ulAmount; +} + +static BOOL IsExternal( HB_COMP_DECL, ULONG ulSymbol ) +{ + PCOMSYMBOL pSymbol = GetFirstSymbol( HB_COMP_PARAM ); + ULONG ul = 0; + + while( ul++ < ulSymbol ) + pSymbol = pSymbol->pNext; + + return ! hb_compFunctionFind( HB_COMP_PARAM, pSymbol->szName ); +} + +static USHORT GetExternalPos( char * szExternal ) +{ + USHORT w = 0; + + while( w < s_wExternals ) + { + if( ! strcmp( szExternal, s_externNames[ w ] ) ) + break; + w++; + } + + return w; +} + +static void GenerateLocalNames( FILE * hObjFile ) +{ + char * localNames[] = { "_TEXT", "CODE", + "_NULL", "_DATA", "DATA", + "_BSS", "BSS", "DGROUP", + "HB_STARTSYMBOLS", "HB_SYMBOLS", "HB_ENDSYMBOLS", "HARBOUR", + "HB_STARTBORSYMBOLS", "_INIT_", "HB_ENDBORSYMBOLS", "INITDATA", "BORLAND", + 0 }; + + LocalNames( hObjFile, localNames ); +} + +static void GenerateSymbolsSegment( HB_COMP_DECL, FILE * hObjFile ) +{ + BYTE symbolsData[] = { 0, 0, 0, 0, 0, 0, 0, 0 }; + BYTE groupDGroup[] = { 2, 3, 4, 0 }; /* segments defined order for DGROUP */ + BYTE groupSymGroup[] = { 5, 6, 7, 0 }; /* segments defined order for SYMGROUP */ + BYTE groupInitData[] = { 8, 9, 10, 0 }; /* segments defined order for INITDATA */ + + DefineSegment( hObjFile, 10, /* HB_STARTSYMBOLS position + 1 into localnames */ + 6, /* "DATA" position + 1 into localNames */ + 0 ); /* segment length */ + DefineSegment( hObjFile, 11, /* HB_SYMBOLS position + 1 into localNames */ + 6, /* "DATA" position + 1 into localNames */ + 8 ); /* segment length */ + DefineSegment( hObjFile, 12, /* HB_ENDSYMBOLS position + 1 into localNames */ + 6, /* "DATA" position + 1 into localNames */ + 0 ); /* segment length */ + + DefineSegment( hObjFile, 14, /* HB_STARTBORSYMBOLS position + 1 into localnames */ + 17, /* INITDATA position + 1 into localNames */ + 0 ); /* segment length */ + DefineSegment( hObjFile, 15, /* HB_STARTSYMBOLS position + 1 into localnames */ + 17, /* INITDATA position + 1 into localNames */ + 0 ); /* segment length */ + DefineSegment( hObjFile, 16, /* HB_ENDBORSYMBOLS position + 1 into localnames */ + 17, /* INITDATA position + 1 into localNames */ + 0 ); /* segment length */ + + GroupDef( hObjFile, 8, groupDGroup ); /* "DGROUP" localNames position - 1 */ + GroupDef( hObjFile, 12, groupSymGroup ); /* "SYMGROUP" localNames position - 1 */ + GroupDef( hObjFile, 17, groupInitData ); /* "BORLAND" localNames position - 1 */ + + * ( USHORT * ) symbolsData = (USHORT) GetSymbolsAmount( HB_COMP_PARAM ); + + EnumeratedData( hObjFile, 6, symbolsData, sizeof( symbolsData ), 0 ); /* HB_SYMBOLS defined order segment */ + + Fixup( hObjFile, 0xE4, 4, /* offset into HB_SYMBOLS segment */ + 0x54, 4 ); /* DATA segment defined order */ +} + +static void GenerateDataSegment( HB_COMP_DECL, FILE * hObjFile ) +{ + HB_SYMB symbol; + ULONG ulSize = GetSymbolsSize( HB_COMP_PARAM ); + PCOMSYMBOL pSymbol = GetFirstSymbol( HB_COMP_PARAM ); + ULONG ulSymbols = GetSymbolsAmount( HB_COMP_PARAM ), ul; + + while( pSymbol ) + { + ulSize += strlen( pSymbol->szName ) + 1; + pSymbol = pSymbol->pNext; + } + + ulSize += GetPCodesSize( HB_COMP_PARAM ); + + DefineSegment( hObjFile, 4, /* _NULL position + 1 into localnames */ + 6, /* "DATA" position + 1 into localNames */ + 0 ); /* segment length */ + DefineSegment( hObjFile, 7, /* _BSS position + 1 into localNames */ + 8, /* "BSS" position + 1 into localNames */ + 0 ); /* segment length */ + DefineSegment( hObjFile, 5, /* "_DATA" position + 1 into localNames */ + 6, /* "DATA" position + 1 into localNames */ + (USHORT) ulSize ); /* segment length */ + + memset( &symbol, 0, sizeof( symbol ) ); + DataSegment( HB_COMP_PARAM, hObjFile, (BYTE *) &symbol, + sizeof( symbol ), GetSymbolsAmount( HB_COMP_PARAM ), ulSize ); + + pSymbol = GetFirstSymbol( HB_COMP_PARAM ); + for( ul = 0; ul < ulSymbols; ul++ ) + { + Fixup( hObjFile, 0xE4, (USHORT) ( ul * sizeof( HB_SYMB ) ), 0x54, 4 ); /* 4 = Data symbol name location */ + + if( IsExternal( HB_COMP_PARAM, ul ) ) + { + if( ! ( pSymbol->cScope & HB_FS_MESSAGE ) ) + Fixup( hObjFile, 0xE4, (USHORT) ( ul * sizeof( HB_SYMB ) ) + 8, 0x56, + GetExternalPos( GetSymbolName( HB_COMP_PARAM, ul ) ) + 1 ); + } + else + { + /* if( ! ( pSymbol->cScope & HB_FS_MESSAGE ) ) */ + Fixup( hObjFile, 0xE4, (USHORT) ( ul * sizeof( HB_SYMB ) ) + 8, 0x54, 1 ); /* function address location */ + } + pSymbol = pSymbol->pNext; + } +} + +static void GenerateCodeSegment( HB_COMP_DECL, FILE * hObjFile ) +{ + USHORT wFunctions = HB_COMP_PARAM->functions.iCount - ( HB_COMP_PARAM->fStartProc ? 0: 1 ); + ULONG ulSize = wFunctions * sizeof( s_prgFunction ); + PFUNCTION pFunc = ( HB_COMP_PARAM->fStartProc ? HB_COMP_PARAM->functions.pFirst: HB_COMP_PARAM->functions.pFirst->pNext ); + USHORT w = 0; + + DefineSegment( hObjFile, 2, /* "_TEXT" position + 1 into localNames */ + 3, /* "CODE" position + 1 into localNames */ + (USHORT) ulSize ); /* segment length */ + + while( pFunc ) + { + if( !( pFunc->cScope & ( HB_FS_STATIC | HB_FS_INIT | HB_FS_EXIT ) ) ) + PubDef( hObjFile, pFunc->szName, 1, w * sizeof( s_prgFunction ) ); + w++; + pFunc = pFunc->pNext; + } + + CodeSegment( HB_COMP_PARAM, hObjFile, s_prgFunction, sizeof( s_prgFunction ), wFunctions ); + + for( w = 0; w < wFunctions; w++ ) + { + /* s_prgFunction fixups */ + Fixup( hObjFile, 0xE4, ( w * sizeof( s_prgFunction ) ) + 1, + 0x54, 4 ); /* 4 = DATA segment defined order */ + + Fixup( hObjFile, 0xE4, ( w * sizeof( s_prgFunction ) ) + 6, + 0x54, 4 ); /* DATA segment define order - pcode location */ + + Fixup( hObjFile, 0xA4, ( w * sizeof( s_prgFunction ) ) + 11, + 0x56, 1 ); /* External: _hb_vmExecute */ + } +} + +static void GenerateExternals( HB_COMP_DECL, FILE * hObjFile ) +{ + USHORT w; + PFUNCALL pFunc; + PFUNCTION pFTemp; + + /* calculate amount of externals */ + pFunc = HB_COMP_PARAM->funcalls.pFirst; + while( pFunc ) + { + if( ( pFTemp = hb_compFunctionFind( HB_COMP_PARAM, pFunc->szName ) ) == NULL || pFTemp == HB_COMP_PARAM->functions.pFirst ) + s_wExternals++; + pFunc = pFunc->pNext; + } + + if( s_wExternals ) + { + s_externNames = ( char * * ) hb_xgrab( sizeof( char * ) * ( s_wExternals + 2 ) ); + w = 1; + s_externNames[ 0 ] = "_hb_vmExecute"; + + pFunc = HB_COMP_PARAM->funcalls.pFirst; + while( pFunc ) + { + if( ( pFTemp = hb_compFunctionFind( HB_COMP_PARAM, pFunc->szName ) ) == NULL || pFTemp == HB_COMP_PARAM->functions.pFirst ) + s_externNames[ w++ ] = pFunc->szName; + pFunc = pFunc->pNext; + } + s_externNames[ w ] = 0; + ExternalNames( hObjFile, s_externNames ); + } +} + +static void putbyte( BYTE b, FILE * hObjFile, BYTE * pbChecksum ) +{ + fputc( b, hObjFile ); + * pbChecksum += b; +} + +static void putword( USHORT w, FILE * hObjFile, BYTE * pbChecksum ) +{ + putbyte( HB_LOBYTE( w ), hObjFile, pbChecksum ); + putbyte( HB_HIBYTE( w ), hObjFile, pbChecksum ); +} + +static void CompiledFileName( FILE * hObjFile, char * szFileName ) +{ + USHORT wLen = strlen( szFileName ); + BYTE bChk = 0; /* this is a checksum the linker will check to asure OBJ integrity */ + BYTE bChar; + + putbyte( 0x80, hObjFile, &bChk ); /* this tells the linker the kind of OBJ record this is */ + putbyte( 1 + 1 + wLen, hObjFile, &bChk ); /* now it comes the total length of this OBJ record */ + putbyte( 0, hObjFile, &bChk ); + putbyte( (BYTE) wLen, hObjFile, &bChk ); /* szFileName length */ + + while( ( bChar = * szFileName++ ) != 0 ) + putbyte( bChar, hObjFile, &bChk ); /* each of the szFileName characters */ + + putbyte( 256 - bChk, hObjFile, &bChk ); /* a checksum that will be recalculated by the linker */ +} + +static void CompilerVersion( FILE * hObjFile, char * szVersion ) +{ + USHORT wLen = strlen( szVersion ); + BYTE bChk = 0; /* this is a checksum the linker will check to asure OBJ integrity */ + BYTE bChar; + + putbyte( 0x88, hObjFile, &bChk ); /* this tells the linker the kind of OBJ record this is */ + putword( 3 + wLen, hObjFile, &bChk ); /* now it comes the total length of this OBJ record */ + putword( 0, hObjFile, &bChk ); + + while( ( bChar = * szVersion++ ) != 0 ) + putbyte( bChar, hObjFile, &bChk ); /* each of the szFileName characters */ + + putbyte( 256 - bChk, hObjFile, &bChk ); /* a checksum that will be recalculated by the linker */ +} + +static void LocalNames( FILE * hObjFile, char * szNames[] ) +{ + BYTE b = 0, c; + USHORT wTotalLen = 0; + BYTE bChk = 0; + + while( szNames[ b ] ) + wTotalLen += strlen( szNames[ b++ ] ); + wTotalLen += 2 + b; + + putbyte( 0x96, hObjFile, &bChk ); + putword( wTotalLen, hObjFile, &bChk ); + putbyte( 0, hObjFile, &bChk ); + + b = 0; + while( szNames[ b ] ) + { + putbyte( strlen( szNames[ b ] ), hObjFile, &bChk ); + + c = 0; + while( szNames[ b ][ c ] ) + putbyte( szNames[ b ][ c++ ], hObjFile, &bChk ); + b++; + } + putbyte( 256 - bChk, hObjFile, &bChk ); +} + +static void ExternalNames( FILE * hObjFile, char * szNames[] ) +{ + BYTE b = 0, c; + USHORT wTotalLen = 0; + BYTE bChk = 0; + + while( szNames[ b ] ) + { + if( b == 0 ) + wTotalLen += strlen( szNames[ b++ ] ) + 1; + else + wTotalLen += strlen( s_szPrefix ) + strlen( szNames[ b++ ] ) + 1; + } + wTotalLen += 2 + b - 1; + + putbyte( 0x8C, hObjFile, &bChk ); + putword( wTotalLen, hObjFile, &bChk ); + + b = 0; + while( szNames[ b ] ) + { + if( b == 0 ) + putbyte( strlen( szNames[ b ] ), hObjFile, &bChk ); + else + putbyte( strlen( s_szPrefix ) + strlen( szNames[ b ] ), hObjFile, &bChk ); + + c = 0; + + if( b > 0 ) + { + while( s_szPrefix[ c ] ) + putbyte( s_szPrefix[ c++ ], hObjFile, &bChk ); + c = 0; + } + + while( szNames[ b ][ c ] ) + putbyte( szNames[ b ][ c++ ], hObjFile, &bChk ); + putbyte( 0, hObjFile, &bChk ); + b++; + } + putbyte( 256 - bChk, hObjFile, &bChk ); +} + +static void CodeSegment( HB_COMP_DECL, FILE * hObjFile, BYTE * prgCode, ULONG ulPrgLen, USHORT wFunctions ) +{ + BYTE bChk = 0; + USHORT y; + USHORT wTotalLen = (USHORT) ( ulPrgLen * wFunctions ) + 4; + ULONG ul; + PFUNCTION pFunction = HB_COMP_PARAM->functions.pFirst; + ULONG ulPCodeOffset = HB_COMP_PARAM->symbols.iCount * sizeof( HB_SYMB ); + + if( ! HB_COMP_PARAM->fStartProc ) + pFunction = pFunction->pNext; + + putbyte( 0xA0, hObjFile, &bChk ); + putword( wTotalLen, hObjFile, &bChk ); + putbyte( 1, hObjFile, &bChk ); /* 1 = _TEXT segment */ + putword( 0, hObjFile, &bChk ); /* 0 = offset */ + + for( y = 0; y < wFunctions; y++ ) + { + * ( ULONG * ) &prgCode[ 6 ] = ulPCodeOffset; /* function pcode offset */ + for( ul = 0; ul < ulPrgLen; ul++ ) + putbyte( * ( prgCode + ul ), hObjFile, &bChk ); + ulPCodeOffset += pFunction->lPCodePos; + pFunction = pFunction->pNext; + } + + putbyte( 256 - bChk, hObjFile, &bChk ); +} + +static void DataSegment( HB_COMP_DECL, FILE * hObjFile, BYTE * symbol, ULONG wSymLen, ULONG wSymbols, + ULONG ulSize ) +{ + BYTE bChk = 0; + ULONG w, y; + USHORT wTotalLen = 4 + (USHORT) ulSize; + PCOMSYMBOL pSymbol = GetFirstSymbol( HB_COMP_PARAM ); + PFUNCTION pFunction = HB_COMP_PARAM->functions.pFirst; + ULONG ulSymbolNameOffset = GetSymbolsSize( HB_COMP_PARAM ) + GetPCodesSize( HB_COMP_PARAM ); + ULONG ulFunctionOffset; + + if( ! HB_COMP_PARAM->fStartProc ) + pFunction = pFunction->pNext; + + putbyte( 0xA0, hObjFile, &bChk ); + putword( wTotalLen, hObjFile, &bChk ); + putbyte( 4, hObjFile, &bChk ); /* 2 = _DATA segment defined order */ + putword( 0, hObjFile, &bChk ); /* 0 = offset */ + + for( y = 0; y < wSymbols; y++ ) + { + * ( ULONG * ) symbol = ulSymbolNameOffset; + + if( ! IsExternal( HB_COMP_PARAM, y ) ) + { + ulFunctionOffset = ( hb_compFunctionGetPos( HB_COMP_PARAM, pSymbol->szName ) - 1 ) * + sizeof( s_prgFunction ); + * ( ( ULONG * ) &symbol[ 8 ] ) = ulFunctionOffset; /* 8 offset of function pointer into symbol */ + } + else + * ( ( ULONG * ) &symbol[ 8 ] ) = 0; /* 8 offset of function pointer into symbol */ + + if( pSymbol->cScope == HB_FS_MESSAGE ) + symbol[ 4 ] = HB_FS_PUBLIC; + else + symbol[ 4 ] = pSymbol->cScope; + + for( w = 0; w < wSymLen; w++ ) + putbyte( * ( symbol + w ), hObjFile, &bChk ); + + ulSymbolNameOffset += strlen( pSymbol->szName ) + 1; + pSymbol = pSymbol->pNext; + } + + while( pFunction ) + { + w = 0; + while( w < pFunction->lPCodePos ) + putbyte( pFunction->pCode[ w++ ], hObjFile, &bChk ); + + pFunction = pFunction->pNext; + } + + pSymbol = GetFirstSymbol( HB_COMP_PARAM ); + + while( pSymbol ) + { + for( w = 0; w < strlen( pSymbol->szName ); w++ ) + putbyte( pSymbol->szName[ w ], hObjFile, &bChk ); + + putbyte( 0, hObjFile, &bChk ); + pSymbol = pSymbol->pNext; + } + + putbyte( 256 - bChk, hObjFile, &bChk ); +} + +static void DefineSegment( FILE * hObjFile, BYTE bName, BYTE bClass, USHORT wLen ) +{ + BYTE bChk = 0; + + putbyte( 0x98, hObjFile, &bChk ); + putbyte( 7, hObjFile, &bChk ); /* SegDef records have always this length */ + putbyte( 0, hObjFile, &bChk ); + + putbyte( 0xA9, hObjFile, &bChk ); + putword( wLen, hObjFile, &bChk ); + putbyte( bName, hObjFile, &bChk ); + putbyte( bClass, hObjFile, &bChk ); + putbyte( 0, hObjFile, &bChk ); + + putbyte( 256 - bChk, hObjFile, &bChk ); +} + +static void PubDef( FILE * hObjFile, char * szName, USHORT wSegment, USHORT wOffset ) +{ + BYTE bChk = 0; + BYTE bChar; + USHORT wLen = 2 + 2 + strlen( s_szPrefix ) + strlen( szName ) + 2 + 1; + const char * szTemp; + + putbyte( 0x90, hObjFile, &bChk ); + putword( wLen, hObjFile, &bChk ); + putbyte( 0x00, hObjFile, &bChk ); + putbyte( (BYTE) wSegment, hObjFile, &bChk ); + putbyte( strlen( s_szPrefix ) + strlen( szName ), hObjFile, &bChk ); + + szTemp = s_szPrefix; + while( ( bChar = * szTemp++ ) != 0 ) + putbyte( bChar, hObjFile, &bChk ); + + while( ( bChar = * szName++ ) != 0 ) + putbyte( bChar, hObjFile, &bChk ); + + putword( wOffset, hObjFile, &bChk ); + putbyte( 0x00, hObjFile, &bChk ); + + putbyte( 256 - bChk, hObjFile, &bChk ); +} + +static void Fixup( FILE * hObjFile, BYTE bType, USHORT wOffset, BYTE bFlags, BYTE bSymbol ) +{ + BYTE bChk = 0; + + putbyte( 0x9D, hObjFile, &bChk ); + putword( 5, hObjFile, &bChk ); + putbyte( bType + HB_HIBYTE( wOffset ), hObjFile, &bChk ); + putbyte( HB_LOBYTE( wOffset ), hObjFile, &bChk ); + putbyte( bFlags, hObjFile, &bChk ); + putbyte( bSymbol, hObjFile, &bChk ); + + putbyte( 256 - bChk, hObjFile, &bChk ); +} + +static void EnumeratedData( FILE * hObjFile, BYTE bSegment, BYTE * pData, USHORT wLen, USHORT wOffset ) +{ + BYTE bChk = 0; + USHORT w; + + putbyte( 0xA0, hObjFile, &bChk ); + putword( ( USHORT ) ( wLen + 4 ), hObjFile, &bChk ); + putbyte( bSegment, hObjFile, &bChk ); + putword( wOffset, hObjFile, &bChk ); + + for( w = 0; w < wLen; w++ ) + putbyte( * ( pData + w ), hObjFile, &bChk ); + + putbyte( 256 - bChk, hObjFile, &bChk ); +} + +static void End( FILE * hObjFile ) +{ + BYTE bChk = 0; + + putbyte( 0x8A, hObjFile, &bChk ); + putbyte( 0x02, hObjFile, &bChk ); + putbyte( 0x00, hObjFile, &bChk ); + putbyte( 0x00, hObjFile, &bChk ); + putbyte( 256 - bChk, hObjFile, &bChk ); +} + +static void GroupDef( FILE * hObjFile, BYTE bName, BYTE * aSegs ) +{ + BYTE bChk = 0; + USHORT wRecLen = 2; + USHORT w = 0; + + while( aSegs[ w++ ] ) + wRecLen += 2; + + putbyte( 0x9A, hObjFile, &bChk ); + putword( wRecLen, hObjFile, &bChk ); + putbyte( bName + 1, hObjFile, &bChk ); + + w = 0; + while( aSegs[ w ] ) + { + putbyte( 0xFF, hObjFile, &bChk ); + putbyte( aSegs[ w++ ], hObjFile, &bChk ); + } + + putbyte( 256 - bChk, hObjFile, &bChk ); +} void hb_compGenObj32( HB_COMP_DECL, PHB_FNAME pFileName ) { @@ -96,10 +646,10 @@ void hb_compGenObj32( HB_COMP_DECL, PHB_FNAME pFileName ) GenerateDataSegment( HB_COMP_PARAM, hObjFile ); GenerateSymbolsSegment( HB_COMP_PARAM, hObjFile ); End( hObjFile ); - if( externNames ) + if( s_externNames ) { - hb_xfree( externNames ); - externNames = NULL; + hb_xfree( s_externNames ); + s_externNames = NULL; } fclose( hObjFile ); @@ -107,580 +657,3 @@ void hb_compGenObj32( HB_COMP_DECL, PHB_FNAME pFileName ) if( ! HB_COMP_PARAM->fQuiet ) hb_compOutStd( HB_COMP_PARAM, "Done.\n" ); } - -static USHORT hb_compFunctionGetPos( HB_COMP_DECL, char * szFunctionName ) /* return 0 if not found or order + 1 */ -{ - PFUNCTION pFunc = HB_COMP_PARAM->functions.pFirst; - USHORT wFunction = HB_COMP_PARAM->fStartProc ? 1 : 0; - - while( pFunc ) - { - if( ! strcmp( pFunc->szName, szFunctionName ) && pFunc != HB_COMP_PARAM->functions.pFirst ) - return wFunction; - wFunction++; - pFunc = pFunc->pNext; - } - return 0; -} - -static ULONG GetSymbolsSize( HB_COMP_DECL ) -{ - return HB_COMP_PARAM->symbols.iCount * sizeof( HB_SYMB ); -} - -static PCOMSYMBOL GetFirstSymbol( HB_COMP_DECL ) -{ - PCOMSYMBOL pSymbol = HB_COMP_PARAM->symbols.pFirst; - return pSymbol; -} - -static char * GetSymbolName( HB_COMP_DECL, ULONG ulPos ) -{ - PCOMSYMBOL pSymbol = GetFirstSymbol( HB_COMP_PARAM ); - ULONG ul = 0; - - while( pSymbol && ( ul++ < ulPos ) ) - pSymbol = pSymbol->pNext; - - return pSymbol->szName; -} - -static ULONG GetPCodesSize( HB_COMP_DECL ) -{ - ULONG ulTotal = 0; - PFUNCTION pFunction = HB_COMP_PARAM->functions.pFirst; - - if( ! HB_COMP_PARAM->fStartProc ) - pFunction = pFunction->pNext; - - while( pFunction ) - { - ulTotal += pFunction->lPCodePos; - pFunction = pFunction->pNext; - } - return ulTotal; -} - -static ULONG GetSymbolsAmount( HB_COMP_DECL ) -{ - PCOMSYMBOL pSymbol = GetFirstSymbol( HB_COMP_PARAM ); - ULONG ulAmount = 1; - - while( pSymbol->pNext ) - { - ulAmount++; - pSymbol = pSymbol->pNext; - } - return ulAmount; -} - -static BOOL IsExternal( HB_COMP_DECL, ULONG ulSymbol ) -{ - PCOMSYMBOL pSymbol = GetFirstSymbol( HB_COMP_PARAM ); - ULONG ul = 0; - - while( ul++ < ulSymbol ) - pSymbol = pSymbol->pNext; - - return ! hb_compFunctionFind( HB_COMP_PARAM, pSymbol->szName ); -} - -static USHORT GetExternalPos( char * szExternal ) -{ - USHORT w = 0; - - while( w < wExternals ) - { - if( ! strcmp( szExternal, externNames[ w ] ) ) - break; - w++; - } - - return w; -} - -static void GenerateLocalNames( FILE * hObjFile ) -{ - char * localNames[] = { "_TEXT", "CODE", - "_NULL", "_DATA", "DATA", - "_BSS", "BSS", "DGROUP", - "HB_STARTSYMBOLS", "HB_SYMBOLS", "HB_ENDSYMBOLS", "HARBOUR", - "HB_STARTBORSYMBOLS", "_INIT_", "HB_ENDBORSYMBOLS", "INITDATA", "BORLAND", - 0 }; - - LocalNames( hObjFile, localNames ); -} - -static void GenerateSymbolsSegment( HB_COMP_DECL, FILE * hObjFile ) -{ - BYTE symbolsData[] = { 0, 0, 0, 0, 0, 0, 0, 0 }; - BYTE groupDGroup[] = { 2, 3, 4, 0 }; /* segments defined order for DGROUP */ - BYTE groupSymGroup[] = { 5, 6, 7, 0 }; /* segments defined order for SYMGROUP */ - BYTE groupInitData[] = { 8, 9, 10, 0 }; /* segments defined order for INITDATA */ - - DefineSegment( hObjFile, 10, /* HB_STARTSYMBOLS position + 1 into localnames */ - 6, /* "DATA" position + 1 into localNames */ - 0 ); /* segment length */ - DefineSegment( hObjFile, 11, /* HB_SYMBOLS position + 1 into localNames */ - 6, /* "DATA" position + 1 into localNames */ - 8 ); /* segment length */ - DefineSegment( hObjFile, 12, /* HB_ENDSYMBOLS position + 1 into localNames */ - 6, /* "DATA" position + 1 into localNames */ - 0 ); /* segment length */ - - DefineSegment( hObjFile, 14, /* HB_STARTBORSYMBOLS position + 1 into localnames */ - 17, /* INITDATA position + 1 into localNames */ - 0 ); /* segment length */ - DefineSegment( hObjFile, 15, /* HB_STARTSYMBOLS position + 1 into localnames */ - 17, /* INITDATA position + 1 into localNames */ - 0 ); /* segment length */ - DefineSegment( hObjFile, 16, /* HB_ENDBORSYMBOLS position + 1 into localnames */ - 17, /* INITDATA position + 1 into localNames */ - 0 ); /* segment length */ - - GroupDef( hObjFile, 8, groupDGroup ); /* "DGROUP" localNames position - 1 */ - GroupDef( hObjFile, 12, groupSymGroup ); /* "SYMGROUP" localNames position - 1 */ - GroupDef( hObjFile, 17, groupInitData ); /* "BORLAND" localNames position - 1 */ - - * ( USHORT * ) symbolsData = (USHORT) GetSymbolsAmount( HB_COMP_PARAM ); - - EnumeratedData( hObjFile, 6, symbolsData, sizeof( symbolsData ), 0 ); /* HB_SYMBOLS defined order segment */ - - Fixup( hObjFile, 0xE4, 4, /* offset into HB_SYMBOLS segment */ - 0x54, - 4 ); /* DATA segment defined order */ -} - -static void GenerateDataSegment( HB_COMP_DECL, FILE * hObjFile ) -{ - HB_SYMB symbol; - ULONG ulSize = GetSymbolsSize( HB_COMP_PARAM ); - PCOMSYMBOL pSymbol = GetFirstSymbol( HB_COMP_PARAM ); - ULONG ulSymbols = GetSymbolsAmount( HB_COMP_PARAM ), ul; - - while( pSymbol ) - { - ulSize += strlen( pSymbol->szName ) + 1; - pSymbol = pSymbol->pNext; - } - - ulSize += GetPCodesSize( HB_COMP_PARAM ); - - DefineSegment( hObjFile, 4, /* _NULL position + 1 into localnames */ - 6, /* "DATA" position + 1 into localNames */ - 0 ); /* segment length */ - DefineSegment( hObjFile, 7, /* _BSS position + 1 into localNames */ - 8, /* "BSS" position + 1 into localNames */ - 0 ); /* segment length */ - DefineSegment( hObjFile, 5, /* "_DATA" position + 1 into localNames */ - 6, /* "DATA" position + 1 into localNames */ - (USHORT) ulSize ); /* segment length */ - - memset( &symbol, 0, sizeof( symbol ) ); - DataSegment( HB_COMP_PARAM, hObjFile, (BYTE *) &symbol, - sizeof( symbol ), GetSymbolsAmount( HB_COMP_PARAM ), ulSize ); - - pSymbol = GetFirstSymbol( HB_COMP_PARAM ); - for( ul = 0; ul < ulSymbols; ul++ ) - { - Fixup( hObjFile, 0xE4, (USHORT) ( ul * sizeof( HB_SYMB ) ), 0x54, 4 ); /* 4 = Data symbol name location */ - - if( IsExternal( HB_COMP_PARAM, ul ) ) - { - if( ! ( pSymbol->cScope & HB_FS_MESSAGE ) ) - Fixup( hObjFile, 0xE4, (USHORT) ( ul * sizeof( HB_SYMB ) ) + 8, 0x56, - GetExternalPos( GetSymbolName( HB_COMP_PARAM, ul ) ) + 1 ); - } - else - { - /* if( ! ( pSymbol->cScope & HB_FS_MESSAGE ) ) */ - Fixup( hObjFile, 0xE4, (USHORT) ( ul * sizeof( HB_SYMB ) ) + 8, 0x54, 1 ); /* function address location */ - } - pSymbol = pSymbol->pNext; - } -} - -static void GenerateCodeSegment( HB_COMP_DECL, FILE * hObjFile ) -{ - USHORT wFunctions = HB_COMP_PARAM->functions.iCount - ( HB_COMP_PARAM->fStartProc ? 0: 1 ); - ULONG ulSize = wFunctions * sizeof( prgFunction ); - PFUNCTION pFunc = ( HB_COMP_PARAM->fStartProc ? HB_COMP_PARAM->functions.pFirst: HB_COMP_PARAM->functions.pFirst->pNext ); - USHORT w = 0; - - DefineSegment( hObjFile, 2, /* "_TEXT" position + 1 into localNames */ - 3, /* "CODE" position + 1 into localNames */ - (USHORT) ulSize ); /* segment length */ - - while( pFunc ) - { - if( !( pFunc->cScope & ( HB_FS_STATIC | HB_FS_INIT | HB_FS_EXIT ) ) ) - PubDef( hObjFile, pFunc->szName, 1, w * sizeof( prgFunction ) ); - w++; - pFunc = pFunc->pNext; - } - - CodeSegment( HB_COMP_PARAM, hObjFile, prgFunction, sizeof( prgFunction ), wFunctions ); - - for( w = 0; w < wFunctions; w++ ) - { - /* prgFunction fixups */ - Fixup( hObjFile, 0xE4, ( w * sizeof( prgFunction ) ) + 1, - 0x54, 4 ); /* 4 = DATA segment defined order */ - - Fixup( hObjFile, 0xE4, ( w * sizeof( prgFunction ) ) + 6, - 0x54, 4 ); /* DATA segment define order - pcode location */ - - Fixup( hObjFile, 0xA4, ( w * sizeof( prgFunction ) ) + 11, - 0x56, 1 ); /* External: _hb_vmExecute */ - } -} - -static void GenerateExternals( HB_COMP_DECL, FILE * hObjFile ) -{ - USHORT w; - PFUNCALL pFunc; - PFUNCTION pFTemp; - - /* calculate amount of externals */ - pFunc = HB_COMP_PARAM->funcalls.pFirst; - while( pFunc ) - { - if( ( pFTemp = hb_compFunctionFind( HB_COMP_PARAM, pFunc->szName ) ) == NULL || pFTemp == HB_COMP_PARAM->functions.pFirst ) - wExternals++; - pFunc = pFunc->pNext; - } - if( wExternals ) - { - externNames = ( char * * ) hb_xgrab( sizeof( char * ) * ( wExternals + 2 ) ); - w = 1; - externNames[ 0 ] = "_hb_vmExecute"; - - pFunc = HB_COMP_PARAM->funcalls.pFirst; - while( pFunc ) - { - if( ( pFTemp = hb_compFunctionFind( HB_COMP_PARAM, pFunc->szName ) ) == NULL || pFTemp == HB_COMP_PARAM->functions.pFirst ) - externNames[ w++ ] = pFunc->szName; - pFunc = pFunc->pNext; - } - externNames[ w ] = 0; - ExternalNames( hObjFile, externNames ); - } -} - -static void putbyte( BYTE b, FILE * hObjFile, BYTE * pbChecksum ) -{ - fputc( b, hObjFile ); - * pbChecksum += b; -} - -static void putword( USHORT w, FILE * hObjFile, BYTE * pbChecksum ) -{ - putbyte( HB_LOBYTE( w ), hObjFile, pbChecksum ); - putbyte( HB_HIBYTE( w ), hObjFile, pbChecksum ); -} - -static void CompiledFileName( FILE * hObjFile, char * szFileName ) -{ - USHORT wLen = strlen( szFileName ); - BYTE bChk = 0; /* this is a checksum the linker will check to asure OBJ integrity */ - BYTE bChar; - - putbyte( 0x80, hObjFile, &bChk ); /* this tells the linker the kind of OBJ record this is */ - putbyte( 1 + 1 + wLen, hObjFile, &bChk ); /* now it comes the total length of this OBJ record */ - putbyte( 0, hObjFile, &bChk ); - putbyte( (BYTE) wLen, hObjFile, &bChk ); /* szFileName length */ - - while( ( bChar = * szFileName++ ) != 0 ) - putbyte( bChar, hObjFile, &bChk ); /* each of the szFileName characters */ - - putbyte( 256 - bChk, hObjFile, &bChk ); /* a checksum that will be recalculated by the linker */ -} - -static void CompilerVersion( FILE * hObjFile, char * szVersion ) -{ - USHORT wLen = strlen( szVersion ); - BYTE bChk = 0; /* this is a checksum the linker will check to asure OBJ integrity */ - BYTE bChar; - - putbyte( 0x88, hObjFile, &bChk ); /* this tells the linker the kind of OBJ record this is */ - putword( 3 + wLen, hObjFile, &bChk ); /* now it comes the total length of this OBJ record */ - putword( 0, hObjFile, &bChk ); - - while( ( bChar = * szVersion++ ) != 0 ) - putbyte( bChar, hObjFile, &bChk ); /* each of the szFileName characters */ - - putbyte( 256 - bChk, hObjFile, &bChk ); /* a checksum that will be recalculated by the linker */ -} - -static void LocalNames( FILE * hObjFile, char * szNames[] ) -{ - BYTE b = 0, c; - USHORT wTotalLen = 0; - BYTE bChk = 0; - - while( szNames[ b ] ) - wTotalLen += strlen( szNames[ b++ ] ); - wTotalLen += 2 + b; - - putbyte( 0x96, hObjFile, &bChk ); - putword( wTotalLen, hObjFile, &bChk ); - putbyte( 0, hObjFile, &bChk ); - - b = 0; - while( szNames[ b ] ) - { - putbyte( strlen( szNames[ b ] ), hObjFile, &bChk ); - - c = 0; - while( szNames[ b ][ c ] ) - putbyte( szNames[ b ][ c++ ], hObjFile, &bChk ); - b++; - } - putbyte( 256 - bChk, hObjFile, &bChk ); -} - -static void ExternalNames( FILE * hObjFile, char * szNames[] ) -{ - BYTE b = 0, c; - USHORT wTotalLen = 0; - BYTE bChk = 0; - - while( szNames[ b ] ) - { - if( b == 0 ) - wTotalLen += strlen( szNames[ b++ ] ) + 1; - else - wTotalLen += strlen( szPrefix ) + strlen( szNames[ b++ ] ) + 1; - } - wTotalLen += 2 + b - 1; - - putbyte( 0x8C, hObjFile, &bChk ); - putword( wTotalLen, hObjFile, &bChk ); - - b = 0; - while( szNames[ b ] ) - { - if( b == 0 ) - putbyte( strlen( szNames[ b ] ), hObjFile, &bChk ); - else - putbyte( strlen( szPrefix ) + strlen( szNames[ b ] ), hObjFile, &bChk ); - - c = 0; - - if( b > 0 ) - { - while( szPrefix[ c ] ) - putbyte( szPrefix[ c++ ], hObjFile, &bChk ); - c = 0; - } - - while( szNames[ b ][ c ] ) - putbyte( szNames[ b ][ c++ ], hObjFile, &bChk ); - putbyte( 0, hObjFile, &bChk ); - b++; - } - putbyte( 256 - bChk, hObjFile, &bChk ); -} - -static void CodeSegment( HB_COMP_DECL, FILE * hObjFile, BYTE * prgCode, ULONG ulPrgLen, USHORT wFunctions ) -{ - BYTE bChk = 0; - USHORT y; - USHORT wTotalLen = (USHORT) ( ulPrgLen * wFunctions ) + 4; - ULONG ul; - PFUNCTION pFunction = HB_COMP_PARAM->functions.pFirst; - ULONG ulPCodeOffset = HB_COMP_PARAM->symbols.iCount * sizeof( HB_SYMB ); - - if( ! HB_COMP_PARAM->fStartProc ) - pFunction = pFunction->pNext; - - putbyte( 0xA0, hObjFile, &bChk ); - putword( wTotalLen, hObjFile, &bChk ); - putbyte( 1, hObjFile, &bChk ); /* 1 = _TEXT segment */ - putword( 0, hObjFile, &bChk ); /* 0 = offset */ - - for( y = 0; y < wFunctions; y++ ) - { - * ( ULONG * ) &prgCode[ 6 ] = ulPCodeOffset; /* function pcode offset */ - for( ul = 0; ul < ulPrgLen; ul++ ) - putbyte( * ( prgCode + ul ), hObjFile, &bChk ); - ulPCodeOffset += pFunction->lPCodePos; - pFunction = pFunction->pNext; - } - - putbyte( 256 - bChk, hObjFile, &bChk ); -} - -static void DataSegment( HB_COMP_DECL, FILE * hObjFile, BYTE * symbol, ULONG wSymLen, ULONG wSymbols, - ULONG ulSize ) -{ - BYTE bChk = 0; - ULONG w, y; - USHORT wTotalLen = 4 + (USHORT) ulSize; - PCOMSYMBOL pSymbol = GetFirstSymbol( HB_COMP_PARAM ); - PFUNCTION pFunction = HB_COMP_PARAM->functions.pFirst; - ULONG ulSymbolNameOffset = GetSymbolsSize( HB_COMP_PARAM ) + GetPCodesSize( HB_COMP_PARAM ); - ULONG ulFunctionOffset; - - if( ! HB_COMP_PARAM->fStartProc ) - pFunction = pFunction->pNext; - - putbyte( 0xA0, hObjFile, &bChk ); - putword( wTotalLen, hObjFile, &bChk ); - putbyte( 4, hObjFile, &bChk ); /* 2 = _DATA segment defined order */ - putword( 0, hObjFile, &bChk ); /* 0 = offset */ - - for( y = 0; y < wSymbols; y++ ) - { - * ( ULONG * ) symbol = ulSymbolNameOffset; - - if( ! IsExternal( HB_COMP_PARAM, y ) ) - { - ulFunctionOffset = ( hb_compFunctionGetPos( HB_COMP_PARAM, pSymbol->szName ) - 1 ) * - sizeof( prgFunction ); - * ( ( ULONG * ) &symbol[ 8 ] ) = ulFunctionOffset; /* 8 offset of function pointer into symbol */ - } - else - * ( ( ULONG * ) &symbol[ 8 ] ) = 0; /* 8 offset of function pointer into symbol */ - - if( pSymbol->cScope == HB_FS_MESSAGE ) - symbol[ 4 ] = HB_FS_PUBLIC; - else - symbol[ 4 ] = pSymbol->cScope; - - for( w = 0; w < wSymLen; w++ ) - putbyte( * ( symbol + w ), hObjFile, &bChk ); - - ulSymbolNameOffset += strlen( pSymbol->szName ) + 1; - pSymbol = pSymbol->pNext; - } - - while( pFunction ) - { - w = 0; - while( w < pFunction->lPCodePos ) - putbyte( pFunction->pCode[ w++ ], hObjFile, &bChk ); - - pFunction = pFunction->pNext; - } - - pSymbol = GetFirstSymbol( HB_COMP_PARAM ); - - while( pSymbol ) - { - for( w = 0; w < strlen( pSymbol->szName ); w++ ) - putbyte( pSymbol->szName[ w ], hObjFile, &bChk ); - - putbyte( 0, hObjFile, &bChk ); - pSymbol = pSymbol->pNext; - } - - putbyte( 256 - bChk, hObjFile, &bChk ); -} - -static void DefineSegment( FILE * hObjFile, BYTE bName, BYTE bClass, USHORT wLen ) -{ - BYTE bChk = 0; - - putbyte( 0x98, hObjFile, &bChk ); - putbyte( 7, hObjFile, &bChk ); /* SegDef records have always this length */ - putbyte( 0, hObjFile, &bChk ); - - putbyte( 0xA9, hObjFile, &bChk ); - putword( wLen, hObjFile, &bChk ); - putbyte( bName, hObjFile, &bChk ); - putbyte( bClass, hObjFile, &bChk ); - putbyte( 0, hObjFile, &bChk ); - - putbyte( 256 - bChk, hObjFile, &bChk ); -} - -static void PubDef( FILE * hObjFile, char * szName, USHORT wSegment, USHORT wOffset ) -{ - BYTE bChk = 0; - BYTE bChar; - USHORT wLen = 2 + 2 + strlen( szPrefix ) + strlen( szName ) + 2 + 1; - const char * szTemp; - - putbyte( 0x90, hObjFile, &bChk ); - putword( wLen, hObjFile, &bChk ); - putbyte( 0x00, hObjFile, &bChk ); - putbyte( (BYTE) wSegment, hObjFile, &bChk ); - putbyte( strlen( szPrefix ) + strlen( szName ), hObjFile, &bChk ); - - szTemp = szPrefix; - while( ( bChar = * szTemp++ ) != 0 ) - putbyte( bChar, hObjFile, &bChk ); - - while( ( bChar = * szName++ ) != 0 ) - putbyte( bChar, hObjFile, &bChk ); - - putword( wOffset, hObjFile, &bChk ); - putbyte( 0x00, hObjFile, &bChk ); - - putbyte( 256 - bChk, hObjFile, &bChk ); -} - -static void Fixup( FILE * hObjFile, BYTE bType, USHORT wOffset, BYTE bFlags, BYTE bSymbol ) -{ - BYTE bChk = 0; - - putbyte( 0x9D, hObjFile, &bChk ); - putword( 5, hObjFile, &bChk ); - putbyte( bType + HB_HIBYTE( wOffset ), hObjFile, &bChk ); - putbyte( HB_LOBYTE( wOffset ), hObjFile, &bChk ); - putbyte( bFlags, hObjFile, &bChk ); - putbyte( bSymbol, hObjFile, &bChk ); - - putbyte( 256 - bChk, hObjFile, &bChk ); -} - -static void EnumeratedData( FILE * hObjFile, BYTE bSegment, BYTE * pData, USHORT wLen, USHORT wOffset ) -{ - BYTE bChk = 0; - USHORT w; - - putbyte( 0xA0, hObjFile, &bChk ); - putword( ( USHORT ) ( wLen + 4 ), hObjFile, &bChk ); - putbyte( bSegment, hObjFile, &bChk ); - putword( wOffset, hObjFile, &bChk ); - - for( w = 0; w < wLen; w++ ) - putbyte( * ( pData + w ), hObjFile, &bChk ); - - putbyte( 256 - bChk, hObjFile, &bChk ); -} - -static void End( FILE * hObjFile ) -{ - BYTE bChk = 0; - - putbyte( 0x8A, hObjFile, &bChk ); - putbyte( 0x02, hObjFile, &bChk ); - putbyte( 0x00, hObjFile, &bChk ); - putbyte( 0x00, hObjFile, &bChk ); - putbyte( 256 - bChk, hObjFile, &bChk ); -} - -static void GroupDef( FILE * hObjFile, BYTE bName, BYTE * aSegs ) -{ - BYTE bChk = 0; - USHORT wRecLen = 2; - USHORT w = 0; - - while( aSegs[ w++ ] ) - wRecLen += 2; - - putbyte( 0x9A, hObjFile, &bChk ); - putword( wRecLen, hObjFile, &bChk ); - putbyte( bName + 1, hObjFile, &bChk ); - - w = 0; - while( aSegs[ w ] ) - { - putbyte( 0xFF, hObjFile, &bChk ); - putbyte( aSegs[ w++ ], hObjFile, &bChk ); - } - - putbyte( 256 - bChk, hObjFile, &bChk ); -}