19990828-14:00 GMT+1

This commit is contained in:
Viktor Szakats
1999-08-28 12:23:53 +00:00
parent 5d2b941e13
commit 90a11a7528
13 changed files with 421 additions and 329 deletions

View File

@@ -1,3 +1,39 @@
19990828-14:00 GMT+1 Victor Szel <info@szelvesz.hu>
* source/rtl/filesys.c
source/hbpp/stdalone/hbpp.c
source/compiler/harbour.y
include/hbsetup.h
include/hbpp.h
! hb_fsFNameSplit() fixed handling of colon in filenames.
(reported by Bruno Cantero)
* source/compiler/harbour.y
! Fixed the name format of the generated symbol registration function,
since it was causing a compiler error where the .prg name begun with
a number ( for example: 1.prg ). The new format is: hb_vm_SymbolInit_*()
* include/ctoharb.h
source/rtl/errorapi.c
source/vm/hvm.c
+ hb_errLaunch() and hb_errLaunchSubst() finished
(the latter not yet tested).
Thanks to Ryszard Glab.
* include/ctoharb.h
source/vm/hvm.c
source/vm/initsymb.c
* hb_vmRTSymbolsInit() -> hb_vmSymbolInit_RT
* include/hbsetup.h
include/hbpp.h
+ Changed OPT_DELIMITER to OS_OPT_DELIMITER_LIST and moved to hbsetup.h
So now it's multiplatform.
* source/rtl/mouse/mousedos.c
+ hb_mouse_IsButtonPressed() added by Luiz Rafael Culik.
(small fixes applied, code not tested)
* include/hbdefs.h
! LOBYTE(),HIBYTE(),LOWORD() put in #ifndef guards.
(reported by Jon Berg)
* tests/working/fileio.prg
+ Some tests added.
19990828-08:40 GMT+1 Antonio Linares <alinares@fivetech.com>
* source/vm/hvm.c
* Fixed hb_vmDebuggerEndProc()
@@ -36,7 +72,7 @@
* source/debug/tbrwtext.prg
* small fixes.
19990826-06:50 GMT+1 Victor Szel <info@szelvesz.hu>
19990827-06:50 GMT+1 Victor Szel <info@szelvesz.hu>
* source/rtl/inkey.c
include/inkey.h
@@ -50,7 +86,7 @@
* hb_inkeyPoll() now calls hb_inkeyPut() to insert the new code.
! INKEY() fixed parameter count checking bug introduced a few hours ago.
19990826-06:00 GMT+1 Victor Szel <info@szelvesz.hu>
19990827-06:00 GMT+1 Victor Szel <info@szelvesz.hu>
* include/mouseapi.h
source/rtl/mouseapi.c
@@ -67,7 +103,7 @@
Non-GNU make file users should add the new files source/rtl/mouseapi.c
and source/rtl/mouse/mousedos.c file to their make system.
19990826-05:00 GMT+1 Victor Szel <info@szelvesz.hu>
19990827-05:00 GMT+1 Victor Szel <info@szelvesz.hu>
* include/Makefile
include/mouseapi.h

View File

@@ -34,7 +34,13 @@ extern void hb_vmExecute( BYTE * pCode, PHB_SYMB pSymbols ); /* invokes the
extern void hb_vmProcessSymbols( PHB_SYMB pSymbols, WORD wSymbols ); /* statics symbols initialization */
extern void hb_vmRequestQuit( void );
extern void hb_vmRequestBreak( PHB_ITEM pItem );
extern void hb_vmRTSymbolsInit( void ); /* initialization of runtime support symbols */
extern WORD hb_vmRequestQuery( void );
extern void hb_vmQuit( void ); /* Immediately quits the virtual machine */
extern void hb_vmSymbolInit_RT( void ); /* initialization of runtime support symbols */
/* Return values of hb_vmRequestQuery() */
#define HB_QUIT_REQUESTED 1 /* immediately quit the application */
#define HB_BREAK_REQUESTED 2 /* break to nearest RECOVER/END sequence */
/* PCode functions */
extern void hb_vmAnd( void ); /* performs the logical AND on the latest two values, removes them and leaves result on the stack */

View File

@@ -65,9 +65,15 @@ typedef unsigned long DWORD;
#define FALSE 0
#define TRUE 1
#ifndef LOBYTE
#define LOBYTE( w ) ( ( BYTE )( w ) )
#endif
#ifndef HIBYTE
#define HIBYTE( w ) ( ( BYTE )( ( ( WORD )( w ) >> 8 ) & 0xFF ) )
#endif
#ifndef LOWORD
#define LOWORD( l ) ( ( WORD )( l ) )
#endif
#endif /* HB_DONT_DEFINE_BASIC_TYPES */
#endif /* __IBMCPP__ */

View File

@@ -38,13 +38,8 @@ typedef struct _COMMANDS
#define STR_SIZE 8192
#define BUFF_SIZE 2048
#define SKIPTABSPACES(sptr) while ( *sptr == ' ' || *sptr == '\t' ) (sptr)++
/* TODO: #define this for various platforms */
#define PATH_DELIMITER "/\\"
#define IS_PATH_SEP( c ) (strchr(PATH_DELIMITER, (c))!=NULL)
#define OPT_DELIMITER "/-"
#define IS_OPT_SEP( c ) (strchr(OPT_DELIMITER, (c))!=NULL)
#define SKIPTABSPACES( sptr ) while ( *sptr == ' ' || *sptr == '\t' ) ( sptr )++
#define IS_OPT_SEP( c ) ( strchr( OS_OPT_DELIMITER_LIST, ( c ) ) != NULL )
/* HBPP.C exported functions */

View File

