From 30d4efb954fc40be10a783bf41c33116cd0fee71 Mon Sep 17 00:00:00 2001 From: Przemyslaw Czerpak Date: Sun, 3 Sep 2006 17:01:55 +0000 Subject: [PATCH] 2006-09-03 18:55 UTC+0200 Przemyslaw Czerpak (druzus/at/priv.onet.pl) * harbour/include/hbapicls.h * harbour/source/vm/classes.c * harbour/source/vm/hvm.c * harbour/tests/overload.prg + added support for overloading [] in assignment operation --- harbour/ChangeLog | 7 ++ harbour/include/hbapicls.h | 2 +- harbour/source/vm/classes.c | 76 ++++++++------ harbour/source/vm/hvm.c | 196 +++++++++++++++++++++--------------- harbour/tests/overload.prg | 11 +- 5 files changed, 174 insertions(+), 118 deletions(-) diff --git a/harbour/ChangeLog b/harbour/ChangeLog index d37bcac09e..c1104305c0 100644 --- a/harbour/ChangeLog +++ b/harbour/ChangeLog @@ -8,6 +8,13 @@ 2002-12-01 13:30 UTC+0100 Foo Bar */ + * harbour/source/vm/classes.c + * stronger parameters validation and fixed some possible problems + in hb_objGetMethod() + + added support for assigning enumerator value by: + :__enumValue() + and enumerator index by: + :__enumIndex() It's a work in progress - please do not create any code which may need such functionality yet + harbour/ChangeLog.015 diff --git a/harbour/include/hbapicls.h b/harbour/include/hbapicls.h index f8d3b28a7a..31ddf71e22 100644 --- a/harbour/include/hbapicls.h +++ b/harbour/include/hbapicls.h @@ -100,7 +100,7 @@ extern PHB_SYMB hb_objGetMethod( PHB_ITEM pObject, PHB_SYMB pSymMsg, PHB_STACK #endif extern BOOL hb_objHasOperator( PHB_ITEM pObject, USHORT uiOperator ); -extern BOOL hb_objOperatorCall( USHORT uiOperator, HB_ITEM_PTR pResult, PHB_ITEM pObject, PHB_ITEM pMsgArg ); +extern BOOL hb_objOperatorCall( USHORT uiOperator, HB_ITEM_PTR pResult, PHB_ITEM pObject, PHB_ITEM pMsgArg1, PHB_ITEM pMsgArg2 ); extern USHORT hb_objGetClass( PHB_ITEM pItem ); /* get object class handle */ extern char * hb_objGetClsName( PHB_ITEM pObject ); /* retrieves an object class name */ diff --git a/harbour/source/vm/classes.c b/harbour/source/vm/classes.c index da919a33d0..23459ba6e7 100644 --- a/harbour/source/vm/classes.c +++ b/harbour/source/vm/classes.c @@ -427,6 +427,35 @@ static PMETHOD hb_clsAllocMsg( PCLASS pClass, PHB_DYNS pMsg ) return NULL; } +static void hb_clsFreeMsg( PCLASS pClass, PHB_DYNS pMsg ) +{ + PMETHOD pMethod = pClass->pMethods + hb_clsMsgBucket( pMsg, pClass->uiHashKey - 1 ); + USHORT uiBucket = BUCKETSIZE; + + do + { + if( ! pMethod->pMessage || pMethod->pMessage == pMsg ) + { + if( pMethod->pFuncSym == &s___msgEvalInline ) + { /* INLINE method deleted, delete INLINE block */ + hb_itemClear( hb_arrayGetItemPtr( pClass->pInlines, + pMethod->uiData ) ); + } + /* Move messages */ + while( --uiBucket ) + { + memcpy( pMethod, pMethod + 1, sizeof( METHOD ) ); + pMethod++; + } + memset( pMethod, 0, sizeof( METHOD ) ); + pClass->uiMethods--; /* Decrease number of messages */ + return; + } + ++pMethod; + } + while( --uiBucket ); +} + static void hb_clsAddInitValue( PCLASS pClass, PHB_ITEM pItem, USHORT uiType, USHORT uiData ) { @@ -1137,10 +1166,10 @@ BOOL hb_objHasOperator( PHB_ITEM pObject, USHORT uiOperator ) * Function return TRUE when object class overloads given operator * and FALSE otherwise. [druzus] */ -BOOL hb_objOperatorCall( USHORT uiOperator, HB_ITEM_PTR pResult, - PHB_ITEM pObject, PHB_ITEM pMsgArg ) +BOOL hb_objOperatorCall( USHORT uiOperator, HB_ITEM_PTR pResult, PHB_ITEM pObject, + PHB_ITEM pMsgArg1, PHB_ITEM pMsgArg2 ) { - HB_TRACE(HB_TR_DEBUG, ("hb_objOperatorCall(%hu,%p,%p,%p)", uiOperator, pResult, pObject, pMsgArg)); + HB_TRACE(HB_TR_DEBUG, ("hb_objOperatorCall(%hu,%p,%p,%p,%p)", uiOperator, pResult, pObject, pMsgArg1, pMsgArg2)); if( hb_objHasOperator( pObject, uiOperator ) ) { @@ -1150,16 +1179,22 @@ BOOL hb_objOperatorCall( USHORT uiOperator, HB_ITEM_PTR pResult, hb_itemClear( hb_stackReturnItem() ); else hb_stackReturnItem()->type = HB_IT_NIL; - if( pMsgArg ) + if( pMsgArg1 ) { - hb_vmPush( pMsgArg ); - hb_vmSend( 1 ); + hb_vmPush( pMsgArg1 ); + if( pMsgArg2 ) + { + hb_vmPush( pMsgArg2 ); + hb_vmSend( 2 ); + } + else + hb_vmSend( 1 ); } else hb_vmSend( 0 ); /* store the return value */ - hb_itemCopy( pResult, hb_stackReturnItem() ); + hb_itemMove( pResult, hb_stackReturnItem() ); return TRUE; } return FALSE; @@ -1823,32 +1858,7 @@ HB_FUNC( __CLSDELMSG ) PHB_DYNS pMsg = hb_dynsymFindName( pString->item.asString.value ); if( pMsg ) - { - PCLASS pClass = s_pClasses + ( uiClass - 1 ); - PMETHOD pMethod = hb_clsFindMsg( pClass, pMsg ); - - if( pMethod ) - { - PHB_SYMB pFuncSym = pMethod->pFuncSym; - USHORT uiPos; - - if( pFuncSym == &s___msgEvalInline ) - { /* INLINE method deleted, delete INLINE block */ - hb_itemClear( hb_arrayGetItemPtr( pClass->pInlines, - pMethod->uiData ) ); - } - /* Move messages */ - uiPos = ( USHORT ) ( pMethod - pClass->pMethods ) & BUCKETMASK; - - while( uiPos++ < BUCKETSIZE && pMethod->pMessage ) - { - memcpy( pMethod, pMethod + 1, sizeof( METHOD ) ); - pMethod++; - } - memset( pMethod, 0, sizeof( METHOD ) ); - pClass->uiMethods--; /* Decrease number messages */ - } - } + hb_clsFreeMsg( s_pClasses + ( uiClass - 1 ), pMsg ); } } diff --git a/harbour/source/vm/hvm.c b/harbour/source/vm/hvm.c index 94e38e85c8..ecaed8ba80 100644 --- a/harbour/source/vm/hvm.c +++ b/harbour/source/vm/hvm.c @@ -1901,7 +1901,7 @@ static void hb_vmAddInt( HB_ITEM_PTR pResult, LONG lAdd ) else if( hb_objHasOperator( pResult, HB_OO_OP_PLUS ) ) { hb_vmPushLong( lAdd ); - hb_objOperatorCall( HB_OO_OP_PLUS, pResult, pResult, hb_stackItemFromTop( -1 ) ); + hb_objOperatorCall( HB_OO_OP_PLUS, pResult, pResult, hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); return; } @@ -2094,7 +2094,7 @@ static void hb_vmPlus( HB_ITEM_PTR pResult, HB_ITEM_PTR pItem1, HB_ITEM_PTR pIte { hb_itemPutDL( pResult, hb_itemGetNL( pItem1 ) + hb_itemGetDL( pItem2 ) ); } - else if( ! hb_objOperatorCall( HB_OO_OP_PLUS, pResult, pItem1, pItem2 ) ) + else if( ! hb_objOperatorCall( HB_OO_OP_PLUS, pResult, pItem1, pItem2, NULL ) ) { PHB_ITEM pSubst = hb_errRT_BASE_Subst( EG_ARG, 1081, NULL, "+", 2, pItem1, pItem2 ); @@ -2166,7 +2166,7 @@ static void hb_vmMinus( HB_ITEM_PTR pResult, HB_ITEM_PTR pItem1, HB_ITEM_PTR pIt else hb_errRT_BASE( EG_STROVERFLOW, 1210, NULL, "-", 2, pItem1, pItem2 ); } - else if( ! hb_objOperatorCall( HB_OO_OP_MINUS, pResult, pItem1, pItem2 ) ) + else if( ! hb_objOperatorCall( HB_OO_OP_MINUS, pResult, pItem1, pItem2, NULL ) ) { PHB_ITEM pSubst = hb_errRT_BASE_Subst( EG_ARG, 1082, NULL, "-", 2, pItem1, pItem2 ); @@ -2205,7 +2205,7 @@ static void hb_vmMult( HB_ITEM_PTR pResult, HB_ITEM_PTR pItem1, HB_ITEM_PTR pIte hb_itemPutNumType( pResult, dNumber1 * dNumber2, iDec1 + iDec2, iType1, iType2 ); } - else if( ! hb_objOperatorCall( HB_OO_OP_MULT, pResult, pItem1, pItem2 ) ) + else if( ! hb_objOperatorCall( HB_OO_OP_MULT, pResult, pItem1, pItem2, NULL ) ) { PHB_ITEM pSubst = hb_errRT_BASE_Subst( EG_ARG, 1083, NULL, "*", 2, pItem1, pItem2 ); @@ -2277,7 +2277,7 @@ static void hb_vmDivide( HB_ITEM_PTR pResult, HB_ITEM_PTR pItem1, HB_ITEM_PTR pI hb_itemPutNDDec( pResult, dNumber1 / dDivisor, hb_set.HB_SET_DECIMALS ); } } - else if( ! hb_objOperatorCall( HB_OO_OP_DIVIDE, pResult, pItem1, pItem2 ) ) + else if( ! hb_objOperatorCall( HB_OO_OP_DIVIDE, pResult, pItem1, pItem2, NULL ) ) { PHB_ITEM pSubst = hb_errRT_BASE_Subst( EG_ARG, 1084, NULL, "/", 2, pItem1, pItem2 ); @@ -2357,7 +2357,7 @@ static void hb_vmModulus( void ) hb_vmPushDouble( fmod( hb_vmPopNumber(), dDivisor ), hb_set.HB_SET_DECIMALS ); } } - else if( hb_objOperatorCall( HB_OO_OP_MOD, pItem1, pItem1, pItem2 ) ) + else if( hb_objOperatorCall( HB_OO_OP_MOD, pItem1, pItem1, pItem2, NULL ) ) hb_stackPop(); else @@ -2393,7 +2393,7 @@ static void hb_vmPower( void ) with the SET number of decimal places. */ hb_vmPushDouble( pow( d1, d2 ), hb_set.HB_SET_DECIMALS ); } - else if( hb_objOperatorCall( HB_OO_OP_POWER, pItem1, pItem1, pItem2 ) ) + else if( hb_objOperatorCall( HB_OO_OP_POWER, pItem1, pItem1, pItem2, NULL ) ) hb_stackPop(); else @@ -2444,7 +2444,7 @@ static void hb_vmInc( void ) pItem->item.asDouble.value++; pItem->item.asDouble.length = HB_DBL_LENGTH( pItem->item.asDouble.value ); } - else if( ! hb_objOperatorCall( HB_OO_OP_INC, pItem, pItem, NULL ) ) + else if( ! hb_objOperatorCall( HB_OO_OP_INC, pItem, pItem, NULL, NULL ) ) { PHB_ITEM pResult = hb_errRT_BASE_Subst( EG_ARG, 1086, NULL, "++", 1, pItem ); @@ -2491,7 +2491,7 @@ static void hb_vmDec( void ) pItem->item.asDouble.value--; pItem->item.asDouble.length = HB_DBL_LENGTH( pItem->item.asDouble.value ); } - else if( ! hb_objOperatorCall( HB_OO_OP_DEC, pItem, pItem, NULL ) ) + else if( ! hb_objOperatorCall( HB_OO_OP_DEC, pItem, pItem, NULL, NULL ) ) { PHB_ITEM pResult = hb_errRT_BASE_Subst( EG_ARG, 1087, NULL, "--", 1, pItem ); @@ -2584,7 +2584,7 @@ static void hb_vmEqual( BOOL bExact ) hb_vmPushLogical( bResult ); } else if( hb_objOperatorCall( bExact ? HB_OO_OP_EXACTEQUAL : HB_OO_OP_EQUAL, - pItem1, pItem1, pItem2 ) ) + pItem1, pItem1, pItem2, NULL ) ) hb_stackPop(); else { @@ -2651,7 +2651,7 @@ static void hb_vmNotEqual( void ) hb_stackPop(); hb_vmPushLogical( fValue ); } - else if( hb_objOperatorCall( HB_OO_OP_NOTEQUAL, pItem1, pItem1, pItem2 ) ) + else if( hb_objOperatorCall( HB_OO_OP_NOTEQUAL, pItem1, pItem1, pItem2, NULL ) ) hb_stackPop(); else { @@ -2708,7 +2708,7 @@ static void hb_vmLess( void ) BOOL bLogical1 = hb_vmPopLogical(); hb_vmPushLogical( bLogical1 < bLogical2 ); } - else if( hb_objOperatorCall( HB_OO_OP_LESS, pItem1, pItem1, pItem2 ) ) + else if( hb_objOperatorCall( HB_OO_OP_LESS, pItem1, pItem1, pItem2, NULL ) ) hb_stackPop(); else @@ -2766,7 +2766,7 @@ static void hb_vmLessEqual( void ) BOOL bLogical1 = hb_vmPopLogical(); hb_vmPushLogical( bLogical1 <= bLogical2 ); } - else if( hb_objOperatorCall( HB_OO_OP_LESSEQUAL, pItem1, pItem1, pItem2 ) ) + else if( hb_objOperatorCall( HB_OO_OP_LESSEQUAL, pItem1, pItem1, pItem2, NULL ) ) hb_stackPop(); else @@ -2824,7 +2824,7 @@ static void hb_vmGreater( void ) BOOL bLogical1 = hb_vmPopLogical(); hb_vmPushLogical( bLogical1 > bLogical2 ); } - else if( hb_objOperatorCall( HB_OO_OP_GREATER, pItem1, pItem1, pItem2 ) ) + else if( hb_objOperatorCall( HB_OO_OP_GREATER, pItem1, pItem1, pItem2, NULL ) ) hb_stackPop(); else @@ -2882,7 +2882,7 @@ static void hb_vmGreaterEqual( void ) BOOL bLogical1 = hb_vmPopLogical(); hb_vmPushLogical( bLogical1 >= bLogical2 ); } - else if( hb_objOperatorCall( HB_OO_OP_GREATEREQUAL, pItem1, pItem1, pItem2 ) ) + else if( hb_objOperatorCall( HB_OO_OP_GREATEREQUAL, pItem1, pItem1, pItem2, NULL ) ) hb_stackPop(); else @@ -2917,7 +2917,7 @@ static void hb_vmInstring( void ) hb_stackPop(); hb_vmPushLogical( bResult ); } - else if( hb_objOperatorCall( HB_OO_OP_INSTRING, pItem1, pItem1, pItem2 ) ) + else if( hb_objOperatorCall( HB_OO_OP_INSTRING, pItem1, pItem1, pItem2, NULL ) ) hb_stackPop(); else @@ -3306,7 +3306,7 @@ static void hb_vmNot( void ) if( HB_IS_LOGICAL( pItem ) ) pItem->item.asLogical.value = ! pItem->item.asLogical.value; - else if( ! hb_objOperatorCall( HB_OO_OP_NOT, pItem, pItem, NULL ) ) + else if( ! hb_objOperatorCall( HB_OO_OP_NOT, pItem, pItem, NULL, NULL ) ) { PHB_ITEM pResult = hb_errRT_BASE_Subst( EG_ARG, 1077, NULL, ".NOT.", 1, pItem ); @@ -3335,7 +3335,7 @@ static void hb_vmAnd( void ) pItem2->type = HB_IT_NIL; hb_stackDec(); } - else if( hb_objOperatorCall( HB_OO_OP_AND, pItem1, pItem1, pItem2 ) ) + else if( hb_objOperatorCall( HB_OO_OP_AND, pItem1, pItem1, pItem2, NULL ) ) hb_stackPop(); else @@ -3368,7 +3368,7 @@ static void hb_vmOr( void ) pItem2->type = HB_IT_NIL; hb_stackDec(); } - else if( hb_objOperatorCall( HB_OO_OP_OR, pItem1, pItem1, pItem2 ) ) + else if( hb_objOperatorCall( HB_OO_OP_OR, pItem1, pItem1, pItem2, NULL ) ) hb_stackPop(); else @@ -3421,28 +3421,10 @@ static void hb_vmArrayPush( void ) return; } -/* #ifndef HB_C52_STRICT */ - if( (hb_vmFlagEnabled(HB_VMFLAG_ARRSTR)) && (HB_IS_STRING( pArray )) ) - { - BYTE b = 0; - - if( ulIndex > 0 && ulIndex <= pArray->item.asString.length ) - b = ( BYTE ) pArray->item.asString.value[ ulIndex - 1 ]; - else - hb_errRT_BASE( EG_BOUND, 1132, NULL, hb_langDGetErrorDesc( EG_ARRACCESS ), - 2, pArray, pIndex ); - - hb_itemPutNI( pArray, b ); - hb_stackPop(); - return; - } -/* #endif */ - - if( HB_IS_ARRAY( pArray ) ) { if( HB_IS_OBJECT( pArray ) && - hb_objOperatorCall( HB_OO_OP_ARRAYINDEX, pArray, pArray, pIndex ) ) + hb_objOperatorCall( HB_OO_OP_ARRAYINDEX, pArray, pArray, pIndex, NULL ) ) { hb_stackPop(); return; @@ -3471,7 +3453,23 @@ static void hb_vmArrayPush( void ) else hb_errRT_BASE( EG_BOUND, 1132, NULL, hb_langDGetErrorDesc( EG_ARRACCESS ), 2, pArray, pIndex ); } - else if( hb_objOperatorCall( HB_OO_OP_ARRAYINDEX, pArray, pArray, pIndex ) ) +/* #ifndef HB_C52_STRICT */ + else if( HB_IS_STRING( pArray ) && hb_vmFlagEnabled( HB_VMFLAG_ARRSTR ) ) + { + BYTE b = 0; + + if( ulIndex > 0 && ulIndex <= pArray->item.asString.length ) + b = ( BYTE ) pArray->item.asString.value[ ulIndex - 1 ]; + else + hb_errRT_BASE( EG_BOUND, 1132, NULL, hb_langDGetErrorDesc( EG_ARRACCESS ), + 2, pArray, pIndex ); + + hb_itemPutNI( pArray, b ); + hb_stackPop(); + return; + } +/* #endif */ + else if( hb_objOperatorCall( HB_OO_OP_ARRAYINDEX, pArray, pArray, pIndex, NULL ) ) hb_stackPop(); else @@ -3508,6 +3506,15 @@ static void hb_vmArrayPop( void ) if( HB_IS_ARRAY( pArray ) ) { + if( HB_IS_OBJECT( pArray ) && + hb_objOperatorCall( HB_OO_OP_ARRAYINDEX, pArray, pArray, pIndex, pValue ) ) + { + hb_stackPop(); + hb_stackPop(); + hb_stackPop(); + return; + } + if( ulIndex > 0 && ulIndex <= pArray->item.asArray.value->ulLen ) { pValue->type &= ~HB_IT_MEMOFLAG; @@ -3520,16 +3527,16 @@ static void hb_vmArrayPop( void ) hb_errRT_BASE( EG_BOUND, 1133, NULL, hb_langDGetErrorDesc( EG_ARRASSIGN ), 1, pIndex ); } /* #ifndef HB_C52_STRICT */ - else if( hb_vmFlagEnabled( HB_VMFLAG_ARRSTR ) && HB_IS_STRING( pArray ) ) + else if( HB_IS_STRING( pArray ) && hb_vmFlagEnabled( HB_VMFLAG_ARRSTR ) ) { if( ulIndex > 0 && ulIndex <= pArray->item.asString.length ) { if( pArray->item.asString.length == 1 ) - hb_itemPutCL( pArray, hb_vm_acAscii[ ( BYTE ) hb_itemGetNI( pValue ) ], 1 ); + hb_itemPutCL( pArray, hb_vm_acAscii[ ( unsigned char ) hb_itemGetNI( pValue ) ], 1 ); else { hb_itemUnShareString( pArray ); - pArray->item.asString.value[ ulIndex - 1 ] = hb_itemGetNI( pValue ); + pArray->item.asString.value[ ulIndex - 1 ] = ( char ) hb_itemGetNI( pValue ); } hb_stackPop(); @@ -3541,7 +3548,13 @@ static void hb_vmArrayPop( void ) 2, pArray, pIndex ); } /* #endif */ - + else if( hb_objOperatorCall( HB_OO_OP_ARRAYINDEX, pArray, pArray, pIndex, pValue ) ) + { + hb_stackPop(); + hb_stackPop(); + hb_stackPop(); + return; + } else hb_errRT_BASE( EG_ARG, 1069, NULL, hb_langDGetErrorDesc( EG_ARRASSIGN ), 1, pIndex ); } @@ -5148,7 +5161,7 @@ static void hb_vmPopLocal( SHORT iLocal ) } if( HB_IS_OBJECT( pLocal ) && - hb_objOperatorCall( HB_OO_OP_ASSIGN, pLocal, pLocal, pVal ) ) + hb_objOperatorCall( HB_OO_OP_ASSIGN, pLocal, pLocal, pVal, NULL ) ) { hb_stackPop(); return; @@ -5175,7 +5188,7 @@ static void hb_vmPopStatic( USHORT uiStatic ) pStatic = hb_itemUnRef( pStatic ); if( HB_IS_OBJECT( pStatic ) && - hb_objOperatorCall( HB_OO_OP_ASSIGN, pStatic, pStatic, pVal ) ) + hb_objOperatorCall( HB_OO_OP_ASSIGN, pStatic, pStatic, pVal, NULL ) ) { hb_stackPop(); return; @@ -6397,7 +6410,7 @@ HB_EXPORT void hb_xvmLocalSetInt( int iLocal, LONG lValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_ASSIGN, pLocal, pLocal, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); } else @@ -6580,7 +6593,7 @@ HB_EXPORT BOOL hb_xvmEqualInt( LONG lValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_EQUAL, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); } else @@ -6626,7 +6639,7 @@ HB_EXPORT BOOL hb_xvmEqualIntIs( LONG lValue, BOOL * pfValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_EQUAL, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); return hb_xvmPopLogical( pfValue ); } @@ -6685,7 +6698,7 @@ HB_EXPORT BOOL hb_xvmNotEqualInt( LONG lValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_NOTEQUAL, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); } else @@ -6731,7 +6744,7 @@ HB_EXPORT BOOL hb_xvmNotEqualIntIs( LONG lValue, BOOL * pfValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_NOTEQUAL, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); return hb_xvmPopLogical( pfValue ); } @@ -6785,7 +6798,7 @@ HB_EXPORT BOOL hb_xvmLessThenInt( LONG lValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_LESS, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); } else @@ -6826,7 +6839,7 @@ HB_EXPORT BOOL hb_xvmLessThenIntIs( LONG lValue, BOOL * pfValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_LESS, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); return hb_xvmPopLogical( pfValue ); } @@ -6880,7 +6893,7 @@ HB_EXPORT BOOL hb_xvmLessEqualThenInt( LONG lValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_LESSEQUAL, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); } else @@ -6921,7 +6934,7 @@ HB_EXPORT BOOL hb_xvmLessEqualThenIntIs( LONG lValue, BOOL * pfValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_LESSEQUAL, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); return hb_xvmPopLogical( pfValue ); } @@ -6975,7 +6988,7 @@ HB_EXPORT BOOL hb_xvmGreaterThenInt( LONG lValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_GREATER, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); } else @@ -7016,7 +7029,7 @@ HB_EXPORT BOOL hb_xvmGreaterThenIntIs( LONG lValue, BOOL * pfValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_GREATER, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); return hb_xvmPopLogical( pfValue ); } @@ -7070,7 +7083,7 @@ HB_EXPORT BOOL hb_xvmGreaterEqualThenInt( LONG lValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_GREATEREQUAL, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); } else @@ -7111,7 +7124,7 @@ HB_EXPORT BOOL hb_xvmGreaterEqualThenIntIs( LONG lValue, BOOL * pfValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_GREATEREQUAL, pItem, pItem, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); return hb_xvmPopLogical( pfValue ); } @@ -7242,7 +7255,7 @@ HB_EXPORT BOOL hb_xvmMultByInt( LONG lValue ) { hb_vmPushLong( lValue ); hb_objOperatorCall( HB_OO_OP_MULT, pValue, pValue, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); } else @@ -7330,7 +7343,7 @@ HB_EXPORT BOOL hb_xvmDivideByInt( LONG lDivisor ) { hb_vmPushLong( lDivisor ); hb_objOperatorCall( HB_OO_OP_DIVIDE, pValue, pValue, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); } else @@ -7434,33 +7447,13 @@ static void hb_vmArrayItemPush( ULONG ulIndex ) pArray = hb_stackItemFromTop( -1 ); -/* #ifndef HB_C52_STRICT */ - if( (hb_vmFlagEnabled(HB_VMFLAG_ARRSTR)) && (HB_IS_STRING( pArray )) ) - { - BYTE b = 0; - - if( ulIndex > 0 && ulIndex <= pArray->item.asString.length ) - b = pArray->item.asString.value[ ulIndex - 1 ]; - else - { - hb_vmPushNumInt( ulIndex ); - hb_errRT_BASE( EG_BOUND, 1132, NULL, hb_langDGetErrorDesc( EG_ARRACCESS ), - 2, pArray, hb_stackItemFromTop( -1 ) ); - hb_stackPop(); - } - hb_stackPop(); - hb_vmPushInteger( b ); - return; - } -/* #endif */ - if( HB_IS_ARRAY( pArray ) ) { if( HB_IS_OBJECT( pArray ) && hb_objHasOperator( pArray, HB_OO_OP_ARRAYINDEX ) ) { hb_vmPushNumInt( ulIndex ); hb_objOperatorCall( HB_OO_OP_ARRAYINDEX, pArray, pArray, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); return; } @@ -7492,11 +7485,30 @@ static void hb_vmArrayItemPush( ULONG ulIndex ) hb_errRT_BASE( EG_BOUND, 1132, NULL, hb_langDGetErrorDesc( EG_ARRACCESS ), 2, pArray, hb_stackItemFromTop( -1 ) ); } } +/* #ifndef HB_C52_STRICT */ + else if( HB_IS_STRING( pArray ) && hb_vmFlagEnabled( HB_VMFLAG_ARRSTR ) ) + { + BYTE b = 0; + + if( ulIndex > 0 && ulIndex <= pArray->item.asString.length ) + b = pArray->item.asString.value[ ulIndex - 1 ]; + else + { + hb_vmPushNumInt( ulIndex ); + hb_errRT_BASE( EG_BOUND, 1132, NULL, hb_langDGetErrorDesc( EG_ARRACCESS ), + 2, pArray, hb_stackItemFromTop( -1 ) ); + hb_stackPop(); + } + hb_stackPop(); + hb_vmPushInteger( b ); + return; + } +/* #endif */ else if( hb_objHasOperator( pArray, HB_OO_OP_ARRAYINDEX ) ) { hb_vmPushNumInt( ulIndex ); hb_objOperatorCall( HB_OO_OP_ARRAYINDEX, pArray, pArray, - hb_stackItemFromTop( -1 ) ); + hb_stackItemFromTop( -1 ), NULL ); hb_stackPop(); } else @@ -7521,6 +7533,17 @@ static void hb_vmArrayItemPop( ULONG ulIndex ) if( HB_IS_ARRAY( pArray ) ) { + if( HB_IS_OBJECT( pArray ) && hb_objHasOperator( pArray, HB_OO_OP_ARRAYINDEX ) ) + { + hb_vmPushNumInt( ulIndex ); + hb_objOperatorCall( HB_OO_OP_ARRAYINDEX, pArray, pArray, + hb_stackItemFromTop( -1 ), pValue ); + hb_stackPop(); + hb_stackPop(); + hb_stackPop(); + return; + } + if( ulIndex > 0 && ulIndex <= pArray->item.asArray.value->ulLen ) { pValue->type &= ~HB_IT_MEMOFLAG; @@ -7557,6 +7580,15 @@ static void hb_vmArrayItemPop( ULONG ulIndex ) } } /* #endif */ + else if( hb_objHasOperator( pArray, HB_OO_OP_ARRAYINDEX ) ) + { + hb_vmPushNumInt( ulIndex ); + hb_objOperatorCall( HB_OO_OP_ARRAYINDEX, pArray, pArray, + hb_stackItemFromTop( -1 ), pValue ); + hb_stackPop(); + hb_stackPop(); + hb_stackPop(); + } else { hb_vmPushNumInt( ulIndex ); diff --git a/harbour/tests/overload.prg b/harbour/tests/overload.prg index 74b26c8b51..57c64a863b 100644 --- a/harbour/tests/overload.prg +++ b/harbour/tests/overload.prg @@ -38,10 +38,13 @@ function Main() QOut( "Substring $ :", oString $ "Hello" ) QOut( "Less than :", oString < "Hello" ) QOut( "Less than or Equal:", oString <= "Hello" ) - QOut( "Greater than :", oString < "Hello" ) - QOut( "Greater than or Equal:", oString <= "Hello" ) + QOut( "Greater than :", oString > "Hello" ) + QOut( "Greater than or Equal:", oString >= "Hello" ) QOut( "Concatenation + :", oString + "Hello" ) QOut( "Concatenation - :", oString - "Hello" ) + QOut( "Array index[2] :", oString[2] ) + QOut( "Array index[3] := 'X' :", oString[3]:='X' ) + QOut( oString:cValue ) return nil @@ -52,6 +55,7 @@ create class tString METHOD New(cText) INLINE ::cValue := cText, self + OPERATOR "=" ARG cArg INLINE ::cValue = cArg OPERATOR "==" ARG cArg INLINE ::cValue == cArg OPERATOR "!=" ARG cArg INLINE ::cValue != cArg OPERATOR "<" ARG cArg INLINE ::cValue < cArg @@ -61,6 +65,9 @@ create class tString OPERATOR "+" ARG cArg INLINE ::cValue + cArg OPERATOR "-" ARG cArg INLINE ::cValue - cArg OPERATOR "$" ARG cArg INLINE ::cValue $ cArg + OPERATOR "[]" ARG nIndex INLINE iif( pcount()>2, ; + ::cValue := stuff( ::cValue, nIndex, 1, hb_pvalue(3) ), ; + substr( ::cValue, nIndex, 1 ) ) endclass