From ae751e58e9d908d17a731f3789673badf60730e4 Mon Sep 17 00:00:00 2001 From: Eddie Runia Date: Fri, 4 Jun 1999 16:28:05 +0000 Subject: [PATCH] see changelog --- harbour/ChangeLog | 6 ++++ harbour/include/pcode.h | 1 + harbour/source/compiler/harbour.y | 26 ++++++++++------- harbour/source/vm/hvm.c | 14 +++++++++ harbour/tests/broken/funcarr.prg | 16 ----------- harbour/tests/working/funcarr.prg | 48 +++++++++++++++++++++++++++++++ 6 files changed, 85 insertions(+), 26 deletions(-) delete mode 100644 harbour/tests/broken/funcarr.prg create mode 100644 harbour/tests/working/funcarr.prg diff --git a/harbour/ChangeLog b/harbour/ChangeLog index 902e512a44..8b219ffb3b 100644 --- a/harbour/ChangeLog +++ b/harbour/ChangeLog @@ -1,3 +1,9 @@ +19990604-17:15 CET Eddie Runia + * source/compiler/harbour.y; source/vm/hvm.c; include/pcode.h; + tests/working/funcarr.prg + Syntax for : + [] added + 19990604-11:45 CET Eddie Runia * source/rtl/classes.c _GetClassName() called by ClassName() diff --git a/harbour/include/pcode.h b/harbour/include/pcode.h index 1e10bbd50f..23824c7b25 100644 --- a/harbour/include/pcode.h +++ b/harbour/include/pcode.h @@ -29,6 +29,7 @@ typedef enum _DIVIDE, /* divides the latest two values on the stack, removing them and leaving there the result */ _DO, /* instructs the virtual machine to execute a function discarding its result */ _DUPLICATE, /* places a copy of the latest virtual machine stack value on to the stack */ + _DUPLTWO, /* places a copy of the latest two virtual machine stack value on to the stack */ _INC, /* increments the latest value on the virtual machine stack */ _INSTRING, /* checks if the second latest value on the stack is a substring of the latest one */ _JUMP, /* jumps to a relative offset */ diff --git a/harbour/source/compiler/harbour.y b/harbour/source/compiler/harbour.y index bac95ca952..7e18bc659d 100644 --- a/harbour/source/compiler/harbour.y +++ b/harbour/source/compiler/harbour.y @@ -509,11 +509,11 @@ Statement : ExecFlow Crlf {} | IDENTIFIER '=' Expression Crlf { PopId( $1 ); } | VarId ArrayIndex '=' Expression Crlf { GenPCode1( _ARRAYPUT ); GenPCode1( _POP ); } - | FunArrayCall '=' Expression Crlf { GenPCode1( _ARRAYPUT ); } + | FunArrayCall '=' Expression Crlf { GenPCode1( _ARRAYPUT ); GenPCode1( _POP ); } | IdSend IDENTIFIER '=' { Message( SetData( $2 ) ); } Expression Crlf { Function( 1 ); } | IdSend IDENTIFIER INASSIGN { Message( SetData( $2 ) ); } Expression Crlf { Function( 1 ); } - | ObjectData ArrayIndex '=' Expression Crlf {} - | ObjectMethod ArrayIndex '=' Expression Crlf {} + | ObjectData ArrayIndex '=' Expression Crlf { GenPCode1( _ARRAYPUT ); GenPCode1( _POP ); } + | ObjectMethod ArrayIndex '=' Expression Crlf { GenPCode1( _ARRAYPUT ); GenPCode1( _POP ); } | BREAK Crlf | BREAK Expression Crlf @@ -684,13 +684,13 @@ VarAssign : IDENTIFIER INASSIGN Expression { PopId( $1 ); PushId( $1 ); } | VarId ArrayIndex DIVEQ { DupPCode( $1 ); GenPCode1( _ARRAYAT ); } Expression { GenPCode1( _DIVIDE ); GenPCode1( _ARRAYPUT ); } | VarId ArrayIndex EXPEQ { DupPCode( $1 ); GenPCode1( _ARRAYAT ); } Expression { GenPCode1( _POWER ); GenPCode1( _ARRAYPUT ); } | VarId ArrayIndex MODEQ { DupPCode( $1 ); GenPCode1( _ARRAYAT ); } Expression { GenPCode1( _MODULUS ); GenPCode1( _ARRAYPUT ); } - | FunArrayCall INASSIGN Expression {} - | FunArrayCall PLUSEQ Expression {} - | FunArrayCall MINUSEQ Expression {} - | FunArrayCall MULTEQ Expression {} - | FunArrayCall DIVEQ Expression {} - | FunArrayCall EXPEQ Expression {} - | FunArrayCall MODEQ Expression {} + | FunArrayCall INASSIGN Expression { GenPCode1( _ARRAYPUT ); } + | FunArrayCall PLUSEQ { GenPCode1( _DUPLTWO ); GenPCode1( _ARRAYAT ); } Expression { GenPCode1( _PLUS ); GenPCode1( _ARRAYPUT ); } + | FunArrayCall MINUSEQ { GenPCode1( _DUPLTWO ); GenPCode1( _ARRAYAT ); } Expression { GenPCode1( _MINUS ); GenPCode1( _ARRAYPUT ); } + | FunArrayCall MULTEQ { GenPCode1( _DUPLTWO ); GenPCode1( _ARRAYAT ); } Expression { GenPCode1( _MULT ); GenPCode1( _ARRAYPUT ); } + | FunArrayCall DIVEQ { GenPCode1( _DUPLTWO ); GenPCode1( _ARRAYAT ); } Expression { GenPCode1( _DIVIDE ); GenPCode1( _ARRAYPUT ); } + | FunArrayCall EXPEQ { GenPCode1( _DUPLTWO ); GenPCode1( _ARRAYAT ); } Expression { GenPCode1( _POWER ); GenPCode1( _ARRAYPUT ); } + | FunArrayCall MODEQ { GenPCode1( _DUPLTWO ); GenPCode1( _ARRAYAT ); } Expression { GenPCode1( _MODULUS ); GenPCode1( _ARRAYPUT ); } | ObjectData PLUSEQ Expression {} | ObjectData MINUSEQ Expression {} | ObjectData MULTEQ Expression {} @@ -1974,6 +1974,11 @@ void GenCCode( char *szFileName, char *szName ) /* generates the C languag lPCodePos++; break; + case _DUPLTWO: + fprintf( yyc, " _DUPLTWO,\n" ); + lPCodePos++; + break; + case _EQUAL: fprintf( yyc, " _EQUAL,\n" ); lPCodePos++; @@ -3636,6 +3641,7 @@ void GenPortObj( char *szFileName, char *szName ) case _DEC: case _DIVIDE: case _DUPLICATE: + case _DUPLTWO: case _EQUAL: case _EXACTLYEQUAL: case _FALSE: diff --git a/harbour/source/vm/hvm.c b/harbour/source/vm/hvm.c index 0038b35a6e..f3edb196f2 100644 --- a/harbour/source/vm/hvm.c +++ b/harbour/source/vm/hvm.c @@ -43,6 +43,7 @@ void Div( void ); /* divides the latest two values on the stack, rem void Do( WORD WParams ); /* invoke the virtual machine */ HARBOUR DoBlock( void ); /* executes a codeblock */ void Duplicate( void ); /* duplicates the latest value on the stack */ +void DuplTwo( void ); /* duplicates the latest two value on the stack */ void EndBlock( void ); /* copies the last codeblock pushed value into the return value */ void Equal( BOOL bExact ); /* checks if the two latest values on the stack are equal, removes both and leaves result */ void ForTest( void ); /* test for end condition of for */ @@ -295,6 +296,11 @@ void VirtualMachine( PBYTE pCode, PSYMBOL pSymbols ) w++; break; + case _DUPLTWO: + DuplTwo(); + w++; + break; + case _ENDBLOCK: EndBlock(); HBDEBUG( "EndProc\n" ); @@ -759,6 +765,14 @@ void Duplicate( void ) StackPush(); } +void DuplTwo( void ) +{ + ItemCopy( stack.pPos, stack.pPos - 2 ); + StackPush(); + ItemCopy( stack.pPos, stack.pPos - 2 ); + StackPush(); +} + HARBOUR EVAL( void ) { PITEM pBlock = _param( 1, IT_BLOCK ); diff --git a/harbour/tests/broken/funcarr.prg b/harbour/tests/broken/funcarr.prg deleted file mode 100644 index 2a8629418e..0000000000 --- a/harbour/tests/broken/funcarr.prg +++ /dev/null @@ -1,16 +0,0 @@ -Function Main - - // Does NOT work ??? - QOut( aFunc()[1] ) - - // Does work - a := aFunc() - QOut( a[1] ) - -return NIL - -Function aFunc() - - local aArray := { [Test] } - -return aArray diff --git a/harbour/tests/working/funcarr.prg b/harbour/tests/working/funcarr.prg new file mode 100644 index 0000000000..11d1baaead --- /dev/null +++ b/harbour/tests/working/funcarr.prg @@ -0,0 +1,48 @@ +// +// Function Array syntax test +// + +Function Main + + local a + + QOut( aFunc()[1] ) + + a := aFunc() + QOut( a[1] ) + + aFunc()[1] := "Something different" + QOut( aFunc()[1] ) + + aFunc()[1] := 4 + QOut( aFunc()[1] ) + + aFunc()[1] += 1 + QOut( aFunc()[1] ) + + aFunc()[1] -= 1 + QOut( aFunc()[1] ) + + aFunc()[1] *= 2 + QOut( aFunc()[1] ) + + aFunc()[1] /= 2 + QOut( aFunc()[1] ) + + aFunc()[1] %= 5 + QOut( aFunc()[1] ) + + aFunc()[1] ^= 3 + QOut( aFunc()[1] ) + + QOut( "Global stack" ) + HBDebug( __aGlobalStack() ) // Please note a is a reference to aArray ! + QOut( "Statics") + HBDebug( __aStatic() ) +return NIL + +Function aFunc() + + static aArray := { [Test] } + +return aArray