@@ -46,8 +46,8 @@
* in run-time support modules and in user defined modules.
* If strict ANSI C compability is required then all symbol tables
* have to be joined manually by calling special function named
* <module_name>__InitSymbols
* (for example for myfirst.prg it will be: 'MYFIRST__InitSymbols'
* hb_vm_SymbolInit_<module_name>
* (for example for myfirst.prg it will be: 'hb_vm_SymbolInit_MYFIRST'
* The generation of this function is performed by the macro called
* HB_CALL_ON_STARTUP that is defined in 'init.h'
*
@@ -74,9 +74,9 @@
* By default we are using automatic lookup (symbol not defined)
*/
#if defined(__WATCOMC__) || defined(__GNUC__)
#if !defined(__DJGPP__) && !defined(HARBOUR_GCC_OS2)
#define HARBOUR_START_PROCEDURE "MAIN"
#endif
#if !defined(__DJGPP__) && !defined(HARBOUR_GCC_OS2)
#define HARBOUR_START_PROCEDURE "MAIN"
#endif
#endif
/* ***********************************************************************
@@ -115,7 +115,7 @@
/* Indicate that one of the GTAPIs is defined */
#if defined(HARBOUR_USE_DOS_GTAPI) || defined(HARBOUR_USE_OS2_GTAPI) || defined(HARBOUR_USE_WIN_GTAPI)
#define HARBOUR_USE_GTAPI
#define HARBOUR_USE_GTAPI
#endif
/* ***********************************************************************
@@ -137,22 +137,28 @@
* Operating system specific definitions
*/
#ifdef __GNUC__
/* The GNU C compiler is used */
#if defined(__DJGPP__) || defined(HARBOUR_GCC_OS2) || defined(_Windows) || defined(_WIN32)
/* The DJGPP port of GNU C is used - for DOS platform */
#define OS_PATH_LIST_SEPARATOR ';'
#define OS_PATH_DELIMITER '\\'
#define OS_DOS_COMPATIBLE
#else
#define OS_PATH_LIST_SEPARATOR ':'
#define OS_PATH_DELIMITER '/'
#define OS_UNIX_COMPATIBLE
#endif
/* The GNU C compiler is used */
#if defined(__DJGPP__) || defined(HARBOUR_GCC_OS2) || defined(_Windows) || defined(_WIN32)
/* The DJGPP port of GNU C is used - for DOS platform */
#define OS_DOS_COMPATIBLE
#define OS_PATH_LIST_SEPARATOR ';'
#define OS_PATH_DELIMITER '\\'
#define OS_PATH_DELIMITER_LIST "\\/:"
#define OS_OPT_DELIMITER_LIST "/-"
#else
#define OS_UNIX_COMPATIBLE
#define OS_PATH_LIST_SEPARATOR ':'
#define OS_PATH_DELIMITER '/'
#define OS_PATH_DELIMITER_LIST "/"
#define OS_OPT_DELIMITER_LIST "-"
#endif
#else
/* we are assuming here the DOS compatible OS */
#define OS_PATH_LIST_SEPARATOR ';'
#define OS_PATH_DELIMITER '\\'
#define OS_DOS_COMPATIBLE
/* we are assuming here the DOS compatible OS */
#define OS_DOS_COMPATIBLE
#define OS_PATH_LIST_SEPARATOR ';'
#define OS_PATH_DELIMITER '\\'
#define OS_PATH_DELIMITER_LIST "\\/:"
#define OS_OPT_DELIMITER_LIST "/-"
#endif
/* ***********************************************************************
@@ -160,27 +166,27 @@
*/
#ifndef DOS
#if defined(_QC) || defined(__DOS__) || defined(MSDOS) || defined(__MSDOS__)
#define DOS
#endif
#if defined(_QC) || defined(__DOS__) || defined(MSDOS) || defined(__MSDOS__)
#define DOS
#endif
#endif
#ifndef OS2
#if defined(__OS2__) || defined(OS_2) || defined(HARBOUR_GCC_OS2)
#define OS2
#endif
#if defined(__OS2__) || defined(OS_2) || defined(HARBOUR_GCC_OS2)
#define OS2
#endif
#endif
#ifndef EMX
#if defined(__EMX__)
#define EMX
#endif
#if defined(__EMX__)
#define EMX
#endif
#endif
#ifndef WINNT
#if defined(__NT__)
#define WINNT
#endif
#if defined(__NT__)
#define WINNT
#endif
#endif
#endif /* HB_SETUP_H_ */

View File

@@ -2336,7 +2336,7 @@ void GenCCode( char *szFileName, char *szName ) /* generates the C languag
/* Generate the wrapper that will initialize local symbol table
*/
yy_strupr( _pFileName->szName );
fprintf( yyc, "\n\nHB_INIT_SYMBOLS_BEGIN( %s__InitSymbols )\n", _pFileName->szName );
fprintf( yyc, "\n\nHB_INIT_SYMBOLS_BEGIN( hb_vm_SymbolInit_%s )\n", _pFileName->szName );
if( ! _bStartProc )
pSym = pSym->pNext; /* starting procedure is always the first symbol */
@@ -2390,8 +2390,8 @@ void GenCCode( char *szFileName, char *szName ) /* generates the C languag
pSym = pSym->pNext;
}
fprintf( yyc, "\nHB_INIT_SYMBOLS_END( %s__InitSymbols )\n", _pFileName->szName );
fprintf( yyc, "#if ! defined(__GNUC__)\n#pragma startup %s__InitSymbols\n#endif\n\n\n", _pFileName->szName );
fprintf( yyc, "\nHB_INIT_SYMBOLS_END( hb_vm_SymbolInit_%s )\n", _pFileName->szName );
fprintf( yyc, "#if ! defined(__GNUC__)\n#pragma startup hb_vm_SymbolInit_%s\n#endif\n\n\n", _pFileName->szName );
/* Generate functions data
*/
@@ -3633,10 +3633,10 @@ void Inc( void )
if( pStackValType )
{
if( pStackValType->cType == ' ' )
GenWarning( _szCWarnings, 'W', WARN_NUMERIC_SUSPECT, NULL, NULL );
else if( pStackValType->cType != 'N' )
GenWarning( _szCWarnings, 'W', WARN_NUMERIC_TYPE, sType, NULL );
if( pStackValType->cType == ' ' )
GenWarning( _szCWarnings, 'W', WARN_NUMERIC_SUSPECT, NULL, NULL );
else if( pStackValType->cType != 'N' )
GenWarning( _szCWarnings, 'W', WARN_NUMERIC_TYPE, sType, NULL );
}
}
}
@@ -4382,10 +4382,10 @@ void Dec( void )
if( pStackValType )
{
if( pStackValType->cType == ' ' )
GenWarning( _szCWarnings, 'W', WARN_NUMERIC_SUSPECT, NULL, NULL );
else if( pStackValType->cType != 'N' )
GenWarning( _szCWarnings, 'W', WARN_NUMERIC_TYPE, sType, NULL );
if( pStackValType->cType == ' ' )
GenWarning( _szCWarnings, 'W', WARN_NUMERIC_SUSPECT, NULL, NULL );
else if( pStackValType->cType != 'N' )
GenWarning( _szCWarnings, 'W', WARN_NUMERIC_TYPE, sType, NULL );
}
}
}
@@ -5284,116 +5284,135 @@ static void LoopEnd( void )
hb_xfree( (void *) pLoop );
}
#define IS_PATH_SEP( c ) ( strchr( OS_PATH_DELIMITER_LIST, ( c ) ) != NULL )
/* Split given filename into path, name and extension */
PHB_FNAME hb_fsFNameSplit( char *szFilename )
PHB_FNAME hb_fsFNameSplit( char * szFilename )
{
PHB_FNAME pName = (PHB_FNAME) hb_xgrab( sizeof(HB_FNAME) );
int iLen = strlen(szFilename);
int iSlashPos;
int iDotPos;
int iPos;
PHB_FNAME pName = ( PHB_FNAME ) hb_xgrab( sizeof( HB_FNAME ) );
pName->szPath = pName->szName = pName->szExtension = NULL;
int iLen = strlen( szFilename );
int iSlashPos;
int iDotPos;
int iPos;
iSlashPos = iLen-1;
iPos = 0;
pName->szPath =
pName->szName =
pName->szExtension = NULL;
while( iSlashPos >= 0 && !IS_PATH_SEP(szFilename[ iSlashPos ]) )
--iSlashPos;
iSlashPos = iLen - 1;
iPos = 0;
if( iSlashPos == 0 )
{
/* root path -> \filename */
pName->szBuffer[ 0 ] = OS_PATH_DELIMITER;
pName->szBuffer[ 1 ] = '\x0';
pName->szPath = pName->szBuffer;
iPos = 2; /* first free position after the slash */
}
else if( iSlashPos > 0 )
{
/* path with separator -> path\filename */
memcpy( pName->szBuffer, szFilename, iSlashPos );
pName->szBuffer[ iSlashPos ] = '\x0';
pName->szPath = pName->szBuffer;
iPos = iSlashPos + 1; /* first free position after the slash */
}
while( iSlashPos >= 0 && !IS_PATH_SEP( szFilename[ iSlashPos ] ) )
--iSlashPos;
iDotPos = iLen-1;
while( iDotPos > iSlashPos && szFilename[ iDotPos ] != '.' )
--iDotPos;
if( (iDotPos-iSlashPos) > 1 )
{
/* the dot was found
* and there is at least one character between a slash and a dot
*/
if( iDotPos == iLen-1 )
{
/* the dot is the last character -use it as extension name */
pName->szExtension = pName->szBuffer+iPos;
pName->szBuffer[ iPos++ ] = '.';
pName->szBuffer[ iPos++ ] = '\x0';
}
else
{
pName->szExtension = pName->szBuffer+iPos;
/* copy rest of the string with terminating ZERO character */
memcpy( pName->szExtension, szFilename+iDotPos+1, iLen-iDotPos );
iPos += iLen-iDotPos;
}
}
else
/* there is no dot in the filename or it is '.filename' */
iDotPos = iLen;
if( iSlashPos == 0 )
{
/* root path -> \filename */
pName->szBuffer[ 0 ] = OS_PATH_DELIMITER;
pName->szBuffer[ 1 ] = '\0';
pName->szPath = pName->szBuffer;
iPos = 2; /* first free position after the slash */
}
else if( iSlashPos > 0 )
{
/* If we are after a drive letter let's keep the following backslash */
if( IS_PATH_SEP( ':' ) &&
( szFilename[ iSlashPos ] == ':' || szFilename[ iSlashPos - 1 ] == ':' ) )
{
/* path with separator -> d:\path\filename or d:path\filename */
memcpy( pName->szBuffer, szFilename, iSlashPos + 1 );
pName->szBuffer[ iSlashPos + 1 ] = '\0';
iPos = iSlashPos + 2; /* first free position after the slash */
}
else
{
/* path with separator -> path\filename */
memcpy( pName->szBuffer, szFilename, iSlashPos );
pName->szBuffer[ iSlashPos ] = '\0';
iPos = iSlashPos + 1; /* first free position after the slash */
}
pName->szName = pName->szBuffer + iPos;
memcpy( pName->szName, szFilename + iSlashPos + 1, iDotPos - iSlashPos - 1 );
pName->szName[ iDotPos - iSlashPos - 1 ] = '\x0';
pName->szPath = pName->szBuffer;
}
return pName;
iDotPos = iLen - 1;
while( iDotPos > iSlashPos && szFilename[ iDotPos ] != '.' )
--iDotPos;
if( ( iDotPos - iSlashPos ) > 1 )
{
/* the dot was found
* and there is at least one character between a slash and a dot
*/
if( iDotPos == iLen - 1 )
{
/* the dot is the last character - use it as extension name */
pName->szExtension = pName->szBuffer + iPos;
pName->szBuffer[ iPos++ ] = '.';
pName->szBuffer[ iPos++ ] = '\0';
}
else
{
pName->szExtension = pName->szBuffer + iPos;
/* copy rest of the string with terminating ZERO character */
memcpy( pName->szExtension, szFilename + iDotPos + 1, iLen - iDotPos );
iPos += iLen - iDotPos;
}
}
else
/* there is no dot in the filename or it is '.filename' */
iDotPos = iLen;
pName->szName = pName->szBuffer + iPos;
memcpy( pName->szName, szFilename + iSlashPos + 1, iDotPos - iSlashPos - 1 );
pName->szName[ iDotPos - iSlashPos - 1 ] = '\0';
return pName;
}
/* This function joins path, name and extension into a string with a filename */
char * hb_fsFNameMerge( char *szFileName, PHB_FNAME pFileName )
char * hb_fsFNameMerge( char * szFileName, PHB_FNAME pFileName )
{
if( pFileName->szPath && pFileName->szPath[ 0 ] )
{
/* we have not empty path specified */
int iLen = strlen(pFileName->szPath);
if( pFileName->szPath && pFileName->szPath[ 0 ] )
{
/* we have not empty path specified */
int iLen = strlen( pFileName->szPath );
strcpy( szFileName, pFileName->szPath );
strcpy( szFileName, pFileName->szPath );
/* if the path is a root directory then we don't need to add path separator */
if( !(IS_PATH_SEP(pFileName->szPath[ 0 ]) && pFileName->szPath[ 0 ] == '\x0') )
{
/* add the path separator only in cases:
* when a name doesn't start with it
* when the path doesn't end with it
*/
if( !( IS_PATH_SEP(pFileName->szName[ 0 ]) || IS_PATH_SEP(pFileName->szPath[ iLen-1 ]) ) )
/* if the path is a root directory then we don't need to add path separator */
if( !( IS_PATH_SEP( pFileName->szPath[ 0 ] ) && pFileName->szPath[ 0 ] == '\0' ) )
{
szFileName[ iLen++ ] = OS_PATH_DELIMITER;
szFileName[ iLen ] = '\x0';
/* add the path separator only in cases:
* when a name doesn't start with it
* when the path doesn't end with it
*/
if( !( IS_PATH_SEP( pFileName->szName[ 0 ] ) || IS_PATH_SEP( pFileName->szPath[ iLen-1 ] ) ) )
{
szFileName[ iLen++ ] = OS_PATH_DELIMITER;
szFileName[ iLen ] = '\0';
}
}
}
strcpy( szFileName+iLen, pFileName->szName );
}
else
strcpy( szFileName, pFileName->szName );
strcpy( szFileName + iLen, pFileName->szName );
}
else
strcpy( szFileName, pFileName->szName );
if( pFileName->szExtension )
{
int iLen = strlen(szFileName);
if( pFileName->szExtension )
{
int iLen = strlen( szFileName );
if( !(pFileName->szExtension[ 0 ] == '.' || szFileName[ iLen-1 ] == '.') )
{
/* add extension separator only when extansion doesn't contain it */
szFileName[ iLen++ ] = '.';
szFileName[ iLen ] = '\x0';
}
strcpy( szFileName+iLen, pFileName->szExtension );
}
if( !( pFileName->szExtension[ 0 ] == '.' || szFileName[ iLen-1 ] == '.') )
{
/* add extension separator only when extansion doesn't contain it */
szFileName[ iLen++ ] = '.';
szFileName[ iLen ] = '\0';
}
strcpy( szFileName + iLen, pFileName->szExtension );
}
return szFileName;
return szFileName;
}
void * hb_xgrab( ULONG ulSize ) /* allocates fixed memory, exits on failure */

View File

@@ -427,116 +427,135 @@ void GenWarning( char* _szWarnings[], char cPrefix, int iWarning, char * szWarni
}
}
#define IS_PATH_SEP( c ) ( strchr( OS_PATH_DELIMITER_LIST, ( c ) ) != NULL )
/* Split given filename into path, name and extension */
PHB_FNAME hb_fsFNameSplit( char *szFilename )
PHB_FNAME hb_fsFNameSplit( char * szFilename )
{
PHB_FNAME pName = (PHB_FNAME) hb_xgrab( sizeof(HB_FNAME) );
int iLen = strlen(szFilename);
int iSlashPos;
int iDotPos;
int iPos;
PHB_FNAME pName = ( PHB_FNAME ) hb_xgrab( sizeof( HB_FNAME ) );
pName->szPath = pName->szName = pName->szExtension = NULL;
int iLen = strlen( szFilename );
int iSlashPos;
int iDotPos;
int iPos;
iSlashPos = iLen-1;
iPos = 0;
pName->szPath =
pName->szName =
pName->szExtension = NULL;
while( iSlashPos >= 0 && !IS_PATH_SEP(szFilename[ iSlashPos ]) )
--iSlashPos;
iSlashPos = iLen - 1;
iPos = 0;
if( iSlashPos == 0 )
{
/* root path -> \filename */
pName->szBuffer[ 0 ] = OS_PATH_DELIMITER;
pName->szBuffer[ 1 ] = '\x0';
pName->szPath = pName->szBuffer;
iPos = 2; /* first free position after the slash */
}
else if( iSlashPos > 0 )
{
/* path with separator -> path\filename */
memcpy( pName->szBuffer, szFilename, iSlashPos );
pName->szBuffer[ iSlashPos ] = '\x0';
pName->szPath = pName->szBuffer;
iPos = iSlashPos + 1; /* first free position after the slash */
}
while( iSlashPos >= 0 && !IS_PATH_SEP( szFilename[ iSlashPos ] ) )
--iSlashPos;
iDotPos = iLen-1;
while( iDotPos > iSlashPos && szFilename[ iDotPos ] != '.' )
--iDotPos;
if( (iDotPos-iSlashPos) > 1 )
{
/* the dot was found
* and there is at least one character between a slash and a dot
*/
if( iDotPos == iLen-1 )
{
/* the dot is the last character -use it as extension name */
pName->szExtension = pName->szBuffer+iPos;
pName->szBuffer[ iPos++ ] = '.';
pName->szBuffer[ iPos++ ] = '\x0';
}
else
{
pName->szExtension = pName->szBuffer+iPos;
/* copy rest of the string with terminating ZERO character */
memcpy( pName->szExtension, szFilename+iDotPos+1, iLen-iDotPos );
iPos += iLen-iDotPos;
}
}
else
/* there is no dot in the filename or it is '.filename' */
iDotPos = iLen;
if( iSlashPos == 0 )
{
/* root path -> \filename */
pName->szBuffer[ 0 ] = OS_PATH_DELIMITER;
pName->szBuffer[ 1 ] = '\0';
pName->szPath = pName->szBuffer;
iPos = 2; /* first free position after the slash */
}
else if( iSlashPos > 0 )
{
/* If we are after a drive letter let's keep the following backslash */
if( IS_PATH_SEP( ':' ) &&
( szFilename[ iSlashPos ] == ':' || szFilename[ iSlashPos - 1 ] == ':' ) )
{
/* path with separator -> d:\path\filename or d:path\filename */
memcpy( pName->szBuffer, szFilename, iSlashPos + 1 );
pName->szBuffer[ iSlashPos + 1 ] = '\0';
iPos = iSlashPos + 2; /* first free position after the slash */
}
else
{
/* path with separator -> path\filename */
memcpy( pName->szBuffer, szFilename, iSlashPos );
pName->szBuffer[ iSlashPos ] = '\0';
iPos = iSlashPos + 1; /* first free position after the slash */
}
pName->szName = pName->szBuffer + iPos;
memcpy( pName->szName, szFilename + iSlashPos + 1, iDotPos - iSlashPos - 1 );
pName->szName[ iDotPos - iSlashPos - 1 ] = '\x0';
pName->szPath = pName->szBuffer;
}
return pName;
iDotPos = iLen - 1;
while( iDotPos > iSlashPos && szFilename[ iDotPos ] != '.' )
--iDotPos;
if( ( iDotPos - iSlashPos ) > 1 )
{
/* the dot was found
* and there is at least one character between a slash and a dot
*/
if( iDotPos == iLen - 1 )
{
/* the dot is the last character - use it as extension name */
pName->szExtension = pName->szBuffer + iPos;
pName->szBuffer[ iPos++ ] = '.';
pName->szBuffer[ iPos++ ] = '\0';
}
else
{
pName->szExtension = pName->szBuffer + iPos;
/* copy rest of the string with terminating ZERO character */
memcpy( pName->szExtension, szFilename + iDotPos + 1, iLen - iDotPos );
iPos += iLen - iDotPos;
}
}
else
/* there is no dot in the filename or it is '.filename' */
iDotPos = iLen;
pName->szName = pName->szBuffer + iPos;
memcpy( pName->szName, szFilename + iSlashPos + 1, iDotPos - iSlashPos - 1 );
pName->szName[ iDotPos - iSlashPos - 1 ] = '\0';
return pName;
}
/* This function joins path, name and extension into a string with a filename */
char * hb_fsFNameMerge( char *szFileName, PHB_FNAME pFileName )
char * hb_fsFNameMerge( char * szFileName, PHB_FNAME pFileName )
{
if( pFileName->szPath && pFileName->szPath[ 0 ] )
{
/* we have not empty path specified */
int iLen = strlen(pFileName->szPath);
if( pFileName->szPath && pFileName->szPath[ 0 ] )
{
/* we have not empty path specified */
int iLen = strlen( pFileName->szPath );
strcpy( szFileName, pFileName->szPath );
strcpy( szFileName, pFileName->szPath );
/* if the path is a root directory then we don't need to add path separator */
if( !(IS_PATH_SEP(pFileName->szPath[ 0 ]) && pFileName->szPath[ 0 ] == '\x0') )
{
/* add the path separator only in cases:
* when a name doesn't start with it
* when the path doesn't end with it
*/
if( !( IS_PATH_SEP(pFileName->szName[ 0 ]) || IS_PATH_SEP(pFileName->szPath[ iLen-1 ]) ) )
/* if the path is a root directory then we don't need to add path separator */
if( !( IS_PATH_SEP( pFileName->szPath[ 0 ] ) && pFileName->szPath[ 0 ] == '\0' ) )
{
szFileName[ iLen++ ] = OS_PATH_DELIMITER;
szFileName[ iLen ] = '\x0';
/* add the path separator only in cases:
* when a name doesn't start with it
* when the path doesn't end with it
*/
if( !( IS_PATH_SEP( pFileName->szName[ 0 ] ) || IS_PATH_SEP( pFileName->szPath[ iLen-1 ] ) ) )
{
szFileName[ iLen++ ] = OS_PATH_DELIMITER;
szFileName[ iLen ] = '\0';
}
}
}
strcpy( szFileName+iLen, pFileName->szName );
}
else
strcpy( szFileName, pFileName->szName );
strcpy( szFileName + iLen, pFileName->szName );
}
else
strcpy( szFileName, pFileName->szName );
if( pFileName->szExtension )
{
int iLen = strlen(szFileName);
if( pFileName->szExtension )
{
int iLen = strlen( szFileName );
if( !(pFileName->szExtension[ 0 ] == '.' || szFileName[ iLen-1 ] == '.') )
{
/* add extension separator only when extansion doesn't contain it */
szFileName[ iLen++ ] = '.';
szFileName[ iLen ] = '\x0';
}
strcpy( szFileName+iLen, pFileName->szExtension );
}
if( !( pFileName->szExtension[ 0 ] == '.' || szFileName[ iLen-1 ] == '.') )
{
/* add extension separator only when extansion doesn't contain it */
szFileName[ iLen++ ] = '.';
szFileName[ iLen ] = '\0';
}
strcpy( szFileName + iLen, pFileName->szExtension );
}
return szFileName;
return szFileName;
}
void * hb_xgrab( ULONG ulSize ) /* allocates fixed memory, exits on failure */

View File

@@ -66,7 +66,7 @@ WORD hb_errLaunch( PHB_ITEM pError )
if( ! IS_BLOCK( &errorBlock ) )
hb_errInternal( 9999, "No ERRORBLOCK() for error", NULL, NULL );
/* Launch the error handler: "lResult := EVAL( bErrorBlock, oError )" */
/* Launch the error handler: "lResult := EVAL( ErrorBlock(), oError )" */
pBlock = hb_itemNew( NULL );
pObject = hb_itemNew( NULL );
@@ -82,22 +82,16 @@ WORD hb_errLaunch( PHB_ITEM pError )
/* Check results */
/* TODO: Determine if there was a BREAK in the error handler. */
if( FALSE )
if( hb_vmRequestQuery() == HB_QUIT_REQUESTED )
{
hb_itemRelease( pResult );
/* TODO: Detect sequence level properly */
if( FALSE )
{
/* TODO: Initiate a jump to the closest RECOVER statement */
wRetVal = E_BREAK;
}
else
{
/* TODO: QUIT correctly, without any message */
exit( 1 );
}
hb_errRelease( pError );
hb_vmQuit();
}
else if( hb_vmRequestQuery() == HB_BREAK_REQUESTED )
{
hb_itemRelease( pResult );
wRetVal = E_BREAK;
}
else
{
@@ -107,20 +101,15 @@ WORD hb_errLaunch( PHB_ITEM pError )
/* If the error block didn't return a logical value, */
/* or the canSubstitute flag has been set, consider it as a failure */
if( ! IS_LOGICAL( pResult ) ||
( uiFlags & EF_CANSUBSTITUTE ) )
{
if( ! IS_LOGICAL( pResult ) || ( uiFlags & EF_CANSUBSTITUTE ) )
bFailure = TRUE;
}
else
{
wRetVal = hb_itemGetL( pResult ) ? E_RETRY : E_DEFAULT;
if( ( wRetVal == E_DEFAULT && !( uiFlags & EF_CANDEFAULT ) ) ||
( wRetVal == E_RETRY && !( uiFlags & EF_CANRETRY ) ) )
{
bFailure = TRUE;
}
}
hb_itemRelease( pResult );
@@ -143,7 +132,7 @@ WORD hb_errLaunch( PHB_ITEM pError )
Since it this case the error handler will return the value
to be substituted */
/* NOTE: The item pointer returned should be hb_itemRelease()-d by the
caller. */
caller if it was not NULL. */
PHB_ITEM hb_errLaunchSubst( PHB_ITEM pError )
{
@@ -160,7 +149,7 @@ PHB_ITEM hb_errLaunchSubst( PHB_ITEM pError )
if( ! IS_BLOCK( &errorBlock ) )
hb_errInternal( 9999, "No ERRORBLOCK() for error", NULL, NULL );
/* Launch the error handler: "xResult := EVAL( bErrorBlock, oError )" */
/* Launch the error handler: "xResult := EVAL( ErrorBlock(), oError )" */
pBlock = hb_itemNew( NULL );
pObject = hb_itemNew( NULL );
@@ -176,23 +165,16 @@ PHB_ITEM hb_errLaunchSubst( PHB_ITEM pError )
/* Check results */
/* TODO: Determine if there was a BREAK in the error handler. */
if( FALSE )
if( hb_vmRequestQuery() == HB_QUIT_REQUESTED )
{
/* TODO: Detect sequence level properly */
if( FALSE )
{
/* TODO: Initiate a jump to the closest RECOVER statement */
/* QUESTION: Will Clipper return to the caller in this case ? */
}
else
{
hb_itemRelease( pResult );
pResult = NULL;
/* TODO: QUIT correctly, without any message */
exit( 1 );
}
hb_itemRelease( pResult );
hb_errRelease( pError );
hb_vmQuit();
}
else if( hb_vmRequestQuery() == HB_BREAK_REQUESTED )
{
hb_itemRelease( pResult );
pResult = NULL;
}
else
{
@@ -200,9 +182,7 @@ PHB_ITEM hb_errLaunchSubst( PHB_ITEM pError )
consider it as a failure. */
if( ! ( hb_errGetFlags( pError ) & EF_CANSUBSTITUTE ) )
{
hb_errInternal( 9999, "Error recovery failure", NULL, NULL );
}
}
}
else

View File

@@ -484,7 +484,7 @@ BOOL hb_fsLock ( FHANDLE hFileHandle, ULONG ulStart,
int iResult = 0;
#if defined(_MSC_VER)
ULONG ulPos;
ULONG ulOldPos;
#endif
#if defined(HAVE_POSIX_IO) && !defined(__GNUC__) && !defined(__IBMCPP__)
@@ -505,7 +505,7 @@ BOOL hb_fsLock ( FHANDLE hFileHandle, ULONG ulStart,
#if defined(_MSC_VER)
ulPos = hb_fsSeek( hFileHandle, ulStart, FS_SET );
ulOldPos = hb_fsSeek( hFileHandle, ulStart, FS_SET );
switch( uiMode )
{
@@ -517,7 +517,7 @@ BOOL hb_fsLock ( FHANDLE hFileHandle, ULONG ulStart,
iResult = locking( hFileHandle, _LK_UNLCK, ulLength );
}
hb_fsSeek( hFileHandle, ulPos, FS_SET );
hb_fsSeek( hFileHandle, ulOldPos, FS_SET );
#else
@@ -725,6 +725,7 @@ USHORT hb_fsIsDrv ( BYTE nDrive )
}
/* TODO: Implement hb_fsExtOpen */
FHANDLE hb_fsExtOpen( BYTE * pFilename, BYTE * pDefExt,
USHORT uiFlags, BYTE * pPaths, PHB_ITEM pError )
{
@@ -741,15 +742,11 @@ FHANDLE hb_fsExtOpen( BYTE * pFilename, BYTE * pDefExt,
HARBOUR HB_FOPEN( void )
{
if( ISCHAR( 1 ) )
{
hb_retni( hb_fsOpen( ( BYTE * ) hb_parc( 1 ),
ISNUM( 2 ) ? hb_parni( 2 ) : FO_READ ) );
}
else
{
/* NOTE: Undocumented but existing Clipper Run-time error */
hb_errRT_BASE( EG_ARG, 2021, NULL, "FOPEN" );
}
}
HARBOUR HB_FCREATE( void )
@@ -1024,10 +1021,10 @@ HARBOUR HB_W2BIN( void )
HB_I2BIN();
}
#define IS_PATH_SEP( c ) ( c == OS_PATH_DELIMITER )
#define IS_PATH_SEP( c ) ( strchr( OS_PATH_DELIMITER_LIST, ( c ) ) != NULL )
/* Split given filename into path, name and extension */
PHB_FNAME hb_fsFNameSplit( char *szFilename )
PHB_FNAME hb_fsFNameSplit( char * szFilename )
{
PHB_FNAME pName = ( PHB_FNAME ) hb_xgrab( sizeof( HB_FNAME ) );
@@ -1052,15 +1049,28 @@ PHB_FNAME hb_fsFNameSplit( char *szFilename )
pName->szBuffer[ 0 ] = OS_PATH_DELIMITER;
pName->szBuffer[ 1 ] = '\0';
pName->szPath = pName->szBuffer;
iPos = 2; /* first free position after the slash */
iPos = 2; /* first free position after the slash */
}
else if( iSlashPos > 0 )
{
/* path with separator -> path\filename */
memcpy( pName->szBuffer, szFilename, iSlashPos );
pName->szBuffer[ iSlashPos ] = '\0';
/* If we are after a drive letter let's keep the following backslash */
if( IS_PATH_SEP( ':' ) &&
( szFilename[ iSlashPos ] == ':' || szFilename[ iSlashPos - 1 ] == ':' ) )
{
/* path with separator -> d:\path\filename or d:path\filename */
memcpy( pName->szBuffer, szFilename, iSlashPos + 1 );
pName->szBuffer[ iSlashPos + 1 ] = '\0';
iPos = iSlashPos + 2; /* first free position after the slash */
}
else
{
/* path with separator -> path\filename */
memcpy( pName->szBuffer, szFilename, iSlashPos );
pName->szBuffer[ iSlashPos ] = '\0';
iPos = iSlashPos + 1; /* first free position after the slash */
}
pName->szPath = pName->szBuffer;
iPos = iSlashPos + 1; /* first free position after the slash */
}
iDotPos = iLen - 1;
@@ -1074,7 +1084,7 @@ PHB_FNAME hb_fsFNameSplit( char *szFilename )
*/
if( iDotPos == iLen - 1 )
{
/* the dot is the last character -use it as extension name */
/* the dot is the last character - use it as extension name */
pName->szExtension = pName->szBuffer + iPos;
pName->szBuffer[ iPos++ ] = '.';
pName->szBuffer[ iPos++ ] = '\0';
@@ -1099,7 +1109,7 @@ PHB_FNAME hb_fsFNameSplit( char *szFilename )
}
/* This function joins path, name and extension into a string with a filename */
char * hb_fsFNameMerge( char *szFileName, PHB_FNAME pFileName )
char * hb_fsFNameMerge( char * szFileName, PHB_FNAME pFileName )
{
if( pFileName->szPath && pFileName->szPath[ 0 ] )
{
@@ -1142,26 +1152,3 @@ char * hb_fsFNameMerge( char *szFileName, PHB_FNAME pFileName )
return szFileName;
}
/* TOFIX:
If you call pFileName = hb_fsFNameSplit( "C:FILE.EXT" ) the result is:
pFileName->szPath => (null) must be 'C:'
pFileName->szName => 'C:FILE' must be 'FILE'
pFileName->szExtension => '.EXT' Ok!
If you call pFileName = hb_fsFNameSplit( "C:\FILE.EXT" ) the result is:
pFileName->szPath => 'C:' must be 'C:\'
pFileName->szName => 'FILE' Ok!
pFileName->szExtension => '.EXT' Ok!
If you call pFileName = hb_fsFNameSplit( "\FILE.EXT" ) the result is:
pFileName->szPath => '\' Ok!
pFileName->szName => 'FILE' Ok!
pFileName->szExtension => '.EXT' Ok!
If you call pFileName = hb_fsFNameSplit( "C:\DIR\FILE.EXT" ) the result
is:
pFileName->szPath => 'C:\DIR' Ok!
pFileName->szName => 'FILE' Ok!
pFileName->szExtension => '.EXT' Ok!
*/

View File

@@ -42,7 +42,6 @@
#pragma inline
#include <dos.h>
#include <mouse.h>
#endif
#include "mouseapi.h"
@@ -200,7 +199,26 @@ BOOL hb_mouse_IsButtonPressed( int iButton )
{
/* TODO: */
HB_SYMBOL_UNUSED( iButton );
if( s_bPresent )
{
#ifdef BORLANDC
int iReturn = 0;
asm
{
mov ax, 5
int MOUSE_INTERRUPT
mov iReturn, bx
}
/* Convert the button number (1 -> x) to a bitmask and check */
/* TODO: Test if this works */
return ( ( 2 ** ( iButton - 1 ) ) && iReturn );
#else
return FALSE;
#endif
}
return FALSE;
}

View File

@@ -109,8 +109,6 @@ static LONG RecoverBase = 0;
/* Request for some action - stop processing of opcodes
*/
static WORD wActionRequest = 0;
#define HB_QUIT_REQUESTED 1 /* immediately quit the application */
#define HB_BREAK_REQUESTED 2 /* break to nearest RECOVER/END sequence */
/* uncomment it to trace the virtual machine activity */
/* #define bHB_DEBUG */
@@ -145,7 +143,7 @@ int main( int argc, char * argv[] )
#ifdef HARBOUR_OBJ_GENERATION
hb_vmProcessObjSymbols(); /* initialize Harbour generated OBJs symbols */
#endif
hb_vmRTSymbolsInit(); /* initialize symbol table with runtime support functions */
hb_vmSymbolInit_RT(); /* initialize symbol table with runtime support functions */
/* Call functions that initializes static variables
* Static variables have to be initialized before any INIT functions
@@ -171,9 +169,21 @@ int main( int argc, char * argv[] )
hb_vmPushString( argv[ i ], strlen( argv[ i ] ) );
hb_vmDo( argc - 1 ); /* invoke it with number of supplied parameters */
hb_vmQuit();
/* This point is never reached */
return 0;
}
void hb_vmQuit( void )
{
wActionRequest = 0; /* EXIT procedures should be processed */
hb_vmDoExitFunctions(); /* process defined EXIT functions */
while( stack.pPos > stack.pItems )
hb_stackPop();
hb_itemClear( &stack.Return );
hb_arrayRelease( &aStatics );
hb_itemClear( &errorBlock );
@@ -189,7 +199,7 @@ int main( int argc, char * argv[] )
HB_DEBUG( "Done!\n" );
return byErrorLevel;
exit( byErrorLevel );
}
void hb_vmExecute( BYTE * pCode, PHB_SYMB pSymbols )
@@ -903,9 +913,9 @@ void hb_vmArrayPut( void )
static void hb_vmDebuggerEndProc( void )
{
HB_ITEM it;
HB_ITEM item;
hb_itemCopy( &it, &stack.Return ); /* saves the previous returned value */
hb_itemCopy( &item, &stack.Return ); /* saves the previous returned value */
bDebugShowLines = FALSE;
hb_vmPushSymbol( hb_dynsymFind( "__DBGENTRY" )->pSymbol );
@@ -913,8 +923,8 @@ static void hb_vmDebuggerEndProc( void )
hb_vmDo( 0 );
bDebugShowLines = TRUE;
hb_itemCopy( &stack.Return, &it ); /* restores the previous returned value */
hb_itemClear( &it );
hb_itemCopy( &stack.Return, &item ); /* restores the previous returned value */
hb_itemClear( &item );
}
static void hb_vmDebuggerShowLine( WORD wLine ) /* makes the debugger shows a specific source code line */
@@ -1534,8 +1544,6 @@ void hb_vmNotEqual( void )
else if( pItem1->type != pItem2->type )
hb_errRT_BASE( EG_ARG, 1072, NULL, "<>" );
else
hb_vmPushLogical( TRUE );
}
@@ -2734,6 +2742,9 @@ HARBOUR HB_ERRORLEVEL(void)
{
BYTE byPrevValue = byErrorLevel;
/* NOTE: This should be ISNUM( 1 ), but it's sort of a Clipper bug that it
accepts other types also and consider them zero. */
if( hb_pcount() > 0 )
/* Only replace the error level if a parameter was passed */
byErrorLevel = hb_parni( 1 );
@@ -2778,6 +2789,11 @@ void hb_vmRequestBreak( PHB_ITEM pItem )
wActionRequest = HB_QUIT_REQUESTED;
}
WORD hb_vmRequestQuery( void )
{
return wActionRequest;
}
/* NOTE: This function should normally have a parameter count check. But
since in Harbour we cannot distinguish between BREAK() function and
the BREAK statement, because both generate a BREAK() function

View File

@@ -127,8 +127,8 @@ static HB_SYMB symbols[] = {
/* NOTE: The system symbol table with runtime functions HAVE TO be called
last */
void hb_vmRTSymbolsInit( void )
void hb_vmSymbolInit_RT( void )
{
hb_vmProcessSymbols( symbols, sizeof(symbols) / sizeof( HB_SYMB ) );
hb_vmProcessSymbols( symbols, sizeof( symbols ) / sizeof( HB_SYMB ) );
}

View File

@@ -74,6 +74,10 @@ FUNCTION Main()
OutSpec("FClose()" , FClose() )
OutSpec("FClose( fhnd )" , FClose( fhnd ) )
OutSpec("FClose( fhnd )" , FClose( fhnd ) )
OutSpec("FErase( 'NOT_HERE.$$$' )" , FErase( 'NOT_HERE.$$$' ) )
OutSpec("FErase( 1 )" , FErase( 1 ) )
OutSpec("FErase( 'NOT_HERE.$$$' )" , FErase( 'NOT_HERE.$$$' ) )
OutSpec("FRename( 'NOT_HERE.$$$', 'A' )" , FRename( 'NOT_HERE.$$$', 'A' ) )
OutSpec("File( cFileName )" , File( cFileName ) )