/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ /************************************************************************* * * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * Copyright 2000, 2010 Oracle and/or its affiliates. * * OpenOffice.org - a multi-platform office productivity suite * * This file is part of OpenOffice.org. * * OpenOffice.org is free software: you can redistribute it and/or modify * it under the terms of the GNU Lesser General Public License version 3 * only, as published by the Free Software Foundation. * * OpenOffice.org is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Lesser General Public License version 3 for more details * (a copy is included in the LICENSE file that accompanied this code). * * You should have received a copy of the GNU Lesser General Public License * version 3 along with OpenOffice.org. If not, see * * for a copy of the LGPLv3 License. * ************************************************************************/ // MARKER(update_precomp.py): autogen include statement, do not remove #include "precompiled_automation.hxx" #ifdef OS2 #define INCL_DOS #include #endif #include "sysdir_win.hxx" #include "registry_win.hxx" #include "sttresid.hxx" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include using namespace com::sun::star::uno; using namespace com::sun::star::lang; using namespace com::sun::star::frame; using namespace com::sun::star::bridge; using namespace com::sun::star::connection; using ::rtl::OUString; #include #ifdef UNX #include // readlink #include #endif #include #include #include #include "tcommuni.hxx" #include "comm_bas.hxx" #include #include "objtest.hxx" #include "rcontrol.hxx" #include #include #include #include #include #include #ifndef SBX_VALUE_DECL_DEFINED #define SBX_VALUE_DECL_DEFINED SV_DECL_REF(SbxValue) #endif SV_IMPL_REF(SbxValue) static CommunicationFactory aComManFac; #define cMyDelim ' ' #define P_FEHLERLISTE pFehlerListe #define KEEP_SEQUENCES 100 // Keep Names of last 100 Calls ControlDefLoad const Controls::arClasses [] = #include "classes.hxx" CNames *Controls::pClasses = NULL; ControlDefLoad const TestToolObj::arR_Cmds [] = #include "r_cmds.hxx" CNames *TestToolObj::pRCommands = NULL; CErrors *TestToolObj::pFehlerListe = NULL; // Hier werden die Fehler des Testtools gespeichert DBG_NAME( ControlItem ) DBG_NAME( ControlDef ) ControlItem::ControlItem( const sal_Char *Name, rtl::OString aUIdP ) { DBG_CTOR(ControlItem,0); InitData(); pData->Kurzname.AssignAscii( Name ); pData->aUId = aUIdP; } ControlItem::ControlItem( const String &Name, rtl::OString aUIdP ) { DBG_CTOR(ControlItem,0); InitData(); pData->Kurzname = Name; pData->aUId = aUIdP; } ControlItem::ControlItem( ControlData *pDataP ) { DBG_CTOR(ControlItem,0); pData = pDataP; } ControlSon::~ControlSon() { if (pSons) { delete pSons; pSons = NULL; } } ControlItemSon::ControlItemSon(const String &Name, rtl::OString aUIdP ) : ControlItem( Name, aUIdP ) {} sal_Bool ControlDef::operator < (const ControlItem &rPar) { return pData->Kurzname.CompareIgnoreCaseToAscii(rPar.pData->Kurzname) == COMPARE_LESS; } sal_Bool ControlDef::operator == (const ControlItem &rPar) { return pData->Kurzname.CompareIgnoreCaseToAscii(rPar.pData->Kurzname) == COMPARE_EQUAL; } void ControlDef::Write( SvStream &aStream ) { // FIXME: HELPID #if 0 if ( pSons ) aStream.WriteByteString( String('*').Append( pData->Kurzname ), RTL_TEXTENCODING_UTF8 ); else aStream.WriteByteString( pData->Kurzname, RTL_TEXTENCODING_UTF8 ); aStream << ((sal_uInt16)pData->aUId.HasNumeric()); if ( pData->aUId.HasString() ) aStream.WriteByteString( pData->aUId.GetStr(), RTL_TEXTENCODING_UTF8 ); else aStream << static_cast(pData->aUId.GetNum()); //GetNum() sal_uLong != comm_ULONG on 64bit if ( pSons ) for ( sal_uInt16 i = 0 ; pSons->Count() > i ; i++ ) ((ControlDef*)(*pSons)[i])->Write(aStream); #else (void)aStream; #endif } ControlDef::ControlDef(const String &Name, rtl::OString aUIdP ) : ControlItemSon( Name, aUIdP) { DBG_CTOR(ControlDef,0); } ControlDef::ControlDef(const String &aOldName, const String &aNewName, ControlDef *pOriginal, sal_Bool bWithSons ) : ControlItemSon("", pOriginal->pData->aUId) { DBG_CTOR(ControlDef,0); if ( pOriginal->pData->Kurzname == aOldName ) pData->Kurzname = aNewName; else pData->Kurzname = pOriginal->pData->Kurzname; if ( bWithSons && pOriginal->pSons ) { pSons = new CNames(); for ( sal_uInt16 i = 0; i < pOriginal->pSons->Count() ; i++) { ControlDef *pNewDef; pNewDef = new ControlDef( aOldName, aNewName, pOriginal->SonGetObject(i) ,sal_True ); if (! SonInsert(pNewDef)) { OSL_FAIL("Name Doppelt im CopyConstructor. Neuer Name = Controlname!!"); delete pNewDef; } } } else pSons = NULL; } sal_Bool ControlItemUId::operator < (const ControlItem &rPar) { return pData->aUId < rPar.pData->aUId; } sal_Bool ControlItemUId::operator == (const ControlItem &rPar) { return pData->aUId == rPar.pData->aUId; } SV_IMPL_OP_PTRARR_SORT( CNames, ControlItem* ) void CRevNames::Insert( String aName, rtl::OString aUId, sal_uLong nSeq ) { ControlItem *pRN = new ReverseName(aName,aUId,nSeq); sal_uInt16 nPos; if ( Seek_Entry(pRN,&nPos) ) DeleteAndDestroy(nPos); if ( !CNames::C40_PTR_INSERT( ControlItem, pRN) ) { OSL_FAIL("Interner Fehler beim Speichern der Lokalen KurzNamen"); delete pRN; } } String CRevNames::GetName( rtl::OString aUId ) { ReverseName *pRN = new ReverseName(UniString(),aUId,0); sal_uInt16 nPos; sal_Bool bSeekOK = Seek_Entry(pRN,&nPos); delete pRN; if ( bSeekOK ) return GetObject(nPos)->pData->Kurzname; else { // FIXME: HELPID #if 0 if ( aUId.Matches( UID_ACTIVE ) ) return CUniString("Active"); else return GEN_RES_STR1( S_NAME_NOT_THERE, aUId.GetText() ); #else return String(); #endif } } void CRevNames::Invalidate ( sal_uLong nSeq ) { sal_uInt16 i; for (i = 0; i < Count() ;) { if (((ReverseName*)GetObject(i))->LastSequence < nSeq) DeleteAndDestroy(i); else i++; } } SV_IMPL_PTRARR(CErrors, ErrorEntry*) SbxTransportMethod::SbxTransportMethod( SbxDataType DT ) : SbxMethod(CUniString("Dummy"),DT) { nValue = 0; } TestToolObj::TestToolObj( String aName, String aFilePath ) // Interner Aufruf : SbxObject( aName ) , bUseIPC(sal_False) , bReturnOK(sal_True) , nSequence(KEEP_SEQUENCES) , ProgPath() , IsBlock(sal_False) , SingleCommandBlock(sal_True) , m_pControls(NULL) , m_pNameKontext(NULL) , m_pSIds(NULL) , m_pReverseSlots(NULL) , m_pReverseControls(NULL) , m_pReverseControlsSon(NULL) , m_pReverseUIds(NULL) , pCommunicationManager(NULL) , aDialogHandlerName() , nWindowHandlerCallLevel(0) , nIdleCount(0) { pImpl = new ImplTestToolObj; pImpl->ProgParam = String(); pImpl->aFileBase = DirEntry(aFilePath); pImpl->aHIDDir = DirEntry(aFilePath); pImpl->bIsStart = sal_False; pImpl->pMyBasic = NULL; pImpl->aServerTimeout = Time(0,1,00); // 1:00 Minuten fest InitTestToolObj(); } TestToolObj::TestToolObj( String aName, MyBasic* pBas ) // Aufruf im Testtool : SbxObject( aName ) , bUseIPC(sal_True) , bReturnOK(sal_True) , nSequence(KEEP_SEQUENCES) , ProgPath() , IsBlock(sal_False) , SingleCommandBlock(sal_True) , m_pControls(NULL) , m_pNameKontext(NULL) , m_pSIds(NULL) , m_pReverseSlots(NULL) , m_pReverseControls(NULL) , m_pReverseControlsSon(NULL) , m_pReverseUIds(NULL) , pCommunicationManager(NULL) , aDialogHandlerName() , nWindowHandlerCallLevel(0) , nIdleCount(0) { pImpl = new ImplTestToolObj; pImpl->ProgParam = String(); pImpl->bIsStart = sal_False; pImpl->pMyBasic = pBas; LoadIniFile(); InitTestToolObj(); pCommunicationManager = new CommunicationManagerClientViaSocketTT(); pCommunicationManager->SetDataReceivedHdl( LINK( this, TestToolObj, ReturnResultsLink )); } void TestToolObj::LoadIniFile() // Laden der IniEinstellungen, die durch den ConfigDialog ge�ndert werden k�nnen { #define GETSET(aVar, KeyName, Dafault) \ { \ ByteString __##aVar##__; \ __##aVar##__ = aConf.ReadKey(KeyName); \ if ( !__##aVar##__.Len() ) \ { \ __##aVar##__ = Dafault; \ aConf.WriteKey(KeyName, __##aVar##__); \ } \ aVar = UniString( __##aVar##__, RTL_TEXTENCODING_UTF8 );\ } #define NEWOLD( NewKey, OldKey ) \ { \ ByteString aValue; \ if ( ( (aValue = aConf.ReadKey( OldKey )).Len() ) && !aConf.ReadKey( NewKey ).Len() ) \ aConf.WriteKey( NewKey, aValue ); \ } Config aConf(Config::GetConfigName( Config::GetDefDirectory(), CUniString("testtool") )); aConf.SetGroup("Misc"); ByteString aCurrentProfile = aConf.ReadKey( "CurrentProfile", "Path" ); aConf.SetGroup( aCurrentProfile ); NEWOLD( "BaseDir", "Basisverzeichnis" ) String aFB; GETSET( aFB, "BaseDir", "" ); pImpl->aFileBase = DirEntry(aFB); // remove old keys if ( aConf.ReadKey("KeyCodes + Classes").Len() != 0 || aConf.ReadKey("KeyCodes + Classes + Res_Type").Len() != 0 ) { aConf.DeleteKey("KeyCodes + Classes + Res_Type"); aConf.DeleteKey("KeyCodes + Classes"); } NEWOLD( "LogBaseDir", "LogBasisverzeichnis" ) String aLFB; GETSET( aLFB, "LogBaseDir", ByteString( aFB, RTL_TEXTENCODING_UTF8 ) ); pImpl->aLogFileBase = DirEntry(aLFB); NEWOLD( "HIDDir", "HIDVerzeichnis" ) String aHID; GETSET( aHID, "HIDDir", "" ); pImpl->aHIDDir = DirEntry(aHID); aConf.SetGroup("Misc"); String aST; GETSET( aST, "ServerTimeout", ByteString::CreateFromInt64(Time(0,0,45).GetTime()) ); // 45 Sekunden Initial pImpl->aServerTimeout = Time(sal_uLong(aST.ToInt64())); String aSOSE; aCurrentProfile = aConf.ReadKey( "CurrentProfile", "Misc" ); aConf.SetGroup( aCurrentProfile ); GETSET( aSOSE, "StopOnSyntaxError", "0" ); pImpl->bStopOnSyntaxError = aSOSE.EqualsAscii("1"); aConf.SetGroup("GUI Platform"); String aGP; ByteString abGP; #if defined WNT && defined INTEL abGP.Append( "501" ); // Windows on x86 #elif defined WNT && defined X86_64 abGP.Append( "502" ); // Windows on x64 #elif defined SOLARIS && defined SPARC abGP.Append( "01" ); // Solaris SPARC #elif defined LINUX && defined INTEL abGP.Append( "03" ); // Linux #elif defined AIX abGP.Append( "04" ); #elif defined SOLARIS && defined INTEL abGP.Append( "05" ); // Solaris x86 #elif defined FREEBSD abGP.Append( "08" ); #elif defined MACOSX abGP.Append( "12" ); #elif defined LINUX && defined PPC abGP.Append( "13" ); #elif defined NETBSD && defined INTEL abGP.Append( "14" ); // NetBSD/i386 #elif defined LINUX && defined X86_64 abGP.Append( "15" ); // Linux x86-64 #elif defined LINUX && defined SPARC abGP.Append( "16" ); // Linux SPARC #elif defined OS2 abGP.Append( "17" ); #elif defined LINUX && defined MIPS abGP.Append( "18" ); // Linux MIPS #elif defined LINUX && defined ARM abGP.Append( "19" ); // Linux ARM #elif defined LINUX && defined IA64 abGP.Append( "20" ); // Linux ia64 #elif defined LINUX && defined S390 abGP.Append( "21" ); // Linux S390 #elif defined LINUX && defined HPPA abGP.Append( "22" ); // Linux PA-RISC #elif defined LINUX && defined AXP abGP.Append( "23" ); // Linux ALPHA #elif defined NETBSD && defined X86_64 abGP.Append( "24" ); // NetBSD/amd64 #elif defined OPENBSD && defined X86 abGP.Append( "25" ); // OpenBSD/i386 #elif defined OPENBSD && defined X86_64 abGP.Append( "26" ); // OpenBSD/amd64 #elif defined DRAGONFLY && defined X86 abGP.Append( "27" ); // DragonFly/i386 #elif defined DRAGONFLY && defined X86_64 abGP.Append( "28" ); // DragonFly/x86-64 #else #error ("unknown platform. please request an ID for your platform on qa/dev") #endif GETSET( aGP, "Current", abGP ); // #i68804# Write default Communication section to testtoolrc/.ini // this is not fastest but too keep defaultsettings in one place in the code GetHostConfig(); GetTTPortConfig(); GetUnoPortConfig(); aConf.SetGroup("Crashreporter"); String aUP; GETSET( aUP, "UseProxy", "false" ); String aPS; GETSET( aPS, "ProxyServer", "" ); String aPP; GETSET( aPP, "ProxyPort", "" ); String aAC; GETSET( aAC, "AllowContact", "false" ); String aRA; GETSET( aRA, "ReturnAddress", "" ); OUString sPath; if( osl_getExecutableFile( (rtl_uString**)&sPath ) == osl_Process_E_None) { sPath = sPath.copy(7); // strip file:// int i = sPath.lastIndexOf('/'); if (i >= 0) i = sPath.lastIndexOf('/', i-1 ); if (i >= 0) { sPath = sPath.copy(0, i); ByteString bsPath( sPath.getStr(), sPath.getLength(), RTL_TEXTENCODING_UTF8 ); aConf.SetGroup( "OOoProgramDir" ); String aOPD; // testtool is installed in Basis3.x/program/ dir nowadays bsPath += "/../program"; GETSET( aOPD, "Current", bsPath); ByteString aSrcRoot(getenv("SRC_ROOT")); aConf.SetGroup( "_profile_Default" ); if (aSrcRoot.Len()) { String aPBD; aSrcRoot += "/testautomation"; GETSET( aPBD, "BaseDir", aSrcRoot ); String aPHD; aSrcRoot += "/global/hid"; GETSET( aPHD, "HIDDir", aSrcRoot ); } else { String aPBD; bsPath += "/qatesttool"; GETSET( aPBD, "BaseDir", bsPath ); String aPHD; bsPath += "/global/hid"; GETSET( aPHD, "HIDDir", bsPath ); } String aLD; GETSET( aLD, "LogBaseDir", ByteString( "/tmp" ) ); } } } #define MAKE_TT_KEYWORD( cName, aType, aResultType, nID ) \ { \ SbxVariableRef pMeth; \ pMeth = Make( CUniString(cName), aType, aResultType ); \ pMeth->SetUserData( nID ); \ } // SetUserData mu� irgendwas sein, sonst wird es im Find rausgefiltert!!! #define MAKE_USHORT_CONSTANT(cName, nValue) \ { \ SbxProperty *pVal = new SbxProperty( CUniString( cName) , SbxINTEGER ); \ pVal->PutInteger( nValue ) ; \ pVal->SetUserData( 32000 ); \ Insert( pVal ); \ } #define RTLNAME "@SBRTL" // copied from basic/source/classes/sb.cxx void TestToolObj::InitTestToolObj() { pImpl->nNumBorders = 0; // F�r Profiling mit k�stchen pImpl->nMinRemoteCommandDelay = 0; pImpl->nMaxRemoteCommandDelay = 0; pImpl->bDoRemoteCommandDelay = sal_False; pImpl->bLnaguageExtensionLoaded= sal_False; pImpl->pTTSfxBroadcaster = NULL; pImpl->nErrorCount = 0; pImpl->nWarningCount = 0; pImpl->nQAErrorCount = 0; pImpl->nIncludeFileWarningCount = 0; pImpl->xErrorList = new SbxDimArray( SbxSTRING ); pImpl->xWarningList = new SbxDimArray( SbxSTRING ); pImpl->xQAErrorList = new SbxDimArray( SbxSTRING ); pImpl->xIncludeFileWarningList = new SbxDimArray( SbxSTRING ); pImpl->nTestCaseLineNr = 0; pImpl->bEnableQaErrors = sal_True; pImpl->bDebugFindNoErrors = sal_False; pImpl->pChildEnv = new Environment; if (!pFehlerListe) pFehlerListe = new CErrors; // Vor allem anderen. Wer weiss, wer alles einen Fehler ausl�st. In = new CmdStream(); pShortNames = new CRevNames; pImpl->pHttpRequest = NULL; // overwrite standard "wait" method, cause we can do better than that!! // Insert Object into SbiStdObject but change listening. SbxVariable* pRTL = pImpl->pMyBasic->Find( CUniString(RTLNAME), SbxCLASS_DONTCARE ); SbxObject* pRTLObject = PTR_CAST( SbxObject, pRTL ); if ( pRTLObject ) { SbxVariableRef pWait; pWait = pRTLObject->Make( CUniString("Wait"), SbxCLASS_METHOD, SbxNULL ); pWait->SetUserData( ID_Wait ); // change listener here pRTLObject->EndListening( pWait->GetBroadcaster(), sal_True ); StartListening( pWait->GetBroadcaster(), sal_True ); } else { OSL_FAIL("Testtool: Could not replace Wait method"); } MAKE_TT_KEYWORD( "Kontext", SbxCLASS_METHOD, SbxNULL, ID_Kontext ); MAKE_TT_KEYWORD( "GetNextError", SbxCLASS_VARIABLE, SbxVARIANT, ID_GetError ); MAKE_TT_KEYWORD( "Start", SbxCLASS_METHOD, SbxSTRING, ID_Start ); MAKE_TT_KEYWORD( "Use", SbxCLASS_METHOD, SbxNULL, ID_Use ); MAKE_TT_KEYWORD( "StartUse", SbxCLASS_METHOD, SbxNULL, ID_StartUse ); MAKE_TT_KEYWORD( "FinishUse", SbxCLASS_METHOD, SbxNULL, ID_FinishUse ); MAKE_TT_KEYWORD( "CaseLog", SbxCLASS_METHOD, SbxNULL, ID_CaseLog ); MAKE_TT_KEYWORD( "ExceptLog", SbxCLASS_METHOD, SbxNULL, ID_ExceptLog ); MAKE_TT_KEYWORD( "PrintLog", SbxCLASS_METHOD, SbxNULL, ID_PrintLog ); MAKE_TT_KEYWORD( "WarnLog", SbxCLASS_METHOD, SbxNULL, ID_WarnLog ); MAKE_TT_KEYWORD( "ErrorLog", SbxCLASS_METHOD, SbxNULL, ID_ErrorLog ); MAKE_TT_KEYWORD( "QAErrorLog", SbxCLASS_METHOD, SbxNULL, ID_QAErrorLog ); MAKE_TT_KEYWORD( "EnableQaErrors", SbxCLASS_PROPERTY, SbxBOOL, ID_EnableQaErrors ); MAKE_TT_KEYWORD( "MaybeAddErr", SbxCLASS_METHOD, SbxNULL, ID_MaybeAddErr ); MAKE_TT_KEYWORD( "ClearError", SbxCLASS_METHOD, SbxNULL, ID_ClearError ); MAKE_TT_KEYWORD( "SaveIDs", SbxCLASS_METHOD, SbxBOOL, ID_SaveIDs ); MAKE_TT_KEYWORD( "AutoExecute", SbxCLASS_PROPERTY, SbxBOOL, ID_AutoExecute ); // Achtung! PROPERTY Also eine Variable MAKE_TT_KEYWORD( "Execute", SbxCLASS_METHOD, SbxNULL, ID_Execute ); MAKE_TT_KEYWORD( "StopOnSyntaxError", SbxCLASS_PROPERTY, SbxBOOL, ID_StopOnSyntaxError ); /* Dialog Handler werden gebraucht, wenn im internen Testtool ein Dialog hochgerissen wird. Nach versenden der Remote-Kommandos wird IdleHandler aktiviert. Er testet, ob das Reschedule zum WaitForAnswer zur�ckkehrt. Bleibt das aus, so wird erst der RemoteHandler zur�ckgesetzt und dann die Handler-Sub im Basic gerufen.(Entkoppelt �ber PostUserEvent.) In returndaten_verarbeiten wird flag f�r ausf�hrung des n�chsten remote-befehls r�ckgesetzt. Der Handler wird damit auch entwertet. Er gilt also nur f�r den n�chsten Remotebefehl. */ MAKE_TT_KEYWORD( "DialogHandler", SbxCLASS_METHOD, SbxNULL, ID_DialogHandler ); MAKE_TT_KEYWORD( "GetUnoApp", SbxCLASS_METHOD, SbxOBJECT, ID_GetUnoApp ); MAKE_TT_KEYWORD( "GetIServer", SbxCLASS_METHOD, SbxOBJECT, ID_GetIServer ); MAKE_TT_KEYWORD( "RemoteCommandDelay", SbxCLASS_METHOD, SbxNULL, ID_RemoteCommandDelay ); MAKE_TT_KEYWORD( "GetApplicationPath", SbxCLASS_METHOD, SbxSTRING, ID_GetApplicationPath ); MAKE_TT_KEYWORD( "GetCommonApplicationPath", SbxCLASS_METHOD, SbxSTRING, ID_GetCommonApplicationPath ); MAKE_TT_KEYWORD( "MakeIniFileName", SbxCLASS_METHOD, SbxSTRING, ID_MakeIniFileName ); /// active constants returning error and warning count MAKE_TT_KEYWORD( "GetErrorCount", SbxCLASS_METHOD, SbxULONG, ID_GetErrorCount ); MAKE_TT_KEYWORD( "GetWarningCount", SbxCLASS_METHOD, SbxULONG, ID_GetWarningCount ); MAKE_TT_KEYWORD( "GetQAErrorCount", SbxCLASS_METHOD, SbxULONG, ID_GetQAErrorCount ); MAKE_TT_KEYWORD( "GetUseFileWarningCount", SbxCLASS_METHOD, SbxULONG, ID_GetUseFileWarningCount ); MAKE_TT_KEYWORD( "GetErrorList", SbxCLASS_METHOD, SbxOBJECT, ID_GetErrorList ); MAKE_TT_KEYWORD( "GetWarningList", SbxCLASS_METHOD, SbxOBJECT, ID_GetWarningList ); MAKE_TT_KEYWORD( "GetQAErrorList", SbxCLASS_METHOD, SbxOBJECT, ID_GetQAErrorList ); MAKE_TT_KEYWORD( "GetUseFileWarningList", SbxCLASS_METHOD, SbxOBJECT, ID_GetUseFileWarningList ); MAKE_TT_KEYWORD( "GetTestCaseName", SbxCLASS_METHOD, SbxSTRING, ID_GetTestCaseName ); MAKE_TT_KEYWORD( "GetTestCaseFileName", SbxCLASS_METHOD, SbxSTRING, ID_GetTestCaseFileName ); MAKE_TT_KEYWORD( "GetTestCaseLineNr", SbxCLASS_METHOD, SbxUSHORT, ID_GetTestCaseLineNr ); MAKE_TT_KEYWORD( "SetChildEnv", SbxCLASS_METHOD, SbxNULL, ID_SetChildEnv ); MAKE_TT_KEYWORD( "GetChildEnv", SbxCLASS_METHOD, SbxSTRING, ID_GetChildEnv ); MAKE_TT_KEYWORD( "GetLinkDestination", SbxCLASS_METHOD, SbxSTRING, ID_GetLinkDestination ); MAKE_TT_KEYWORD( "GetRegistryValue", SbxCLASS_METHOD, SbxSTRING, ID_GetRegistryValue ); MAKE_TT_KEYWORD( "KillApp", SbxCLASS_METHOD, SbxNULL, ID_KillApp ); MAKE_TT_KEYWORD( "HTTPSend", SbxCLASS_METHOD, SbxUSHORT, ID_HTTPSend ); MAKE_TT_KEYWORD( "HTTPSetProxy", SbxCLASS_METHOD, SbxNULL, ID_HTTPSetProxy ); // Load the Remote Commands from list if ( !pRCommands ) // Ist static, wird also nur einmal geladen ReadFlatArray( arR_Cmds, pRCommands ); sal_uInt16 i; for ( i = 0 ; i < pRCommands->Count() ; i++ ) { SbxTransportMethod *pMeth = new SbxTransportMethod( SbxVARIANT ); pMeth->SetName( pRCommands->GetObject( i )->pData->Kurzname ); pMeth->SetUserData( ID_RemoteCommand ); // FIXME: HELPID #if 0 pMeth->nValue = pRCommands->GetObject( i )->pData->aUId.GetNum(); #else pMeth->nValue = 0; #endif Insert( pMeth ); StartListening( pMeth->GetBroadcaster(), sal_True ); } // Konstanten f�r SetControlType MAKE_USHORT_CONSTANT("CTBrowseBox",CONST_CTBrowseBox); MAKE_USHORT_CONSTANT("CTValueSet",CONST_CTValueSet); // Konstanten f�r das Alignment des gesuchten Splitters MAKE_USHORT_CONSTANT("AlignLeft",CONST_ALIGN_LEFT); MAKE_USHORT_CONSTANT("AlignTop",CONST_ALIGN_TOP); MAKE_USHORT_CONSTANT("AlignRight",CONST_ALIGN_RIGHT); MAKE_USHORT_CONSTANT("AlignBottom",CONST_ALIGN_BOTTOM); /// What dialog to use in RC_CloseSysDialog or RC_ExistsSysDialog MAKE_USHORT_CONSTANT("FilePicker",CONST_FilePicker); MAKE_USHORT_CONSTANT("FolderPicker",CONST_FolderPicker); /// NodeTypes of the SAX Parser MAKE_USHORT_CONSTANT("NodeTypeCharacter",CONST_NodeTypeCharacter); MAKE_USHORT_CONSTANT("NodeTypeElement",CONST_NodeTypeElement); MAKE_USHORT_CONSTANT("NodeTypeComment",CONST_NodeTypeComment); /// ItemTypes for TreeListBox and maybe others MAKE_USHORT_CONSTANT("ItemTypeText",CONST_ItemTypeText); MAKE_USHORT_CONSTANT("ItemTypeBMP",CONST_ItemTypeBMP); MAKE_USHORT_CONSTANT("ItemTypeCheckbox",CONST_ItemTypeCheckbox); MAKE_USHORT_CONSTANT("ItemTypeContextBMP",CONST_ItemTypeContextBMP); MAKE_USHORT_CONSTANT("ItemTypeUnknown",CONST_ItemTypeUnknown); /// Return values for WaitSlot MAKE_USHORT_CONSTANT("WSTimeout",CONST_WSTimeout); MAKE_USHORT_CONSTANT("WSAborted",CONST_WSAborted); MAKE_USHORT_CONSTANT("WSFinished",CONST_WSFinished); pImpl->pControlsObj = new Controls( CUniString("GetNextCloseWindow") ); pImpl->pControlsObj->SetType( SbxVARIANT ); Insert( pImpl->pControlsObj ); pImpl->pControlsObj->SetUserData( ID_GetNextCloseWindow ); pImpl->pControlsObj->ChangeListener( this ); for ( i=0;ipMyVars[i] = new SbxTransportMethod( SbxVARIANT ); pImpl->pMyVars[i]->SetName( CUniString("VarDummy").Append(String::CreateFromInt32(i) ) ); Insert( pImpl->pMyVars[i] ); } m_pControls = new CNames(); m_pSIds = new CNames(); m_pNameKontext = m_pControls; nMyVar = 0; pImpl->pMyBasic->AddFactory( &aComManFac ); } TestToolObj::~TestToolObj() { pImpl->pMyBasic->RemoveFactory( &aComManFac ); EndListening( ((StarBASIC*)GetParent())->GetBroadcaster() ); pImpl->pNextReturn.Clear(); pImpl->pControlsObj.Clear(); for ( int i = 0 ; i < VAR_POOL_SIZE ; i++ ) { pImpl->pMyVars[i].Clear(); } if (m_pControls) delete m_pControls; if (m_pReverseSlots) delete m_pReverseSlots; if (m_pReverseControls) delete m_pReverseControls; if (m_pReverseControlsSon) delete m_pReverseControlsSon; if (m_pReverseUIds) delete m_pReverseUIds; if (m_pSIds) delete m_pSIds; if (pFehlerListe) { delete pFehlerListe; pFehlerListe = NULL; // da pFehlerListe static ist!! } if ( pCommunicationManager ) { pCommunicationManager->StopCommunication(); delete pCommunicationManager; } delete In; if ( pImpl->pTTSfxBroadcaster ) delete pImpl->pTTSfxBroadcaster; delete pImpl->pChildEnv; pImpl->xErrorList.Clear(); pImpl->xWarningList.Clear(); pImpl->xQAErrorList.Clear(); pImpl->xIncludeFileWarningList.Clear(); delete pImpl; delete pShortNames; } SfxBroadcaster& TestToolObj::GetTTBroadcaster() { if ( !pImpl->pTTSfxBroadcaster ) pImpl->pTTSfxBroadcaster = new SfxBroadcaster; return *pImpl->pTTSfxBroadcaster; } void TestToolObj::ReadNames( String Filename, CNames *&pNames, CNames *&pUIds, sal_Bool bIsFlat ) { /******************************************************************************* ** ** Folgende Dateiendungen sind vorhanden ** ** hid.lst Langname UId ** *.sid Slot Ids Kurzname Langname Datei ist flach ** *.win Controlname Langname Datei mit *name und +name Notation ** ** *******************************************************************************/ SvFileStream Stream; String aLine,aShortname,aLongname; rtl::OString aUId; xub_StrLen nLineNr; sal_uInt16 nElement; ControlDef *pNewDef, *pNewDef2; ControlDef *pFatherDef = NULL; nLineNr = 0; // Wir sind ja noch vor der Datei if (! pUIds) { String aFileName = (pImpl->aHIDDir + DirEntry(CUniString("hid.lst"))).GetFull(); { TTExecutionStatusHint aHint( TT_EXECUTION_SHOW_ACTION, String(SttResId(S_READING_LONGNAMES)), aFileName ); GetTTBroadcaster().Broadcast( aHint ); } ReadFlat( aFileName ,pUIds, sal_True ); if ( !pUIds ) return; pNewDef = new ControlDef("Active",rtl::OString()); const ControlItem *pItem = pNewDef; if (! pUIds->Insert(pItem)) { ADD_WARNING_LOG2( GEN_RES_STR1c( S_DOUBLE_NAME, "Active" ), Filename, nLineNr ); delete pNewDef; } } ADD_MESSAGE_LOG( Filename ); Stream.Open(Filename, STREAM_STD_READ); if (!Stream.IsOpen()) { ADD_ERROR(ERR_NO_FILE,GEN_RES_STR1(S_CANNOT_OPEN_FILE, Filename)); return; } if ( bIsFlat && !pNames ) { TTExecutionStatusHint aHint( TT_EXECUTION_SHOW_ACTION, String(SttResId(S_READING_SLOT_IDS)), Filename ); GetTTBroadcaster().Broadcast( aHint ); } else { TTExecutionStatusHint aHint( TT_EXECUTION_SHOW_ACTION, String(SttResId(S_READING_CONTROLS)), Filename ); GetTTBroadcaster().Broadcast( aHint ); } if ( !pNames ) pNames = new CNames(); { TTExecutionStatusHint aHint( TT_EXECUTION_ENTERWAIT ); GetTTBroadcaster().Broadcast( aHint ); } while (!Stream.IsEof()) { nLineNr++; Stream.ReadByteStringLine(aLine, RTL_TEXTENCODING_IBM_850); aLine.EraseLeadingChars(); aLine.EraseTrailingChars(); while ( aLine.SearchAscii(" ") != STRING_NOTFOUND ) aLine.SearchAndReplaceAllAscii(" ",UniString(' ')); if (aLine.Len() == 0) continue; if (aLine.Copy(0,4).CompareIgnoreCaseToAscii("Rem ") == COMPARE_EQUAL) continue; if (aLine.Copy(0,1).CompareToAscii("'") == COMPARE_EQUAL) continue; if ( (aLine.GetTokenCount(cMyDelim) < 2 || aLine.GetTokenCount(cMyDelim) > 3) && aLine.CompareIgnoreCaseToAscii("*Active") != COMPARE_EQUAL ) { ADD_WARNING_LOG2( GEN_RES_STR1( S_INVALID_LINE, aLine ), Filename, nLineNr ); continue; } aShortname = aLine.GetToken(0,cMyDelim); aLongname = aLine.GetToken(1,cMyDelim); String aFirstAllowedExtra, aAllowed; aFirstAllowedExtra.AssignAscii("+*"); aAllowed.AssignAscii("_"); xub_StrLen nIndex = 0; sal_Bool bOK = sal_True; while ( bOK && nIndex < aShortname.Len() ) { sal_Unicode aChar = aShortname.GetChar( nIndex ); sal_Bool bOKThis = sal_False; bOKThis |= ( aAllowed.Search( aChar ) != STRING_NOTFOUND ); if ( !nIndex ) bOKThis |= ( aFirstAllowedExtra.Search( aChar ) != STRING_NOTFOUND ); bOKThis |= ( aChar >= 'A' && aChar <= 'Z' ); bOKThis |= ( aChar >= 'a' && aChar <= 'z' ); bOKThis |= ( aChar >= '0' && aChar <= '9' ); bOK &= bOKThis; nIndex++; } if ( !bOK ) { ADD_WARNING_LOG2( CUniString("Zeile \"").Append(aLine).AppendAscii("\" enth�lt ung�ltige Zeichen."), Filename, nLineNr ); continue; } sal_Bool bUnoName = ( aLongname.Copy( 0, 5 ).EqualsIgnoreCaseAscii( ".uno:" ) || aLongname.Copy( 0, 4 ).EqualsIgnoreCaseAscii( "http" ) || aLongname.Copy( 0, 15 ).EqualsIgnoreCaseAscii( "private:factory" ) || aLongname.Copy( 0, 8 ).EqualsIgnoreCaseAscii( "service:" ) || aLongname.Copy( 0, 6 ).EqualsIgnoreCaseAscii( "macro:" ) || aLongname.Copy( 0, 8 ).EqualsIgnoreCaseAscii( ".HelpId:" ) ); // generic method to mark longnames as symbolic if ( aLongname.Copy( 0, 4 ).EqualsIgnoreCaseAscii( "sym:" ) ) { bUnoName = sal_True; aLongname.Erase( 0, 4 ); } sal_Bool bMozillaName = ( !bIsFlat && aLongname.Copy( 0, 4 ).EqualsIgnoreCaseAscii( ".moz" ) ); if ( aShortname.GetChar(0) == '+' ) // Kompletten Eintrag kopieren { aShortname.Erase(0,1); ControlDef WhatName(aLongname,rtl::OString()); ControlDef *OldTree; if (pNames->Seek_Entry(&WhatName,&nElement)) { OldTree = (ControlDef*)pNames->GetObject(nElement); pNewDef = new ControlDef(aLongname,aShortname,OldTree,sal_True); const ControlItem *pItem = pNewDef; if (! pNames->Insert(pItem)) { ADD_WARNING_LOG2( GEN_RES_STR1( S_DOUBLE_NAME, aLine ), Filename, nLineNr ); delete pNewDef; pFatherDef = NULL; } else { pFatherDef = pNewDef; } } else { ADD_WARNING_LOG2( GEN_RES_STR1( S_SHORTNAME_UNKNOWN, aLine ), Filename, nLineNr ); continue; } } else { // FIXME: HELPID #if 0 if (aShortname.CompareIgnoreCaseToAscii("*Active") == COMPARE_EQUAL) aUId = rtl::OString( UID_ACTIVE ); else #endif if ( !bUnoName && !bMozillaName ) { // Bestimmen der ID aus der Hid.Lst ControlDef WhatName(aLongname,rtl::OString()); if (pUIds->Seek_Entry(&WhatName,&nElement)) aUId = pUIds->GetObject(nElement)->pData->aUId; else { ADD_WARNING_LOG2( GEN_RES_STR1( S_LONGNAME_UNKNOWN, aLine ), Filename, nLineNr ); continue; } } else { // FIXME: HELPID #if 0 if ( bUnoName ) aUId = rtl::OString( aLongname ); else if ( bMozillaName ) aUId = rtl::OString( aLongname ); else { OSL_FAIL("Unknown URL schema"); } #endif } if (aShortname.GetChar(0) == '*' || bIsFlat) // Globaler Kurzname (Dialogname oder SId) { if (!bIsFlat) aShortname.Erase(0,1); pNewDef = new ControlDef(aShortname,aUId); if (!bIsFlat) { pNewDef->Sons( new CNames() ); pNewDef2 = new ControlDef(aShortname,aUId); if (!pNewDef->SonInsert( pNewDef2 )) // Dialog in eigenen Namespace eintragen { delete pNewDef2; OSL_FAIL(" !!!! ACHTUNG !!!! Fehler beim einf�gen in leere Liste!"); } } const ControlItem *pItem = pNewDef; if (! pNames->Insert(pItem)) { ADD_WARNING_LOG2( GEN_RES_STR1( S_DOUBLE_NAME, aLine ), Filename, nLineNr ); delete pNewDef; pFatherDef = NULL; } else { pFatherDef = pNewDef; } } else { if (!pFatherDef) { ADD_WARNING_LOG2( GEN_RES_STR0( S_FIRST_SHORTNAME_REQ_ASTRX ), Filename, nLineNr ); } else { pNewDef = new ControlDef(aShortname,aUId); if (! pFatherDef->SonInsert(pNewDef)) { ADD_WARNING_LOG2( GEN_RES_STR1( S_DOUBLE_NAME, aLine ), Filename, nLineNr ); delete pNewDef; } } } } GetpApp()->Reschedule(); } { TTExecutionStatusHint aHint( TT_EXECUTION_LEAVEWAIT ); GetTTBroadcaster().Broadcast( aHint ); } { TTExecutionStatusHint aHint( TT_EXECUTION_HIDE_ACTION ); GetTTBroadcaster().Broadcast( aHint ); } Stream.Close(); } void TestToolObj::AddName(String &aBisher, String &aNeu ) { String aSl( '/' ); if ( UniString(aSl).Append(aBisher).Append(aSl).ToUpperAscii().Search( UniString(aSl).Append(aNeu).Append(aSl).ToUpperAscii() ) == STRING_NOTFOUND ) { aBisher += aSl; aBisher += aNeu; } } void TestToolObj::ReadFlat( String Filename, CNames *&pNames, sal_Bool bSortByName ) // Wenn bSortByName == sal_False, dann nach UId Sortieren (ControlItemUId statt ControlDef) { SvFileStream Stream; String aLine,aLongname; rtl::OString aUId; xub_StrLen nLineNr; ControlItem *pNewItem; sal_uInt16 nDoubleCount = 0; Stream.Open(Filename, STREAM_STD_READ); if (!Stream.IsOpen()) { ADD_ERROR(ERR_NO_FILE,GEN_RES_STR1(S_CANNOT_OPEN_FILE, Filename)); return; } nLineNr = 0; // Wir sind ja noch vor der Datei if ( !pNames ) pNames = new CNames(); { TTExecutionStatusHint aHint( TT_EXECUTION_ENTERWAIT ); GetTTBroadcaster().Broadcast( aHint ); } ADD_MESSAGE_LOG( Filename ); while (!Stream.IsEof()) { nLineNr++; Stream.ReadByteStringLine(aLine, RTL_TEXTENCODING_IBM_850); aLine.EraseLeadingChars(); aLine.EraseTrailingChars(); while ( aLine.SearchAscii(" ") != STRING_NOTFOUND ) aLine.SearchAndReplaceAllAscii(" ",UniString(' ')); if (aLine.Len() == 0) continue; if ( (aLine.GetTokenCount(cMyDelim) < 2 || aLine.GetTokenCount(cMyDelim) > 3) && aLine.CompareIgnoreCaseToAscii("*Active") != COMPARE_EQUAL ) { ADD_WARNING_LOG2( GEN_RES_STR1( S_INVALID_LINE, aLine ), Filename, nLineNr ); continue; } aLongname = aLine.GetToken(0,cMyDelim); // FIXME: HELPID aUId = rtl::OUStringToOString( aLine.GetToken(1,cMyDelim), RTL_TEXTENCODING_UTF8 ); if ( bSortByName ) pNewItem = new ControlDef( aLongname, aUId ); else pNewItem = new ControlItemUId( aLongname, aUId ); if ( !pNames->C40_PTR_INSERT( ControlItem, pNewItem ) ) { if ( bSortByName ) { if ( nDoubleCount++ < 10 ) { ADD_WARNING_LOG2( GEN_RES_STR1( S_DOUBLE_NAME, aLine ), Filename, nLineNr ); } } else { sal_uInt16 nNr; pNames->Seek_Entry( pNewItem, &nNr ); AddName( pNames->GetObject(nNr)->pData->Kurzname, pNewItem->pData->Kurzname ); } delete pNewItem; } GetpApp()->Reschedule(); } { TTExecutionStatusHint aHint( TT_EXECUTION_LEAVEWAIT ); GetTTBroadcaster().Broadcast( aHint ); } Stream.Close(); } void ReadFlatArray( const ControlDefLoad arWas [], CNames *&pNames ) { sal_uInt16 nIndex = 0; if ( !pNames ) pNames = new CNames(); while ( String::CreateFromAscii(arWas[nIndex].Kurzname).Len() > 0 ) { // FIXME: HELPID rtl::OString aUId;// (arWas[nIndex].nUId); const ControlItem *pX = new ControlDef( arWas[nIndex].Kurzname, aUId); pNames->C40_PTR_INSERT(ControlItem, pX); nIndex++; } } void TestToolObj::WaitForAnswer () { if ( bUseIPC ) { sal_Bool bWasRealWait = !bReturnOK; BasicRuntime aRun( NULL ); if ( BasicRuntimeAccess::HasRuntime() ) aRun = BasicRuntimeAccess::GetRuntime(); // this timer to terminate Yield below Timer aTimer; aTimer.SetTimeout( pImpl->aServerTimeout.GetMSFromTime() ); aTimer.Start(); while ( !bReturnOK && aTimer.IsActive() && pCommunicationManager->IsCommunicationRunning() && aRun.IsValid() && aRun.IsRun() ) { #ifdef OS2 DosSleep(100); #endif GetpApp()->Yield(); if ( BasicRuntimeAccess::HasRuntime() ) aRun = BasicRuntimeAccess::GetRuntime(); else aRun = BasicRuntime( NULL ); } if ( bWasRealWait && aDialogHandlerName.Len() > 0 ) // Damit das ganze auch im Testtool l�uft CallDialogHandler(GetpApp()); } else { Time Ende; Ende += pImpl->aServerTimeout; SvStream *pTemp = NULL; while ( !bReturnOK && Ende > Time() ) { if ( pTemp ) { ReturnResults( pTemp ); bReturnOK = sal_True; } else { GetpApp()->Reschedule(); } nIdleCount = 0; } } if ( !bReturnOK ) { ADD_ERROR(ERR_EXEC_TIMEOUT,GEN_RES_STR1(S_TIMOUT_WAITING, String::CreateFromInt64(nSequence))); bReturnOK = sal_True; nSequence++; } } IMPL_LINK( TestToolObj, IdleHdl, Application*, EMPTYARG ) { if ( !bReturnOK ) nIdleCount++; if ( nIdleCount > 10 ) // d.h. Schon 10 mal hier gewesen und noch keinmal im WaitForAnswer { GetpApp()->RemoveIdleHdl( LINK( this, TestToolObj, IdleHdl ) ); GetpApp()->PostUserEvent( LINK( this, TestToolObj, CallDialogHandler ) ); } return 0; } IMPL_LINK( TestToolObj, CallDialogHandler, Application*, EMPTYARG ) { nWindowHandlerCallLevel++; String aHandlerName(aDialogHandlerName); aDialogHandlerName.Erase(); sal_uLong nRememberSequence = nSequence; // Da sich die Sequence im DialogHandler �ndert ((StarBASIC*)GetParent())->Call( aHandlerName ); nSequence = nRememberSequence; // Die Sequenznummern werden dann zwar doppelt vergeben, aber wen k�mmerts. nWindowHandlerCallLevel--; return 0; } void TestToolObj::BeginBlock() { WaitForAnswer(); if ( IsError() ) return; DBG_ASSERT(!IsBlock,"BeginBlock innerhalb eines Blockes"); In->Reset(nSequence); IsBlock = sal_True; } void TestToolObj::SendViaSocket() { if ( !pCommunicationManager ) { OSL_FAIL("Kein CommunicationManager vorhanden!!"); return; } if ( !pCommunicationManager->IsCommunicationRunning() ) { // first try to run basic sub "startTheOffice" see i86540 SbxVariable* pMeth = pImpl->pMyBasic->Find( CUniString( "startTheOffice" ), SbxCLASS_DONTCARE); if( !pImpl->bIsStart && pMeth && pMeth->ISA(SbxMethod) ) { pImpl->pMyBasic->Call( CUniString( "startTheOffice" ) ); } else { pImpl->pMyBasic->ResetError(); // reset error produced by failed Find above if ( !pCommunicationManager->StartCommunication( ProgPath, pImpl->ProgParam, pImpl->pChildEnv ) ) { ADD_ERROR(ERR_RESTART_FAIL,GEN_RES_STR1(S_APPLICATION_START_FAILED, ProgPath)); } else { if ( !pImpl->bIsStart ) { ADD_ERROR(ERR_RESTART,GEN_RES_STR0(S_APPLICATION_RESTARTED)); } } } } bReturnOK = sal_False; if ( pCommunicationManager->GetLastNewLink() ) { if ( !pCommunicationManager->GetLastNewLink()->TransferDataStream( In->GetStream() ) ) { ADD_ERROR(ERR_SEND_TIMEOUT,GEN_RES_STR1(S_TIMOUT_SENDING, String::CreateFromInt64(nSequence))); nSequence++; bReturnOK = sal_True; // Kein Return zu erwarten } } else { ADD_ERROR(ERR_SEND_TIMEOUT,GEN_RES_STR1(S_NO_CONNECTION, String::CreateFromInt64(nSequence))); nSequence++; bReturnOK = sal_True; // Kein Return zu erwarten } } void TestToolObj::EndBlock() { if (IsBlock) { pImpl->LocalStarttime = Time::GetSystemTicks(); // Setzen der Anfangszeit f�r Performancemessung In->GenCmdFlow (F_EndCommandBlock); if ( pImpl->bDoRemoteCommandDelay ) { sal_uLong nTimeWait = pImpl->nMinRemoteCommandDelay; if ( pImpl->nMaxRemoteCommandDelay != pImpl->nMinRemoteCommandDelay ) nTimeWait += Time::GetSystemTicks() % ( pImpl->nMaxRemoteCommandDelay - pImpl->nMinRemoteCommandDelay ); Timer aTimer; aTimer.SetTimeout( nTimeWait ); aTimer.Start(); while ( aTimer.IsActive() && pCommunicationManager->IsCommunicationRunning() ) { #ifdef OS2 DosSleep(100); #endif GetpApp()->Yield(); } } if ( bUseIPC ) SendViaSocket(); else { bReturnOK = sal_False; if ( aDialogHandlerName.Len() > 0 ) GetpApp()->InsertIdleHdl( LINK( this, TestToolObj, IdleHdl ), 1 ); } IsBlock = sal_False; } else { OSL_FAIL("EndBlock au�erhalb eines Blockes"); } } sal_Bool TestToolObj::Load( String aFileName, SbModule *pMod ) { sal_Bool bOk = sal_True; SvFileStream aStrm( aFileName, STREAM_STD_READ ); if( aStrm.IsOpen() ) { String aText, aLine; sal_Bool bIsFirstLine = sal_True; rtl_TextEncoding aFileEncoding = RTL_TEXTENCODING_IBM_850; while( !aStrm.IsEof() && bOk ) { aStrm.ReadByteStringLine( aLine, aFileEncoding ); if ( bIsFirstLine && IsTTSignatureForUnicodeTextfile( aLine ) ) aFileEncoding = RTL_TEXTENCODING_UTF8; else { if ( !bIsFirstLine ) aText += '\n'; aText += aLine; bIsFirstLine = sal_False; } if( aStrm.GetError() != SVSTREAM_OK ) bOk = sal_False; } aText.ConvertLineEnd(); pMod->SetName(CUniString("--").Append(aFileName)); pMod->SetComment( GetRevision( aText ) ); SbModule* pOldModule = MyBasic::GetCompileModule(); MyBasic::SetCompileModule( pMod ); pMod->SetSource( PreCompile( aText ) ); MyBasic::SetCompileModule( pOldModule ); if ( WasPrecompilerError() ) bOk = sal_False; } else bOk = sal_False; return bOk; } sal_Bool TestToolObj::ReadNamesBin( String Filename, CNames *&pSIds, CNames *&pControls ) { SvFileStream aStream; String aName,aURL; rtl::OString aUId; ControlDef *pNewDef, *pNewDef2; ControlDef *pFatherDef = NULL; aStream.Open(Filename, STREAM_STD_READ); if (!aStream.IsOpen()) { ADD_ERROR(ERR_NO_FILE,GEN_RES_STR1(S_CANNOT_OPEN_FILE, Filename)); return sal_False; } if ( !pSIds ) pSIds = new CNames(); if ( !pControls ) pControls = new CNames(); { TTExecutionStatusHint aHint( TT_EXECUTION_ENTERWAIT ); GetTTBroadcaster().Broadcast( aHint ); } sal_uInt16 nAnz; aStream >> nAnz; CNames *pNames = pSIds; // first read all the slots sal_Bool bIsFlat = sal_True; // Slots do not have children while ( nAnz && !aStream.IsEof() ) { aStream.ReadByteString( aName, RTL_TEXTENCODING_UTF8 ); sal_uInt16 nType; aStream >> nType; if ( !nType /* HasNumeric() */) { String aStrId; aStream.ReadByteString( aStrId, RTL_TEXTENCODING_UTF8 ); // FIXME: HELPID #if 0 aUId = rtl::OString( aStrId ); #endif } else { comm_ULONG nUId; aStream >> nUId; aUId = rtl::OString();// nUId; } if (aName.GetChar(0) == '*' || bIsFlat ) // Globaler Kurzname (Dialogname oder SId) { if (!bIsFlat) aName.Erase(0,1); pNewDef = new ControlDef(aName,aUId); if (!bIsFlat) { pNewDef->Sons(new CNames()); pNewDef2 = new ControlDef(aName,aUId); // Noch einen machen if (!pNewDef->SonInsert(pNewDef2)) // Dialog in eigenen Namespace eintragen { delete pNewDef2; OSL_FAIL(" !!!! ACHTUNG !!!! Fehler beim einf�gen in leere Liste!"); } } const ControlItem *pItem = pNewDef; if (! pNames->Insert(pItem)) { OSL_FAIL(" !!!! ACHTUNG !!!! Fehler beim einf�gen eines namens!"); delete pNewDef; pFatherDef = NULL; } else { pFatherDef = pNewDef; } } else { if (!pFatherDef) { OSL_FAIL( "Internal Error: Erster Kurzname mu� mit * beginnen. �berspringe." ); } else { pNewDef = new ControlDef(aName,aUId); if (! pFatherDef->SonInsert(pNewDef)) { delete pNewDef; OSL_FAIL(" !!!! ACHTUNG !!!! Fehler beim einf�gen eines namens!"); } } } nAnz--; if ( !nAnz && bIsFlat ) // We have read all slots { aStream >> nAnz; pNames = pControls; // Now read the controls bIsFlat = sal_False; // Controls *do* have children } GetpApp()->Reschedule(); } { TTExecutionStatusHint aHint( TT_EXECUTION_LEAVEWAIT ); GetTTBroadcaster().Broadcast( aHint ); } aStream.Close(); return sal_True; } sal_Bool TestToolObj::WriteNamesBin( String Filename, CNames *pSIds, CNames *pControls ) { sal_Bool bOk = sal_True; SvFileStream aStrm( String(Filename).AppendAscii(".bin"), STREAM_STD_WRITE ); if( aStrm.IsOpen() ) { sal_uInt16 i; if ( pSIds ) { aStrm << pSIds->Count(); for ( i = 0 ; pSIds->Count() > i && bOk ; i++ ) { ((ControlDef*)(*pSIds)[i])->Write(aStrm); if( aStrm.GetError() != SVSTREAM_OK ) bOk = sal_False; } } else aStrm << sal_uInt16( 0 ); if ( pControls ) { aStrm << pControls->Count(); for ( i = 0 ; pControls->Count() > i && bOk ; i++ ) { ((ControlDef*)(*pControls)[i])->Write(aStrm); if( aStrm.GetError() != SVSTREAM_OK ) bOk = sal_False; } } else aStrm << sal_uInt16( 0 ); } else bOk = sal_False; return bOk; } void TestToolObj::SFX_NOTIFY( SfxBroadcaster&, const TypeId&, const SfxHint& rHint, const TypeId& ) { static CNames *pUIds = NULL; // Halten der hid.lst const SbxHint* p = PTR_CAST(SbxHint,&rHint); if( p ) { SbxVariable* pVar = p->GetVar(); SbxArray* rPar = pVar->GetParameters(); sal_uLong nHintId = p->GetId(); sal_uLong nHintUserData = pVar->GetUserData(); if( nHintId == SBX_HINT_DATAWANTED ) { nMyVar = 0; switch( nHintUserData ) { case ID_Kontext: if ( !rPar ) { m_pNameKontext = m_pControls; // So da� nicht immer mal wieder was aus einem alten Kontext dazwischenhaut for (sal_uInt16 i=0;ipMyVars[i]->SetName( CUniString("VarDummy").Append(UniString::CreateFromInt32(i)) ); } } else if ( rPar && rPar->Count() == 2 ) { sal_uInt16 nElement; SbxVariableRef pArg = rPar->Get( 1 ); String aKontext = pArg->GetString(); ControlDef WhatName(aKontext,rtl::OString()); if (m_pControls && m_pControls->Seek_Entry(&WhatName,&nElement)) { m_pNameKontext = ((ControlDef*)m_pControls->GetObject(nElement))->GetSons(); // So da� nicht immer mal wieder was aus einem alten Kontext dazwischenhaut for (sal_uInt16 i=0;ipMyVars[i]->SetName( CUniString("VarDummy").Append(UniString::CreateFromInt32(i)) ); } } } else SetError( SbxERR_WRONG_ARGS ); break; case ID_Start: if ( rPar && rPar->Count() >= 2 ) { SbxVariableRef pArg = rPar->Get( 1 ); ProgPath = pArg->GetString(); if ( rPar && rPar->Count() >= 3 ) { pArg = rPar->Get( 2 ); pImpl->ProgParam = pArg->GetString(); } else pImpl->ProgParam.Erase(); String aTmpStr(ProgPath); aTmpStr += ' '; aTmpStr += pImpl->ProgParam; { TTExecutionStatusHint aHint( TT_EXECUTION_SHOW_ACTION, String(SttResId(S_STARTING_APPLICATION)), aTmpStr ); GetTTBroadcaster().Broadcast( aHint ); } pImpl->bIsStart = sal_True; BeginBlock(); EndBlock(); pImpl->bIsStart = sal_False; { TTExecutionStatusHint aHint( TT_EXECUTION_HIDE_ACTION ); GetTTBroadcaster().Broadcast( aHint ); } } break; case ID_KillApp: pCommunicationManager->KillApplication(); break; case ID_SaveIDs: if ( rPar && rPar->Count() >= 2 ) // Genau ein Parameter { SbxVariableRef pArg = rPar->Get( 1 ); DirEntry FilePath = pImpl->aFileBase + DirEntry(pArg->GetString(),FSYS_STYLE_VFAT); WriteNamesBin( FilePath.GetFull(), m_pSIds, m_pControls ); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_AutoExecute: if ( !rPar ) // rPar = NULL <=> Kein Parameter { pVar->PutBool(SingleCommandBlock); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_Execute: if ( !rPar ) // rPar = NULL <=> Kein Parameter { EndBlock(); BeginBlock(); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_DialogHandler: if ( rPar && rPar->Count() >= 2 ) // Genau ein Parameter { SbxVariableRef pArg = rPar->Get( 1 ); aDialogHandlerName = pArg->GetString(); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_GetError: if ( !rPar ) // rPar = NULL <=> Kein Parameter { WaitForAnswer(); if ( IS_ERROR() ) { pVar->PutString( GET_ERROR()->aText ); POP_ERROR(); } else { pVar->PutString( String() ); } } else SetError( SbxERR_WRONG_ARGS ); break; case ID_StartUse: if ( !rPar ) // rPar = NULL <=> Kein Parameter { { BasicRuntime aRun = BasicRuntimeAccess::GetRuntime(); aLogFileName = DirEntry(aRun.GetModuleName(SbxNAME_NONE)).GetBase().AppendAscii(".res"); } ADD_RUN_LOG(); ADD_CASE_LOG(GEN_RES_STR0(S_READING_FILE)); pCommunicationManager->StopCommunication(); // Wait for asynchronous events to be processed, so communication will be restarted properly while ( pCommunicationManager->IsCommunicationRunning() ) Application::Reschedule(); SingleCommandBlock = sal_True; IsBlock = sal_False; for (sal_uInt16 i=0;ipMyVars[i]->SetName( CUniString("VarDummy").Append(UniString::CreateFromInt32(i)) ); } nMyVar = 0; if (m_pControls) { delete m_pControls; m_pControls = NULL; } if (m_pReverseSlots) { delete m_pReverseSlots; m_pReverseSlots = NULL; } if (m_pReverseControls) { delete m_pReverseControls; m_pReverseControls = NULL; } if (m_pReverseControlsSon) { delete m_pReverseControlsSon; m_pReverseControlsSon = NULL; } if (m_pSIds) { delete m_pSIds; m_pSIds = NULL; } if (pUIds) { delete pUIds; pUIds = NULL; } if (m_pReverseUIds) { delete m_pReverseUIds; m_pReverseUIds = NULL; } m_pNameKontext = m_pControls; pImpl->bLnaguageExtensionLoaded = sal_False; SfxSimpleHint aHint( SBX_HINT_LANGUAGE_EXTENSION_LOADED ); GetTTBroadcaster().Broadcast( aHint ); pImpl->nMinRemoteCommandDelay = 0; pImpl->nMaxRemoteCommandDelay = 0; pImpl->bDoRemoteCommandDelay = sal_False; pImpl->aTestCaseName.Erase(); pImpl->aTestCaseFileName.Erase(); pImpl->nTestCaseLineNr = 0; pImpl->bEnableQaErrors = sal_True; pImpl->bDebugFindNoErrors = sal_False; pImpl->pChildEnv->clear(); String aName( CUniString( "StopOnSyntaxError" ) ); SbxVariableRef xStopOnSyntaxError = SbxObject::Find( aName, SbxCLASS_PROPERTY ); if ( xStopOnSyntaxError.Is() ) xStopOnSyntaxError->PutBool( pImpl->bStopOnSyntaxError ); else SetError( SbxERR_BAD_ACTION ); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_Use: if ( rPar && rPar->Count() >= 2 ) { SbxVariableRef pArg = rPar->Get( 1 ); DirEntry FilePath(pArg->GetString(),FSYS_STYLE_VFAT); if ( !FilePath.IsAbs() ) FilePath = pImpl->aFileBase + FilePath; String Ext = FilePath.GetExtension(); if ( Ext.CompareIgnoreCaseToAscii("Win") == COMPARE_EQUAL ) { ReadNames( FilePath.GetFull(),m_pControls,pUIds); pImpl->bLnaguageExtensionLoaded = sal_True; SfxSimpleHint aHint( SBX_HINT_LANGUAGE_EXTENSION_LOADED ); GetTTBroadcaster().Broadcast( aHint ); } else if ( Ext.CompareIgnoreCaseToAscii("Sid") == COMPARE_EQUAL ) { ReadNames( FilePath.GetFull(),m_pSIds,pUIds,FLAT); pImpl->bLnaguageExtensionLoaded = sal_True; SfxSimpleHint aHint( SBX_HINT_LANGUAGE_EXTENSION_LOADED ); GetTTBroadcaster().Broadcast( aHint ); } else if ( Ext.CompareIgnoreCaseToAscii("Bin") == COMPARE_EQUAL ) { ReadNamesBin( FilePath.GetFull(), m_pSIds, m_pControls ); pImpl->bLnaguageExtensionLoaded = sal_True; SfxSimpleHint aHint( SBX_HINT_LANGUAGE_EXTENSION_LOADED ); GetTTBroadcaster().Broadcast( aHint ); } else if ( Ext.CompareIgnoreCaseToAscii("Inc") == COMPARE_EQUAL ) { { TTExecutionStatusHint aHint( TT_EXECUTION_SHOW_ACTION, String(SttResId(S_READING_BASIC_MODULE)), FilePath.GetFull() ); GetTTBroadcaster().Broadcast( aHint ); } String aFullPathname = FilePath.GetFull(); StarBASIC *pBasic = (StarBASIC*)GetParent(); if ( !aModuleWinExistsHdl.Call( &aFullPathname ) && !pBasic->FindModule( CUniString( "--" ).Append(aFullPathname) ) ) { SbModule *pMod; pMod = pBasic->MakeModule( CUniString("--"), String() ); pMod->Clear(); if ( Load( aFullPathname, pMod ) ) { if ( !IS_ERROR() ) { pBasic->Compile( pMod ); pMod->RunInit(); } } else { ADD_ERROR( SbxERR_CANNOT_LOAD, FilePath.GetFull() ); } } { TTExecutionStatusHint aHint( TT_EXECUTION_HIDE_ACTION ); GetTTBroadcaster().Broadcast( aHint ); } } else { ADD_ERROR(SbxERR_CANNOT_LOAD,FilePath.GetFull()); } } else SetError( SbxERR_WRONG_ARGS ); break; case ID_FinishUse: if ( !rPar ) // rPar = NULL <=> Kein Parameter { ADD_CASE_LOG( String() ); // Case abschliessen if (!m_pControls) m_pControls = new CNames(); if (!m_pSIds) m_pSIds = new CNames(); if (pUIds) { // save some memory delete pUIds; pUIds = NULL; } m_pNameKontext = m_pControls; if ( pImpl->bLnaguageExtensionLoaded ) { SfxSimpleHint aHint( SBX_HINT_LANGUAGE_EXTENSION_LOADED ); GetTTBroadcaster().Broadcast( aHint ); } pImpl->nIncludeFileWarningCount = pImpl->nWarningCount; pImpl->nWarningCount = 0; *pImpl->xIncludeFileWarningList = *pImpl->xWarningList; pImpl->xWarningList->SbxArray::Clear(); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_CaseLog: if ( rPar ) // rPar != NULL <=> Es gibt Parameter { sal_uInt16 n; String aX; for ( n = 1; n < rPar->Count(); n++ ) { SbxVariableRef pArg = rPar->Get( n ); aX += pArg->GetString(); } pImpl->aTestCaseName = aX; if ( pImpl->aTestCaseName.Len() && BasicRuntimeAccess::HasRuntime() ) { BasicRuntime aRun = BasicRuntimeAccess::GetRuntime(); pImpl->aTestCaseFileName = aRun.GetModuleName(SbxNAME_SHORT_TYPES); if ( pImpl->aTestCaseFileName.Copy(0,2).CompareToAscii( "--" ) == COMPARE_EQUAL ) pImpl->aTestCaseFileName.Erase(0,2); pImpl->nTestCaseLineNr = aRun.GetLine(); } else { pImpl->aTestCaseFileName.Erase(); pImpl->nTestCaseLineNr = 0; } ADD_CASE_LOG( aX ); } break; case ID_ExceptLog: if ( IS_ERROR() ) { BasicRuntime aRun = BasicRuntimeAccess::GetRuntime(); sal_Bool bWasNewError = sal_False; if ( BasicRuntimeAccess::HasStack() ) { for ( sal_uInt16 i = 0 ; i < BasicRuntimeAccess::GetStackEntryCount() -1 ; i++ ) { BasicErrorStackEntry aThisEntry = BasicRuntimeAccess::GetStackEntry(i); if ( !bWasNewError ) { bWasNewError = sal_True; ADD_ERROR_LOG( GET_ERROR()->aText, aThisEntry.GetModuleName(SbxNAME_SHORT_TYPES), aThisEntry.GetLine(), aThisEntry.GetCol1(), aThisEntry.GetCol2(), aThisEntry.GetSourceRevision() ); } ADD_CALL_STACK_LOG( String(aThisEntry.GetModuleName(SbxNAME_SHORT_TYPES)) .AppendAscii(": ").Append(aThisEntry.GetMethodName(SbxNAME_SHORT_TYPES)), aThisEntry.GetModuleName(SbxNAME_SHORT_TYPES), aThisEntry.GetLine(), aThisEntry.GetCol1(), aThisEntry.GetCol2() ); } BasicRuntimeAccess::DeleteStack(); } sal_Bool bIsFirst = sal_True; while ( aRun.IsValid() ) { xub_StrLen nErrLn; xub_StrLen nCol1; xub_StrLen nCol2; if ( bIsFirst ) { bIsFirst = sal_False; nErrLn = GET_ERROR()->nLine; nCol1 = GET_ERROR()->nCol1; nCol2 = GET_ERROR()->nCol2; } else { nErrLn = aRun.GetLine(); nCol1 = aRun.GetCol1(); nCol2 = aRun.GetCol2(); } if ( !bWasNewError ) { bWasNewError = sal_True; ADD_ERROR_LOG( GET_ERROR()->aText, aRun.GetModuleName(SbxNAME_SHORT_TYPES), nErrLn, nCol1, nCol2, aRun.GetSourceRevision() ); } ADD_CALL_STACK_LOG( String(aRun.GetModuleName(SbxNAME_SHORT_TYPES)) .AppendAscii(": ").Append(aRun.GetMethodName(SbxNAME_SHORT_TYPES)), aRun.GetModuleName(SbxNAME_SHORT_TYPES), nErrLn, nCol1, nCol2 ); aRun = aRun.GetNextRuntime(); } } break; case ID_ErrorLog: if ( IS_ERROR() ) { BasicRuntime aRun = BasicRuntimeAccess::GetRuntime(); if ( BasicRuntimeAccess::HasStack() ) { BasicErrorStackEntry aThisEntry = BasicRuntimeAccess::GetStackEntry( 0 ); ADD_ERROR_LOG( GET_ERROR()->aText, aThisEntry.GetModuleName(SbxNAME_SHORT_TYPES), aThisEntry.GetLine(), aThisEntry.GetCol1(), aThisEntry.GetCol2(), aThisEntry.GetSourceRevision() ); BasicRuntimeAccess::DeleteStack(); } else { ADD_ERROR_LOG( GET_ERROR()->aText, aRun.GetModuleName(SbxNAME_SHORT_TYPES), StarBASIC::GetErl(), aRun.GetCol1(), aRun.GetCol2(), aRun.GetSourceRevision() ); } } break; case ID_QAErrorLog: if ( rPar ) // rPar != NULL <=> Es gibt Parameter { sal_uInt16 n; String aSammel; for ( n = 1; n < rPar->Count(); n++ ) { SbxVariableRef pArg = rPar->Get( n ); aSammel += pArg->GetString(); } ADD_QA_ERROR_LOG( aSammel ); } break; case ID_PrintLog: if ( rPar ) // rPar != NULL <=> Es gibt Parameter { sal_uInt16 n; String aSammel; for ( n = 1; n < rPar->Count(); n++ ) { SbxVariableRef pArg = rPar->Get( n ); aSammel += pArg->GetString(); } ADD_MESSAGE_LOG( aSammel ); } break; case ID_WarnLog: if ( rPar ) // rPar != NULL <=> Es gibt Parameter { sal_uInt16 n; String aSammel; for ( n = 1; n < rPar->Count(); n++ ) { SbxVariableRef pArg = rPar->Get( n ); aSammel += pArg->GetString(); } ADD_WARNING_LOG( aSammel ); } break; case ID_ClearError: while ( IS_ERROR() ) { POP_ERROR(); } break; case ID_MaybeAddErr: if ( ((StarBASIC*)GetParent())->GetErrBasic() && ( !IS_ERROR() || pFehlerListe->GetObject(pFehlerListe->Count()-1)->nError != ((StarBASIC*)GetParent())->GetErrBasic() ) ) { ((StarBASIC*)GetParent())->MakeErrorText(((StarBASIC*)GetParent())->GetErrBasic(),String()); ADD_ERROR_QUIET(((StarBASIC*)GetParent())->GetErrBasic() , ((StarBASIC*)GetParent())->GetErrorText()) } break; case ID_GetNextCloseWindow: if ( !rPar ) // rPar = NULL <=> Kein Parameter { SetError( SbxERR_NOTIMP ); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_RemoteCommand: { if ( SingleCommandBlock ) BeginBlock(); else if ( ((SbxTransportMethod*)pVar)->nValue & M_WITH_RETURN ) { SetError( SbxERR_NOTIMP ); } if ( !IsError() ) In->GenCmdCommand ((sal_uInt16)(((SbxTransportMethod*)pVar)->nValue),rPar); if ( !IsError() && ((SbxTransportMethod*)pVar)->nValue & M_WITH_RETURN ) { pImpl->pNextReturn = ((SbxTransportMethod*)pVar); // FIXME: HELPID aNextReturnId = rtl::OString();// ((SbxTransportMethod*)pVar)->nValue ); } if ( SingleCommandBlock ) EndBlock(); if ( !IsError() && (sal_uInt16)((SbxTransportMethod*)pVar)->nValue & M_WITH_RETURN ) { WaitForAnswer(); } // f�r einige noch etwas Nachbehandlung switch ( ((SbxTransportMethod*)pVar)->nValue ) { case RC_WinTree: break; } } break; case ID_Dispatch: if ( !rPar || (rPar->Count() % 2) == 1 ) // rPar = NULL <=> Kein Parameter ansonsten Gerade Anzahl(Ungerade, da immer Anzahl+1 { if ( SingleCommandBlock ) BeginBlock(); if ( !IsError() ) In->GenCmdSlot ( (sal_uInt16)((SbxTransportMethod*)pVar)->nValue, rPar ); pVar->PutInteger( (sal_uInt16)((SbxTransportMethod*)pVar)->nValue ); if ( SingleCommandBlock ) EndBlock(); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_UNODispatch: if ( !rPar ) // rPar = NULL <=> Kein Parameter ansonsten Gerade Anzahl(Ungerade, da immer Anzahl+1 { if ( SingleCommandBlock ) BeginBlock(); if ( !IsError() ) In->GenCmdUNOSlot ( ((SbxTransportMethod*)pVar)->aUnoSlot ); pVar->PutString( ((SbxTransportMethod*)pVar)->aUnoSlot ); if ( SingleCommandBlock ) EndBlock(); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_Control: case ID_StringControl: // if only the object is given in the script we don't have to do anything (object stands for itself) if ( !pVar->ISA( SbxObject ) ) { if ( SingleCommandBlock ) BeginBlock(); else if ( ((SbxTransportMethod*)pVar)->nValue & M_WITH_RETURN ) { SetError( SbxERR_NOTIMP ); } if ( !IsError() ) { SbxVariable *pMember = NULL; if ( pVar->GetParent() ) pMember = pVar->GetParent()->Find(CUniString("ID"),SbxCLASS_DONTCARE); if ( pMember == NULL ) { SetError( SbxERR_NAMED_NOT_FOUND ); } else { if ( nHintUserData == ID_Control ) { In->GenCmdControl (pMember->GetULong(), (sal_uInt16)((SbxTransportMethod*)pVar)->nValue, rPar); // FIXME: HELPID aNextReturnId = rtl::OString();// pMember->GetULong() ); } else { In->GenCmdControl (pMember->GetString(), (sal_uInt16)((SbxTransportMethod*)pVar)->nValue, rPar); // FIXME: HELPID #if 0 aNextReturnId = rtl::OString( pMember->GetString() ); #endif } } if ( !IsError() && ((SbxTransportMethod*)pVar)->nValue & M_WITH_RETURN ) { pImpl->pNextReturn = ((SbxTransportMethod*)pVar); } else { pImpl->pNextReturn = NULL; aNextReturnId = rtl::OString(); } } if ( SingleCommandBlock ) EndBlock(); if ( !IsError() && (sal_uInt16)((SbxTransportMethod*)pVar)->nValue & M_WITH_RETURN ) { WaitForAnswer(); } } break; case ID_GetUnoApp: { // Hier wird der Remote UNO Kram gestartet // Eintrag in die Konfiguration unter // org.openoffice.Office.Common/Start/Connection // socket,host=0,port=12345;iiop;XBla // oder // socket,host=0,port=12345;urp;;XBla String aString; aString.AppendAscii( "socket,host=" ); aString += GetHostConfig(); aString.AppendAscii( ",port=" ); aString += String::CreateFromInt32( GetUnoPortConfig() ); Reference< XMultiServiceFactory > smgr_xMultiserviceFactory; try { Reference< XMultiServiceFactory > xSMgr = comphelper::getProcessServiceFactory(); OUString aURL( aString ); Reference< XConnector > xConnector( xSMgr->createInstance( OUString( RTL_CONSTASCII_USTRINGPARAM("com.sun.star.connection.Connector") ) ), UNO_QUERY ); Reference< XConnection > xConnection( xConnector->connect( aURL ) ); Reference< XBridgeFactory > xBridgeFactory( xSMgr->createInstance( OUString( RTL_CONSTASCII_USTRINGPARAM("com.sun.star.bridge.BridgeFactory") ) ), UNO_QUERY ); Reference< XBridge > xBridge( xBridgeFactory->createBridge( OUString(), OUString( RTL_CONSTASCII_USTRINGPARAM("urp") ), xConnection, Reference< XInstanceProvider >() ) ); Reference< XInterface > xRet( xBridge->getInstance( OUString( RTL_CONSTASCII_USTRINGPARAM("StarOffice.ServiceManager")) ) ); smgr_xMultiserviceFactory = Reference< XMultiServiceFactory >(xRet, UNO_QUERY); //MBA fragen!! } catch( class Exception & rEx) { ADD_ERROR(SbxERR_BAD_ACTION, String( rEx.Message ) ); } catch( ... ) { ADD_ERROR(SbxERR_BAD_ACTION, CUniString( "Unknown Error" ) ); } if( smgr_xMultiserviceFactory.is() ) { Any aAny; aAny <<= smgr_xMultiserviceFactory; SbxObjectRef xMySbxObj = GetSbUnoObject( CUniString("RemoteUnoAppFuerTesttool"), aAny ); if ( xMySbxObj.Is() ) pVar->PutObject( xMySbxObj ); } } break; case ID_GetIServer: { // Hier wird der Remote UNO Kram gestartet String aString; Reference< XMultiServiceFactory > xSMgr; { xSMgr = ::cppu::createRegistryServiceFactory(OUString(RTL_CONSTASCII_USTRINGPARAM("g:\\iserverproxy.rdb")), sal_True); } OUString aURL( aString ); Reference< XConnector > xConnector( xSMgr->createInstance( OUString( RTL_CONSTASCII_USTRINGPARAM("com.sun.star.connection.Connector") ) ), UNO_QUERY ); Reference< XConnection > xConnection( xConnector->connect( OUString( RTL_CONSTASCII_USTRINGPARAM("socket,host=grande,port=7453")) ) ); Reference< XBridgeFactory > xBridgeFactory( xSMgr->createInstance( OUString( RTL_CONSTASCII_USTRINGPARAM("com.sun.star.bridge.BridgeFactory") ) ), UNO_QUERY ); Reference< XBridge > xBridge( xBridgeFactory->createBridge( OUString(), OUString( RTL_CONSTASCII_USTRINGPARAM("urp") ), xConnection, Reference< XInstanceProvider >() ) ); Reference< XInterface > xRet( xBridge->getInstance( OUString( RTL_CONSTASCII_USTRINGPARAM("XIServerProxy")) ) ); if( xRet.is() ) { Any aAny; aAny <<= xRet; SbxObjectRef xMySbxObj = GetSbUnoObject( CUniString("IServerProxy"), aAny ); if ( xMySbxObj.Is() ) pVar->PutObject( xMySbxObj ); } // In Basic: // msgbox dbg_SupportedInterfaces // msgbox dbg_Properties // msgbox dbg_Methods } break; case ID_RemoteCommandDelay: if ( rPar && rPar->Count() >= 2 && rPar->Count() <=3 ) { switch (rPar->Get( 1 )->GetType()) { case SbxLONG: // alles immer als Short �bertragen case SbxULONG: case SbxSALINT64: case SbxSALUINT64: case SbxDOUBLE: case SbxINTEGER: case SbxBYTE: case SbxUSHORT: case SbxINT: case SbxUINT: case SbxSINGLE: pImpl->nMinRemoteCommandDelay = rPar->Get( 1 )->GetULong(); if ( rPar->Count() == 3 ) pImpl->nMaxRemoteCommandDelay = rPar->Get( 2 )->GetULong(); else pImpl->nMaxRemoteCommandDelay = pImpl->nMinRemoteCommandDelay; break; case SbxBOOL: pImpl->bDoRemoteCommandDelay = rPar->Get( 1 )->GetBool(); break; default: SbxBase::SetError( SbxERR_WRONG_ARGS ); break; } } else SetError( SbxERR_WRONG_ARGS ); break; case ID_GetApplicationPath: if ( !rPar ) { OUString aUrl = Config::GetDefDirectory(); OUString aPath; osl::FileBase::getSystemPathFromFileURL( aUrl, aPath ); pVar->PutString( String( aPath ) ); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_GetCommonApplicationPath: if ( !rPar ) { #ifdef WNT //////// adapted this from setup2\win\source\system\winos.cxx String aSysPath; aSysPath = _SHGetSpecialFolder_COMMON_APPDATA(); if ( aSysPath.Len() ) { pVar->PutString( aSysPath ); } else // default to ID_GetApplicationPath (same as in setup) { OUString aUrl = Config::GetDefDirectory(); OUString aPath; osl::FileBase::getSystemPathFromFileURL( aUrl, aPath ); pVar->PutString( String( aPath ) ); } #elif defined OS2 { char* etc = getenv("ETC"); if (etc) pVar->PutString( CUniString( etc ) ); else pVar->PutString( CUniString( "/etc" ) ); } #else #if UNX pVar->PutString( CUniString( "/etc" ) ); #else #error not implemented #endif #endif } else SetError( SbxERR_WRONG_ARGS ); break; case ID_MakeIniFileName: if ( rPar && rPar->Count() == 2 ) { OUString aUrl = Config::GetConfigName( String(), rPar->Get( 1 )->GetString() ); OUString aPath; osl::FileBase::getSystemPathFromFileURL( aUrl, aPath ); pVar->PutString( String( aPath ) ); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_Wait: { if( rPar && rPar->Count() == 2 ) { long nWait = rPar->Get(1)->GetLong(); if( nWait >= 0 ) { #ifdef DEBUG Time aStart; #endif Timer aTimer; aTimer.SetTimeout( nWait ); aTimer.Start(); while ( aTimer.IsActive() ) Application::Yield(); #ifdef DEBUG Time aEnd; Time aDiff = aEnd - aStart; long aMS = long( aDiff.GetMSFromTime() ); if ( Abs( aMS - nWait ) > 100 ) { OSL_TRACE("Wait was off limit by %i", aDiff.GetMSFromTime() - nWait ); } #endif } } else SetError( SbERR_BAD_NUMBER_OF_ARGS ); } break; case ID_GetErrorCount: { pVar->PutULong( pImpl->nErrorCount ); } break; case ID_GetWarningCount: { pVar->PutULong( pImpl->nWarningCount ); } break; case ID_GetQAErrorCount: { pVar->PutULong( pImpl->nQAErrorCount ); } break; case ID_GetUseFileWarningCount: { pVar->PutULong( pImpl->nIncludeFileWarningCount ); } break; case ID_GetErrorList: { if ( ! pImpl->xErrorList->GetDims() ) pImpl->xErrorList->AddDim( 1, 32000 ); pVar->PutObject( pImpl->xErrorList ); } break; case ID_GetWarningList: { if ( ! pImpl->xWarningList->GetDims() ) pImpl->xWarningList->AddDim( 1, 32000 ); pVar->PutObject( pImpl->xWarningList ); } break; case ID_GetQAErrorList: { if ( ! pImpl->xQAErrorList->GetDims() ) pImpl->xQAErrorList->AddDim( 1, 32000 ); pVar->PutObject( pImpl->xQAErrorList ); } break; case ID_GetUseFileWarningList: { if ( ! pImpl->xIncludeFileWarningList->GetDims() ) pImpl->xIncludeFileWarningList->AddDim( 1, 32000 ); pVar->PutObject( pImpl->xIncludeFileWarningList ); } break; case ID_GetTestCaseName: { pVar->PutString( pImpl->aTestCaseName ); } break; case ID_GetTestCaseFileName: { pVar->PutString( pImpl->aTestCaseFileName ); } break; case ID_GetTestCaseLineNr: { pVar->PutUShort( pImpl->nTestCaseLineNr ); } break; case ID_SetChildEnv: { if( rPar && rPar->Count() == 3 ) { pImpl->pChildEnv->erase( rPar->Get(1)->GetString() ); pImpl->pChildEnv->insert( EnvironmentVariable( rPar->Get(1)->GetString(), rPar->Get(2)->GetString() ) ); } else SetError( SbERR_BAD_NUMBER_OF_ARGS ); } break; case ID_GetChildEnv: { if( rPar && rPar->Count() == 2 ) { Environment::const_iterator aIter = pImpl->pChildEnv->find( rPar->Get(1)->GetString() ); if ( aIter != pImpl->pChildEnv->end() ) pVar->PutString( (*aIter).second ); else pVar->PutString( String() ); } else SetError( SbERR_BAD_NUMBER_OF_ARGS ); } break; case ID_GetLinkDestination: { if( rPar && rPar->Count() == 2 ) { String aSource,aDest; aSource = rPar->Get(1)->GetString(); #ifdef UNX ByteString aByteSource( aSource, osl_getThreadTextEncoding() ); char cDest[1024]; int nLen = 0; if ( ( nLen = readlink( aByteSource.GetBuffer(), cDest, sizeof(cDest) ) ) >= 0 ) { aDest = String( cDest, nLen, osl_getThreadTextEncoding() ); } else { int nErr = errno; switch ( nErr ) { case EINVAL: aDest = aSource; break; default: SetError( SbERR_ACCESS_ERROR ); } } #else aDest = aSource; #endif pVar->PutString( aDest ); } else SetError( SbERR_BAD_NUMBER_OF_ARGS ); } break; case ID_GetRegistryValue: { if( rPar && rPar->Count() == 3 ) { String aValue; #ifdef WNT aValue = ReadRegistry( rPar->Get(1)->GetString(), rPar->Get(2)->GetString() ); #endif pVar->PutString( aValue ); } else SetError( SbERR_BAD_NUMBER_OF_ARGS ); } break; case ID_HTTPSend: { if( rPar && ( rPar->Count() == 4 || rPar->Count() == 5 ) ) { if ( !pImpl->pHttpRequest ) pImpl->pHttpRequest = new HttpRequest; pImpl->pHttpRequest->SetRequest( ByteString( rPar->Get(1)->GetString(), RTL_TEXTENCODING_ASCII_US ), ByteString( rPar->Get(2)->GetString(), RTL_TEXTENCODING_ASCII_US ), rPar->Get(3)->GetUShort() ); if ( pImpl->pHttpRequest->Execute() ) { if ( rPar->Count() == 5 ) { // filename is given SvFileStream aDestination( rPar->Get(4)->GetString(), STREAM_STD_READWRITE | STREAM_TRUNC ); (*(pImpl->pHttpRequest->GetBody())) >> aDestination; if ( aDestination.GetError() != ERRCODE_NONE ) SetError( SbERR_ACCESS_ERROR ); aDestination.Close(); } pVar->PutUShort( pImpl->pHttpRequest->GetResultId() ); } else SetError( SbERR_ACCESS_ERROR ); } else SetError( SbERR_BAD_NUMBER_OF_ARGS ); } break; case ID_HTTPSetProxy: { if( rPar && rPar->Count() == 3 ) { if ( !pImpl->pHttpRequest ) pImpl->pHttpRequest = new HttpRequest; pImpl->pHttpRequest->SetProxy( ByteString( rPar->Get(1)->GetString(), RTL_TEXTENCODING_ASCII_US ), rPar->Get(2)->GetUShort() ); } else SetError( SbERR_BAD_NUMBER_OF_ARGS ); } break; } // switch( nHintUserData ) } // if( nHintId == SBX_HINT_DATAWANTED ) else if( nHintId == SBX_HINT_DATACHANGED ) { switch( nHintUserData ) { case ID_AutoExecute: if ( !rPar ) // rPar = NULL <=> Kein Parameter { SingleCommandBlock = pVar->GetBool(); if ( SingleCommandBlock ) EndBlock(); else BeginBlock(); } else SetError( SbxERR_WRONG_ARGS ); break; case ID_EnableQaErrors: if ( !rPar ) // rPar = NULL <=> Kein Parameter pImpl->bEnableQaErrors = pVar->GetBool(); else SetError( SbxERR_WRONG_ARGS ); break; } } // if( nHintId == SBX_HINT_DATACHANGED ) else if( nHintId == SBX_HINT_BASICSTART ) { pImpl->nErrorCount = 0; pImpl->nWarningCount = 0; pImpl->nQAErrorCount = 0; pImpl->nIncludeFileWarningCount = 0; pImpl->xErrorList->SbxArray::Clear(); // call SbxArray::Clear because SbxVarArray::Clear only clears dimensions but no content pImpl->xWarningList->SbxArray::Clear(); // call SbxArray::Clear because SbxVarArray::Clear only clears dimensions but no content pImpl->xQAErrorList->SbxArray::Clear(); // call SbxArray::Clear because SbxVarArray::Clear only clears dimensions but no content pImpl->xIncludeFileWarningList->SbxArray::Clear(); // call SbxArray::Clear because SbxVarArray::Clear only clears dimensions but no content if (pFehlerListe) delete pFehlerListe; pFehlerListe = new CErrors; for (sal_uInt16 i=0;ipMyVars[i]->SetName( CUniString("VarDummy").Append(UniString::CreateFromInt32(i)) ); } nMyVar = 0; } // if( nHintId == SBX_HINT_BASICSTART ) else if( nHintId == SBX_HINT_BASICSTOP ) { // Log summary to journal ADD_CASE_LOG( String() ); // Case abschliessen ADD_MESSAGE_LOG( CUniString("***************************************************") ); if ( pImpl->nErrorCount ) { ADD_WARNING_LOG( GEN_RES_STR1( S_ERRORS_DETECTED, String::CreateFromInt32( pImpl->nErrorCount ) ) ); pImpl->nWarningCount--; // Anpassen, da diese Warnung nicht in die Statistik soll } else ADD_MESSAGE_LOG( GEN_RES_STR0( S_NO_ERRORS_DETECTED ) ); if ( pImpl->nWarningCount ) ADD_WARNING_LOG( GEN_RES_STR1( S_WARNINGS_DETECTED, String::CreateFromInt32( pImpl->nWarningCount ) ) ) else ADD_MESSAGE_LOG( GEN_RES_STR0( S_NO_WARNINGS_DETECTED ) ); if ( pImpl->nIncludeFileWarningCount ) ADD_WARNING_LOG( GEN_RES_STR1( S_INCLUDE_FILE_WARNINGS_DETECTED, String::CreateFromInt32( pImpl->nIncludeFileWarningCount ) ) ) else ADD_MESSAGE_LOG( GEN_RES_STR0( S_NO_INCLUDE_FILE_WARNINGS_DETECTED ) ); ADD_MESSAGE_LOG( CUniString("***************************************************") ); pImpl->nErrorCount = 0; pImpl->nWarningCount = 0; pImpl->nQAErrorCount = 0; pImpl->nIncludeFileWarningCount = 0; pImpl->xErrorList->SbxArray::Clear(); // call SbxArray::Clear because SbxVarArray::Clear only clears dimensions but no content pImpl->xWarningList->SbxArray::Clear(); // call SbxArray::Clear because SbxVarArray::Clear only clears dimensions but no content pImpl->xQAErrorList->SbxArray::Clear(); // call SbxArray::Clear because SbxVarArray::Clear only clears dimensions but no content pImpl->xIncludeFileWarningList->SbxArray::Clear(); // call SbxArray::Clear because SbxVarArray::Clear only clears dimensions but no content } // if( nHintId == SBX_HINT_BASICSTOP ) WaitForAnswer(); if ( IsError() && ( !IS_ERROR() || GET_ERROR()->nError != GetError() ) ) { ((StarBASIC*)GetParent())->MakeErrorText(GetError(),String()); ADD_ERROR_QUIET(GetError(),String(pVar->GetName()).AppendAscii(": "). Append(((StarBASIC*)GetParent())->GetErrorText())); } } } void TestToolObj::DebugFindNoErrors( sal_Bool bDebugFindNoErrors ) { pImpl->bDebugFindNoErrors = bDebugFindNoErrors; } SbxVariable* TestToolObj::Find( const String& aStr, SbxClassType aType) { if ( BasicRuntimeAccess::IsRunInit() || ( aStr == String( RTL_CONSTASCII_USTRINGPARAM( "ThisComponent" ) ) ) ) // wegen Find im "Global" Befehl des Basic return NULL; SbxVariableRef Old = SbxObject::Find(aStr, aType ); // do not return any objects from pMyVars[] if (Old && Old->GetUserData() != ID_Dispatch && Old->GetUserData() != ID_UNODispatch && Old->GetUserData() != ID_ErrorDummy && Old->GetUserData() != 0 ) return Old; else if ( aStr.SearchAscii(":") != STRING_NOTFOUND ) { // ignore qualified names e.g. main:FormWizard If this was removed an error would be generated } else { sal_uInt16 nElement; ControlDef *pWhatName = new ControlDef(aStr,rtl::OString()); /// nach Controls suchen if (m_pNameKontext && m_pNameKontext->Seek_Entry(pWhatName,&nElement)) { delete pWhatName; pWhatName = ((ControlDef*)m_pNameKontext->GetObject(nElement)); //// new Controls Object every time pImpl->pControlsObj = new Controls( pWhatName->pData->Kurzname ); pImpl->pControlsObj->SetType( SbxOBJECT ); pImpl->pControlsObj->ChangeListener( this ); // Will be set on method-child further down // FIXME: HELPID #if 0 if ( pWhatName->pData->aUId.HasNumeric() ) pImpl->pControlsObj->SetUserData( ID_Control ); else #endif pImpl->pControlsObj->SetUserData( ID_StringControl ); pShortNames->Insert(pWhatName->pData->Kurzname,pWhatName->pData->aUId,nSequence); SbxVariable *pMember = pImpl->pControlsObj->Find(CUniString("ID"),SbxCLASS_DONTCARE); if ( pMember == NULL ) { SbxProperty* pID = new SbxProperty(CUniString("ID"),SbxVARIANT); pImpl->pControlsObj->Insert(pID); pImpl->pControlsObj->SetDfltProperty(pID); pMember = pID; } // FIXME: HELPID #if 0 if ( pWhatName->pData->aUId.HasNumeric() ) pMember->PutULong(pWhatName->pData->aUId.GetNum()); else pMember->PutString(pWhatName->pData->aUId.GetStr()); #endif pMember = pImpl->pControlsObj->Find(CUniString("name"),SbxCLASS_DONTCARE); if ( pMember != NULL ) pMember->PutString(pWhatName->pData->Kurzname); return pImpl->pControlsObj; } /// Nach slots suchen if (m_pSIds && m_pSIds->Seek_Entry(pWhatName,&nElement)) { SbxTransportMethodRef pMyVar; pMyVar = pImpl->pMyVars[nMyVar++]; if ( nMyVar >= VAR_POOL_SIZE ) nMyVar = 0; delete pWhatName; pWhatName = ( (ControlDef*)m_pSIds->GetObject( nElement ) ); pMyVar->SetName( pWhatName->pData->Kurzname ); // FIXME: HELPID #if 0 if ( pWhatName->pData->aUId.HasNumeric() ) { pMyVar->SetUserData( ID_Dispatch ); pMyVar->nValue = pWhatName->pData->aUId.GetNum(); pShortNames->Insert( aStr, pWhatName->pData->aUId, nSequence ); } else { pMyVar->SetUserData( ID_UNODispatch ); pMyVar->aUnoSlot = pWhatName->pData->aUId.GetStr(); } #endif return pMyVar; } /// es kann sich noch um eine SlotID handeln, die numerisch abgefragt wird, statt ausgef�hrt zu werden if ( aStr.Copy( aStr.Len()-3, 3 ).CompareIgnoreCaseToAscii("_ID") == COMPARE_EQUAL && m_pSIds ) { delete pWhatName; pWhatName = new ControlDef( aStr.Copy( 0, aStr.Len()-3 ), rtl::OString() ); if ( m_pSIds->Seek_Entry( pWhatName, &nElement ) ) { // Nach slots suchen SbxVariable *pReturn = new SbxVariable; delete pWhatName; pWhatName = ( (ControlDef*)m_pSIds->GetObject( nElement ) ); pReturn->SetName( pWhatName->pData->Kurzname ); // FIXME: HELPID #if 0 if ( pWhatName->pData->aUId.HasNumeric() ) pReturn->PutULong(pWhatName->pData->aUId.GetNum()); else pReturn->PutString(pWhatName->pData->aUId.GetStr()); #endif return pReturn; } } if ( !pImpl->bDebugFindNoErrors ) { ADD_ERROR(SbxERR_PROC_UNDEFINED,GEN_RES_STR1(S_UNKNOWN_SLOT_CONTROL, aStr) ); } } return NULL; } String TestToolObj::GetRevision( String const &aSourceIn ) { // search $Revision: 1.40 $ xub_StrLen nPos; if ( ( nPos = aSourceIn.SearchAscii( "$Revision:" ) ) != STRING_NOTFOUND ) return aSourceIn.Copy( nPos+ 10, aSourceIn.SearchAscii( "$", nPos+10 ) -nPos-10); else return String::CreateFromAscii("No Revision found"); } sal_Bool TestToolObj::CError( sal_uLong code, const String& rMsg, xub_StrLen l, xub_StrLen c1, xub_StrLen c2 ) { bWasPrecompilerError = sal_True; if ( aCErrorHdl.IsSet() ) { ErrorEntry aErrorEntry( code, rMsg, l, c1, c2 ); return (sal_Bool)aCErrorHdl.Call( &aErrorEntry ); } else { ADD_ERROR( code, rMsg ) return sal_True; } } void TestToolObj::CalcPosition( String const &aSource, xub_StrLen nPos, xub_StrLen &l, xub_StrLen &c ) { l = 1; xub_StrLen nAkt = 0; xub_StrLen nNext; while ( (nNext = aSource.Search( '\n', nAkt )) != STRING_NOTFOUND && nNext < nPos ) { l++; nAkt = nNext+1; } c = nPos - nAkt; } #define CATCH_LABEL CUniString( "ctch" ) #define CATCHRES_LABEL CUniString( "ctchres" ) #define ENDCATCH_LABEL CUniString( "endctch" ) sal_Bool IsAlphaChar( sal_Unicode cChar ) { return ( cChar >= 'a' && cChar <= 'z' ) || ( cChar >= 'A' && cChar <= 'Z' ); } sal_Bool IsInsideString( const String& aSource, const xub_StrLen nStart ) { sal_Bool bInside = sal_False; xub_StrLen nPos = nStart-1; while ( nPos && aSource.GetChar(nPos) != _CR && aSource.GetChar(nPos) != _LF ) { if ( aSource.GetChar(nPos) == '"' ) bInside = !bInside; nPos--; } return bInside; } sal_Bool IsValidHit( const String& aSource, const xub_StrLen nStart, const xub_StrLen nEnd ) { return !IsAlphaChar( aSource.GetChar(nStart-1) ) && !IsAlphaChar( aSource.GetChar(nEnd+1)) && !IsInsideString( aSource, nStart ); } xub_StrLen TestToolObj::ImplSearch( const String &aSource, const xub_StrLen nStart, const xub_StrLen nEnd, const String &aSearch, const xub_StrLen nSearchStart ) { xub_StrLen nPos = aSource.Search( aSearch, std::max( nSearchStart, nStart ) ); if ( nPos > nEnd - aSearch.Len() || nPos == STRING_NOTFOUND ) return STRING_NOTFOUND; else { if ( IsValidHit( aSource, nPos, nPos+aSearch.Len()-1 ) ) return nPos; else return ImplSearch( aSource, nStart, nEnd, aSearch, nPos+aSearch.Len() ); } } xub_StrLen TestToolObj::PreCompilePart( String &aSource, xub_StrLen nStart, xub_StrLen nEnd, String aFinalErrorLabel, sal_uInt16 &nLabelCount ) { xub_StrLen nTry,nCatch,nEndcatch; if( (nTry = ImplSearch( aSource, nStart, nEnd, CUniString("try"), nStart )) == STRING_NOTFOUND ) return nEnd; if ( (nCatch = ImplSearch( aSource, nStart, nEnd, CUniString("catch"), nTry )) == STRING_NOTFOUND ) { xub_StrLen l,c; CalcPosition( aSource, nTry, l, c ); CError( SbERR_BAD_BLOCK, CUniString("catch"), l, c, c+2 ); return nEnd; } if ( (nEndcatch = ImplSearch( aSource, nStart, nEnd, CUniString("endcatch"), nCatch )) == STRING_NOTFOUND ) { xub_StrLen l,c; CalcPosition( aSource, nCatch, l, c ); CError( SbERR_BAD_BLOCK, CUniString("endcatch"), l, c, c+4 ); return nEnd; } nLabelCount++; String aStr = String::CreateFromInt32( nLabelCount ); String aCatchLabel(CATCH_LABEL); aCatchLabel += aStr; String aCatchresLabel(CATCHRES_LABEL); aCatchresLabel += aStr; String aEndcatchLabel( ENDCATCH_LABEL); aEndcatchLabel += aStr; xub_StrLen nTry2 = 0; while ( !WasPrecompilerError() && (nTry2 = ImplSearch( aSource, nStart, nEnd, CUniString("try"), nTry+1 )) != STRING_NOTFOUND ) { // Wir rekursieren erstmal mit dem 2. Try if ( nTry2 < nCatch ) nEnd += PreCompilePart( aSource, nTry2, nEndcatch+8, aCatchLabel, nLabelCount ) - nEndcatch-8; else nEnd = PreCompilePart( aSource, nTry2, nEnd, aFinalErrorLabel, nLabelCount ); if ( (nCatch = ImplSearch( aSource, nStart, nEnd, CUniString("catch"), nTry )) == STRING_NOTFOUND ) { xub_StrLen l,c; CalcPosition( aSource, nTry, l, c ); CError( SbERR_BAD_BLOCK, CUniString("catch"), l, c, c+2 ); return nEnd; } if ( (nEndcatch = ImplSearch( aSource, nStart, nEnd, CUniString("endcatch"), nCatch )) == STRING_NOTFOUND ) { xub_StrLen l,c; CalcPosition( aSource, nCatch, l, c ); CError( SbERR_BAD_BLOCK, CUniString("endcatch"), l, c, c+4 ); return nEnd; } } String aReplacement; int nTotalLength = -3 -5 -8; // try, catch und endcatch fallen raus aReplacement.AppendAscii( "on error goto " ); aReplacement += aCatchLabel; aSource.SearchAndReplaceAscii( "try", aReplacement, nTry ); nTotalLength += aReplacement.Len(); aReplacement.Erase(); aReplacement.AppendAscii( "on error goto " ); aReplacement += aFinalErrorLabel; aReplacement.AppendAscii( " : goto " ); aReplacement += aEndcatchLabel; aReplacement.AppendAscii( " : " ); aReplacement += aCatchLabel; aReplacement.AppendAscii( ": if err = 35 or err = 18 then : on error goto 0 : resume : endif" ); aReplacement.AppendAscii( " : MaybeAddErr : on error goto " ); aReplacement += aFinalErrorLabel; aReplacement.AppendAscii( " : resume " ); aReplacement += aCatchresLabel; aReplacement.AppendAscii( " : " ); aReplacement += aCatchresLabel; aReplacement.AppendAscii( ": " ); aSource.SearchAndReplaceAscii( "catch", aReplacement, nCatch ); nTotalLength += aReplacement.Len(); aReplacement.Erase(); aReplacement.AppendAscii("ClearError : "); aReplacement += aEndcatchLabel; aReplacement.AppendAscii(": "); aSource.SearchAndReplaceAscii( "endcatch", aReplacement, nEndcatch ); nTotalLength += aReplacement.Len(); if ( aSource.Len() >= STRING_MAXLEN ) { xub_StrLen l,c; CalcPosition( aSource, nEndcatch, l, c ); CError( SbERR_PROG_TOO_LARGE, CUniString("endcatch"), l, c, c+2 ); } return xub_StrLen( nEnd + nTotalLength ); } void TestToolObj::PreCompileDispatchParts( String &aSource, String aStart, String aEnd, String aFinalLable ) { sal_uInt16 nLabelCount = 0; xub_StrLen nPartPos = 0; while ( !WasPrecompilerError() && (nPartPos = ImplSearch( aSource, nPartPos, aSource.Len(), aStart )) != STRING_NOTFOUND ) { xub_StrLen nEndPart = ImplSearch( aSource, nPartPos, aSource.Len(), aEnd ); if ( nEndPart == STRING_NOTFOUND ) return; nPartPos = PreCompilePart( aSource, nPartPos, nEndPart, aFinalLable, nLabelCount ); nPartPos = nPartPos + aEnd.Len(); } } sal_Bool TestToolObj::WasPrecompilerError() { return bWasPrecompilerError; } String TestToolObj::PreCompile( String const &aSourceIn ) { // Im CTOR zu fr�h, und hier grade nicg rechtzeitig. Start und Stop von Programmausf�hrung StartListening( ((StarBASIC*)GetParent())->GetBroadcaster(), sal_True ); xub_StrLen nTestCase; xub_StrLen nEndCase; xub_StrLen nStartPos = 0; String aSource(aSourceIn); bWasPrecompilerError = sal_False; HACK("Ich gestehe alles: Ich war zu faul das richtig zu machen.") aSource = String(' ').Append( aSource ); // Da Schl�sselworte an Position 0 sonst nicht gefunden werden // Erstmal alle "'" Kommentare raus xub_StrLen nComment; while ( (nComment = aSource.SearchAscii("'",nStartPos)) != STRING_NOTFOUND ) { sal_uInt16 nStringEndCount = 0; xub_StrLen nIndex = nComment; while ( nIndex && aSource.GetChar(nIndex) != '\n' ) { if ( aSource.GetChar(nIndex) == '"' ) nStringEndCount++; nIndex--; } if ( (nStringEndCount & 1) == 0 ) // Wir waren also nicht innerhalb eines Strings { xub_StrLen nComEnd = aSource.SearchAscii("\n",nComment); while ( aSource.GetChar(nComEnd) == _CR || aSource.GetChar(nComEnd) == _LF ) nComEnd--; nComEnd++; aSource.Erase(nComment,nComEnd-nComment); } else nComment++; nStartPos = nComment; } PreCompileDispatchParts( aSource, CUniString("sub"), CUniString("end sub"), CUniString("0") ); PreCompileDispatchParts( aSource, CUniString("function"), CUniString("end function"), CUniString("0") ); PreCompileDispatchParts( aSource, CUniString("testcase"), CUniString("endcase"), CUniString("endcse") ); xub_StrLen nMainPos = ImplSearch( aSource, 0, aSource.Len(), CUniString("sub main") ); aSource.SearchAndReplaceAscii("sub main",CUniString("Sub Main StartUse : LoadIncludeFiles : FinishUse "), nMainPos ); if ( aSource.Len() >= STRING_MAXLEN ) { xub_StrLen l,c; CalcPosition( aSource, nMainPos, l, c ); CError( SbERR_PROG_TOO_LARGE, CUniString("endcatch"), l, c, c+2 ); } while ( (nTestCase = ImplSearch( aSource, 0, aSource.Len(), CUniString("testcase") ) ) != STRING_NOTFOUND ) { xub_StrLen nTcEnd = aSource.SearchAscii("\n",nTestCase); while ( aSource.GetChar(nTcEnd) == _CR || aSource.GetChar(nTcEnd) == _LF ) nTcEnd--; nTcEnd++; if ( aSource.SearchAscii(":",nTestCase) < nTcEnd ) nTcEnd = aSource.SearchAscii(":",nTestCase) -1; String aSuffix = aSource.Copy(nTestCase+8,nTcEnd-nTestCase-8); sal_uInt16 nOldLen; do { nOldLen = aSuffix.Len(); aSuffix.EraseLeadingAndTrailingChars( ' ' ); aSuffix.EraseLeadingAndTrailingChars( 0x09 ); } while ( nOldLen != aSuffix.Len() ); aSource.Erase(nTestCase,nTcEnd-nTestCase); aSource.Insert(CUniString("Sub ").Append(aSuffix).AppendAscii(" CaseLog \"").Append(aSuffix).AppendAscii("\" : on error goto endcse : TestEnter "),nTestCase); } ///////////////////////////////////////////////////////////////////////////////////////////////////////// // Attention!!! The lable endsub is officially used to exit a sub instead of using 'exit sub' or 'return' ///////////////////////////////////////////////////////////////////////////////////////////////////////// while ( (nEndCase = ImplSearch( aSource, 0, aSource.Len(), CUniString("endcase") ) ) != STRING_NOTFOUND ) aSource.SearchAndReplaceAscii("endcase",CUniString("goto endsub : endcse: if ( err = 35 and StopOnSyntaxError ) or err = 18 then : on error goto 0 : resume : endif : MaybeAddErr : ExceptLog : resume endcse_res : endcse_res: on error goto 0 : endsub: TestExit : ClearError : CaseLog \"\" : end sub "), nEndCase ); if ( aSource.Len() >= STRING_MAXLEN ) { xub_StrLen l,c; CalcPosition( aSource, 0, l, c ); CError( SbERR_PROG_TOO_LARGE, CUniString("endcatch"), l, c, c+2 ); } return aSource; } void TestToolObj::AddToListByNr( CNames *&pControls, ControlItemUId *&pNewItem ) { sal_uInt16 nNr; if ( pControls->Seek_Entry( pNewItem, &nNr ) ) { AddName( pControls->GetObject(nNr)->pData->Kurzname, pNewItem->pData->Kurzname ); delete pNewItem; pNewItem = (ControlItemUId*)pControls->GetObject(nNr); // f�r einf�gen der S�hne } else { ControlItem* pNI = pNewItem; pControls->C40_PTR_INSERT(ControlItem,pNI); } } IMPL_LINK( TestToolObj, ReturnResultsLink, CommunicationLink*, pCommLink ) { return ReturnResults( pCommLink->GetServiceData() ); } void TestToolObj::ReadHidLstByNumber() { // Die Hid.Lst nach Nummern sortiert einlesen if ( !m_pReverseUIds ) { String aName = (pImpl->aHIDDir + DirEntry(CUniString("hid.lst"))).GetFull(); { TTExecutionStatusHint aHint( TT_EXECUTION_SHOW_ACTION, String(SttResId(S_READING_LONGNAMES)), aName ); GetTTBroadcaster().Broadcast( aHint ); } ReadFlat( aName, m_pReverseUIds, sal_False ); { TTExecutionStatusHint aHint( TT_EXECUTION_HIDE_ACTION ); GetTTBroadcaster().Broadcast( aHint ); } } } void TestToolObj::SortControlsByNumber( sal_Bool bIncludeActive ) { // Die Controls einmal hirarchisch und einmal alle flach nach nummer sortiert if ( !m_pReverseControls && !m_pReverseControlsSon && m_pControls ) { m_pReverseControls = new CNames; m_pReverseControlsSon = new CNames; sal_uInt16 nWin,nCont; const String aSl('/'); for ( nWin = 0 ; nWin < m_pControls->Count() ; nWin++ ) { String aFatherName( m_pControls->GetObject(nWin)->pData->Kurzname ); ControlItemUId *pNewFather = new ControlItemUIdSon(aFatherName,m_pControls->GetObject(nWin)->pData->aUId); AddToListByNr( m_pReverseControlsSon, pNewFather ); if (! ((ControlItemUIdSon*)pNewFather)->GetSons() ) ((ControlItemUIdSon*)pNewFather)->Sons( new CNames ); // Existieren S�hne, diese in beide Listen eintragen CNames *pControlList = ((ControlItemSon*)m_pControls->GetObject(nWin))->GetSons(); if ( pControlList ) for ( nCont = 0 ; nCont < pControlList->Count() ; nCont++ ) { ControlItemUId *pNewItem; String aCombinedName( aFatherName ); aCombinedName.AppendAscii( ":" ); aCombinedName.Append( pControlList->GetObject(nCont)->pData->Kurzname ); pNewItem = new ControlItemUId( aCombinedName, pControlList->GetObject(nCont)->pData->aUId ); AddToListByNr( m_pReverseControls, pNewItem ); pNewItem = new ControlItemUId( pControlList->GetObject(nCont)->pData->Kurzname, pControlList->GetObject(nCont)->pData->aUId ); AddToListByNr( ((ControlItemUIdSon*)pNewFather)->GetSons(), pNewItem ); } } if ( !bIncludeActive ) { // FIXME: HELPID ControlItem *pZeroItem = new ControlItemUId( UniString(), rtl::OString() ); sal_uInt16 nNr; if ( m_pReverseControls->Seek_Entry( pZeroItem, &nNr ) ) { m_pReverseControls->DeleteAndDestroy( nNr ); // um VorlagenLaden/UntergeordneteIniDatei/SpeichernDlg/OrdnerDlg/OeffnenDlg/MessageBox/LetzteVersion/GrafikEinfuegenDlg/FarbeDlg/ExportierenDlg/DruckerEinrichten/DruckenDlg/DateiEinfuegenDlg/Active zu verhindern } delete pZeroItem; } } } sal_Bool TestToolObj::ReturnResults( SvStream *pIn ) { sal_uInt16 nId; sal_uLong nClearSequence = 0; sal_Bool bSequenceOK = sal_True; CNames *pReverseControlsKontext = NULL; CRetStream *pRetStream = new CRetStream(pIn); pRetStream->Read( nId ); while( !pIn->IsEof() ) { switch( nId ) { case SIReturn: { sal_uInt16 nRet,nParams; rtl::OString aUId; pRetStream->Read(nRet); if ( pRetStream->GetNextType() == BinString ) { String aUStrId; // UniqueStringID Used for Mozilla Integration pRetStream->Read( aUStrId ); // FIXME: HELPID #if 0 aUId = rtl::OString( aUStrId ); #endif } else { comm_ULONG nUId; pRetStream->Read( nUId ); // bei Sequence einfach die Sequence // FIXME: HELPID #if 0 aUId = rtl::OString( nUId ); #endif } pRetStream->Read(nParams); sal_uInt16 nNr1 = 0; comm_ULONG nLNr1 = 0; String aString1; sal_Bool bBool1 = sal_False; SbxValueRef xValue1 = new SbxValue; if( nParams & PARAM_USHORT_1 ) pRetStream->Read( nNr1 ); if( nParams & PARAM_ULONG_1 ) pRetStream->Read( nLNr1 ); if( nParams & PARAM_STR_1 ) { pRetStream->Read( aString1 ); ReplaceNumbers ( aString1 ); } else aString1.Erase(); if( nParams & PARAM_BOOL_1 ) pRetStream->Read( bBool1 ); if( nParams & PARAM_SBXVALUE_1 ) pRetStream->Read( *xValue1 ); switch (nRet) { case RET_Sequence: { // FIXME: HELPID #if 0 sal_uLong nUId = aUId.GetNum(); if ( nSequence != nUId ) { bSequenceOK = sal_False; ADD_ERROR(SbxERR_BAD_ACTION, GEN_RES_STR2(S_RETURN_SEQUENCE_MISSMATCH, String::CreateFromInt64(nUId), String::CreateFromInt64(nSequence)) ); } else { nClearSequence = nUId; } #endif } break; case RET_Value: if ( pImpl->pNextReturn ) { if ( aNextReturnId.equals( aUId ) ) { if( nParams & PARAM_ULONG_1 ) // FIXME this is to allow negative numbers, hoping that no large numbers are interpreted wrong. should have new PARAM_LONG_1 instead { if ( nLNr1 > 0x7fffffff ) pImpl->pNextReturn->PutLong( long(nLNr1 - 0xffffffff) -1 ); else pImpl->pNextReturn->PutULong( nLNr1 ); } if( nParams & PARAM_USHORT_1 ) pImpl->pNextReturn->PutUShort( nNr1 ); if( nParams & PARAM_STR_1 ) pImpl->pNextReturn->PutString( aString1 ); if( nParams & PARAM_BOOL_1 ) pImpl->pNextReturn->PutBool( bBool1 ); if( nParams & PARAM_SBXVALUE_1 ) // FIXME: allow generic datatype { SbxValues aValues( SbxDATE ); xValue1->Get( aValues ); pImpl->pNextReturn->Put( aValues ); } } else { ADD_ERROR(SbxERR_BAD_ACTION, GEN_RES_STR0(S_RETURNED_VALUE_ID_MISSMATCH) ) } pImpl->pNextReturn = NULL; } else { ADD_ERROR(SbxERR_BAD_ACTION, GEN_RES_STR0(S_RETURNED_VALUE_NO_RECEIVER) ) } break; case RET_WinInfo: { if ( !m_pReverseControls && !m_pReverseControlsSon ) pReverseControlsKontext = NULL; ReadHidLstByNumber(); SortControlsByNumber(); // Alle Slots nach Nummer Sortiert if ( !m_pReverseSlots && m_pSIds ) { m_pReverseSlots = new CNames; sal_uInt16 nWin; const String aSl('/'); for ( nWin = 0 ; nWin < m_pSIds->Count() ; nWin++ ) { ControlItemUId *pNewItem = new ControlItemUId(m_pSIds->GetObject(nWin)->pData->Kurzname,m_pSIds->GetObject(nWin)->pData->aUId); AddToListByNr( m_pReverseSlots, pNewItem ); } } WinInfoRec *pWinInfo = new WinInfoRec; // FIXME: HELPID #if 0 pWinInfo->aUId = aUId.GetText(); #endif pWinInfo->nRType = (sal_uInt16)nLNr1; // just sal_uLong for Transport, data is always USHORT pWinInfo->aRName = aString1; pWinInfo->bIsReset = bBool1; pWinInfo->aKurzname.Erase(); pWinInfo->aSlotname.Erase(); // eventuell den Kontext feststellen. Passiert nur beim ersten Eintrag nach reset if ( !pReverseControlsKontext && m_pReverseControlsSon ) { sal_uInt16 nNr; ControlItem *pNewItem = new ControlItemUId( String(), aUId ); if ( m_pReverseControlsSon->Seek_Entry(pNewItem,&nNr) ) { pReverseControlsKontext = ((ControlItemUIdSon*)m_pReverseControlsSon->GetObject(nNr))->GetSons(); pWinInfo->aKurzname = CUniString("*"); } else pReverseControlsKontext = m_pReverseControls; delete pNewItem; } // Reset. Mu� nach bestimmen des Kontext stehen, da sonst mit dem reset-record // der Kontext falsch gesetzt wird. if ( pWinInfo->bIsReset ) pReverseControlsKontext = NULL; // Reihenfolge wichtig! // Kurzname feststellen if ( pReverseControlsKontext ) { sal_uInt16 nNr; ControlItem *pNewItem = new ControlItemUId( String(), aUId ); if ( pReverseControlsKontext->Seek_Entry(pNewItem,&nNr) ) { pWinInfo->aKurzname += pReverseControlsKontext->GetObject(nNr)->pData->Kurzname; } delete pNewItem; } // Slotname feststellen if ( m_pReverseSlots ) { sal_uInt16 nNr; ControlItem *pNewItem = new ControlItemUId( String(), aUId ); if ( m_pReverseSlots->Seek_Entry(pNewItem,&nNr) ) pWinInfo->aSlotname = m_pReverseSlots->GetObject(nNr)->pData->Kurzname; delete pNewItem; } // Langname feststellen // FIXME: HELPID #if 0 if ( aUId.HasString() ) { // use the String ID since there is no LongName in hid.lst pWinInfo->aLangname = aUId.GetStr(); } else { if ( m_pReverseUIds ) { sal_uInt16 nNr; ControlItem *pNewItem = new ControlItemUId( String(), aUId ); if ( m_pReverseUIds->Seek_Entry(pNewItem,&nNr) ) pWinInfo->aLangname = m_pReverseUIds->GetObject(nNr)->pData->Kurzname; delete pNewItem; } } #endif aWinInfoHdl.Call( pWinInfo ); delete pWinInfo; } break; case RET_ProfileInfo: { // FIXME: HELPID #if 0 sal_uLong nUId = aUId.GetNum(); if ( nParams & PARAM_STR_1 ) { DirEntry FilePath = pImpl->aLogFileBase + DirEntry(DirEntry(aLogFileName).GetBase().AppendAscii(".prf")); SvFileStream aStrm( FilePath.GetFull(), STREAM_STD_WRITE ); if( aStrm.IsOpen() ) { aString1.ConvertLineEnd(LINEEND_CRLF); aStrm.Seek(STREAM_SEEK_TO_END); aStrm << ByteString( aString1, RTL_TEXTENCODING_UTF8 ).GetBuffer(); aStrm.Close(); } } if ( nParams & PARAM_ULONG_1 ) { switch ( nUId ) { case S_ProfileReset: // nLNr1 = Anzahl Borders { pImpl->nNumBorders = (sal_uInt16)nLNr1; // Borders are 0 to 4 sal_uInt16 i; for ( i=0 ; i<4 ; i++ ) pImpl->naValBorders[i] = 0; for ( i=0 ; i<5 ; i++ ) { pImpl->naNumEntries[i] = 0; pImpl->naRemoteTime[i] = 0; pImpl->naLocalTime[i] = 0; } break; } case S_ProfileBorder1: // nLNr1 = Border1 in ms case S_ProfileBorder2: // nLNr1 = Border2 in ms case S_ProfileBorder3: // nLNr1 = Border3 in ms case S_ProfileBorder4: // nLNr1 = Border4 in ms { pImpl->naValBorders[ nUId - S_ProfileBorder1 ] = nLNr1; break; } case S_ProfileTime: // nLNr1 = remote Zeit des Befehls { sal_uInt16 i; for ( i=0 ; inNumBorders && pImpl->naValBorders[i] <= nLNr1 ; i++ ) {}; pImpl->naNumEntries[ i ]++; pImpl->naRemoteTime[ i ] += nLNr1; pImpl->naLocalTime[ i ] += Time::GetSystemTicks() - pImpl->LocalStarttime; #if OSL_DEBUG_LEVEL > 1 if ( nLNr1 > (Time::GetSystemTicks() - pImpl->LocalStarttime) ) { String aLine = CUniString("Testtoolzeit(").Append(String::CreateFromInt64(Time::GetSystemTicks() - pImpl->LocalStarttime)).AppendAscii(") kleiner Officezeit(").Append(String::CreateFromInt64(nLNr1)).AppendAscii(")\n"); DirEntry FilePath = pImpl->aLogFileBase + DirEntry(DirEntry(aLogFileName).GetBase().AppendAscii(".prf")); SvFileStream aStrm( FilePath.GetFull(), STREAM_STD_WRITE ); if( aStrm.IsOpen() ) { aLine.ConvertLineEnd(LINEEND_CRLF); aStrm.Seek(STREAM_SEEK_TO_END); aStrm << ByteString( aLine, RTL_TEXTENCODING_UTF8 ).GetBuffer(); aStrm.Close(); } } #endif break; } case S_ProfileDump: // Gibt die daten aus. { if ( pImpl->nNumBorders == 0 ) // Also keine alte R�ckmeldung vom Office break; DirEntry FilePath = pImpl->aLogFileBase + DirEntry(DirEntry(aLogFileName).GetBase().AppendAscii(".prf")); SvFileStream aStrm( FilePath.GetFull(), STREAM_STD_WRITE ); if( aStrm.IsOpen() ) { String aProfile; sal_uInt16 i; aProfile += String().Expand(15); for ( i=0 ; inNumBorders ; i++ ) aProfile += (CUniString("< ").Append(String::CreateFromInt64(pImpl->naValBorders[i]))).Expand(20); aProfile += (CUniString(">= ").Append(TTFormat::ms2s(pImpl->naValBorders[pImpl->nNumBorders-1]))); aProfile += '\n'; aProfile += CUniString("Ereignisse").Expand(15); for ( i=0 ; i<=pImpl->nNumBorders ; i++ ) aProfile += TTFormat::ms2s(pImpl->naNumEntries[i]).Expand(20); aProfile += '\n'; aProfile += CUniString("Server Zeit").Expand(15); for ( i=0 ; i<=pImpl->nNumBorders ; i++ ) aProfile += TTFormat::ms2s(pImpl->naRemoteTime[i]).Expand(20); aProfile += '\n'; aProfile += CUniString("Testtool Zeit").Expand(15); for ( i=0 ; i<=pImpl->nNumBorders ; i++ ) aProfile += TTFormat::ms2s(pImpl->naLocalTime[i]).Expand(20); aProfile += '\n'; aProfile += CUniString("Overhead p.e.").Expand(15); for ( i=0 ; i<=pImpl->nNumBorders ; i++ ) { if ( pImpl->naNumEntries[i] > 0 ) aProfile += TTFormat::ms2s((pImpl->naLocalTime[i]-pImpl->naRemoteTime[i])/pImpl->naNumEntries[i]).Expand(20); else aProfile += CUniString( "??" ).Expand(20); } aProfile += '\n'; aProfile.ConvertLineEnd(LINEEND_CRLF); aStrm.Seek(STREAM_SEEK_TO_END); aStrm << ByteString( aProfile, RTL_TEXTENCODING_UTF8 ).GetBuffer(); aStrm.Close(); } break; } default: OSL_TRACE("Unbekannter Sub Return Code bei Profile: %hu", nUId ); break; } } #endif } break; case RET_DirectLoging: { // FIXME: HELPID #if 0 sal_uLong nUId = aUId.GetNum(); switch ( nUId ) { case S_AssertError: { ADD_ASSERTION_LOG( aString1 ); } break; case S_QAError: { ADD_QA_ERROR_LOG( aString1 ); } break; default: ; } #endif } break; case RET_MacroRecorder: { SortControlsByNumber( sal_True ); String aCommand,aControls,aControl,aULongNames,aULongName; sal_Bool bWriteNewKontext = sal_False; aControls.Erase(); // Kurzname feststellen if ( m_pReverseControls ) { sal_uInt16 nNr; ControlItem *pNewItem = new ControlItemUId( String(), aUId ); if ( m_pReverseControls->Seek_Entry(pNewItem,&nNr) ) aControls = m_pReverseControls->GetObject(nNr)->pData->Kurzname; delete pNewItem; } if ( !aControls.Len() ) { aControls = String::CreateFromAscii("UnknownControl:UnknownControl"); Sound::Beep( SOUND_WARNING ); } aULongNames.Erase(); if( (nParams & PARAM_ULONG_1) && (nNr1 & M_RET_NUM_CONTROL) ) { if ( m_pReverseControls ) { sal_uInt16 nNr; // FIXME: HELPID ControlItem *pNewItem = new ControlItemUId( String(), rtl::OString( /*nLNr1*/ ) ); if ( m_pReverseControls->Seek_Entry(pNewItem,&nNr) ) aULongNames = m_pReverseControls->GetObject(nNr)->pData->Kurzname; delete pNewItem; } if ( !aULongNames.Len() ) { aULongNames = String::CreateFromAscii("Unknown:Unknown"); Sound::Beep( SOUND_WARNING ); } // now determin the best common kontext sal_uInt16 i,j; sal_Bool bFoundUlongName = sal_False, bFoundControl = sal_False; // check for current kontext for ( i = 0 ; !bFoundUlongName && i < aULongNames.GetTokenCount('/') ; i++ ) bFoundUlongName = aLastRecordedKontext.Equals( aULongNames.GetToken(i,'/').GetToken( 0,':') ); for ( j = 0 ; !bFoundControl && j < aControls.GetTokenCount('/') ; j++ ) bFoundControl = aLastRecordedKontext.Equals( aControls.GetToken(j,'/').GetToken( 0,':') ); if ( bFoundUlongName && bFoundControl ) { aULongName = aULongNames.GetToken(i-1,'/').GetToken( 1,':'); aControl = aControls.GetToken(j-1,'/').GetToken( 1,':'); } else { // see if we can find common kontext sal_Bool bFound = sal_False; String aCurrentKontext; for ( i = 0 ; !bFound && i < aULongNames.GetTokenCount('/') ; i++ ) { aCurrentKontext = aULongNames.GetToken(i,'/').GetToken( 0,':'); for ( j = 0 ; !bFound && j < aControls.GetTokenCount('/') ; j++ ) { if ( aCurrentKontext.Equals( aControls.GetToken(j,'/').GetToken( 0,':') ) ) { bFound = sal_True; aULongName = aULongNames.GetToken(i,'/').GetToken( 1,':'); aControl = aControls.GetToken(j,'/').GetToken( 1,':'); aLastRecordedKontext = aCurrentKontext; bWriteNewKontext = sal_True; } } } if ( !bFound ) { // check if both contain toplevel bFoundUlongName = sal_False; bFoundControl = sal_False; for ( i = 0 ; !bFoundUlongName && i < aULongNames.GetTokenCount('/') ; i++ ) bFoundUlongName = aULongNames.GetToken(i,'/').GetToken( 0,':').Equals( aULongNames.GetToken(i,'/').GetToken( 1,':') ); for ( j = 0 ; !bFoundControl && j < aControls.GetTokenCount('/') ; j++ ) bFoundControl = aControls.GetToken(j,'/').GetToken( 0,':').Equals( aControls.GetToken(j,'/').GetToken( 1,':') ); if ( bFoundUlongName && bFoundControl ) { aULongName = aULongNames.GetToken(i-1,'/').GetToken( 1,':'); aControl = aControls.GetToken(j-1,'/').GetToken( 1,':'); if ( aLastRecordedKontext.Len() ) { aLastRecordedKontext.Erase(); bWriteNewKontext = sal_True; } } else { String aComment; aComment = CUniString( "'could not Determin common kontext\n" ); Sound::Beep( SOUND_WARNING ); aWriteStringHdl.Call( &aComment ); aULongName = aULongNames.GetToken(i,'/'); aControl = aControls.GetToken(j,'/'); } } } } else { // we only have a Control sal_uInt16 i; sal_Bool bFoundControl = sal_False; // check for current kontext for ( i = 0 ; !bFoundControl && i < aControls.GetTokenCount('/') ; i++ ) bFoundControl = aLastRecordedKontext.Equals( aControls.GetToken(i,'/').GetToken( 0,':') ); if ( bFoundControl ) aControl = aControls.GetToken(i-1,'/').GetToken( 1,':'); else { aLastRecordedKontext = aControls.GetToken(0,'/').GetToken( 0,':'); bWriteNewKontext = sal_True; aControl = aControls.GetToken(0,'/').GetToken( 1,':'); } } if ( bWriteNewKontext ) { String aKontextCommand = CUniString( "Kontext" ); if ( aLastRecordedKontext.Len() ) { aKontextCommand.AppendAscii ( " \"" ); aKontextCommand += aLastRecordedKontext; aKontextCommand.AppendAscii ( "\"" ); } aKontextCommand.AppendAscii( "\n" ); aWriteStringHdl.Call( &aKontextCommand ); } aCommand = aControl; // Add Method name String aMethod = GetMethodName( nNr1 & ~M_RET_NUM_CONTROL ); aCommand += '.'; aCommand += aMethod; sal_Bool bWasParam = sal_False; if( nParams & PARAM_STR_1 ) { bWasParam = sal_True; aCommand.AppendAscii( " \"" ); if ( nNr1 & M_KEY_STRING ) { sal_uInt16 nModify = 0; sal_Bool bIsProsa = sal_False; xub_StrLen i; for ( i = 0; i < aString1.Len(); i++ ) { if ( ((sal_uInt16)aString1.GetChar(i)) == 1 ) // we have a spechial char { i++; if ( !bIsProsa ) { aCommand.AppendAscii( "<" ); bIsProsa = sal_True; } else aCommand.AppendAscii( " " ); sal_uInt16 nKeyCode = (sal_uInt16)aString1.GetChar(i) & KEY_CODE; sal_uInt16 nNewModify = (sal_uInt16)aString1.GetChar(i) & KEY_MODTYPE; if ( nNewModify != nModify ) { // generate modifiers sal_uInt16 nChanged = ( nNewModify ^ nModify ); if ( nChanged & KEY_SHIFT ) { aCommand += GetKeyName( KEY_SHIFT ); aCommand.AppendAscii( " " ); } if ( nChanged & KEY_MOD1 ) { aCommand += GetKeyName( KEY_MOD1 ); aCommand.AppendAscii( " " ); } if ( nChanged & KEY_MOD2 ) { aCommand += GetKeyName( KEY_MOD2 ); aCommand.AppendAscii( " " ); } } aCommand += GetKeyName( nKeyCode ); nModify = nNewModify; } else { if ( bIsProsa ) { aCommand.AppendAscii( ">" ); bIsProsa = sal_False; } aCommand += aString1.GetChar(i); nModify = 0; } } if ( bIsProsa ) { aCommand.AppendAscii( ">" ); bIsProsa = sal_False; } } else { aCommand += aString1; } aCommand.AppendAscii( "\"" ); } if( nParams & PARAM_ULONG_1 ) { if ( bWasParam ) aCommand.AppendAscii( ", " ); else aCommand.AppendAscii( " " ); bWasParam = sal_True; if ( nNr1 & M_RET_NUM_CONTROL ) { aCommand.Append( aULongName ); } else { aCommand.Append( String::CreateFromInt64( nLNr1 ) ); } } if( nParams & PARAM_BOOL_1 ) { if ( bWasParam ) aCommand.AppendAscii( ", " ); else aCommand.AppendAscii( " " ); bWasParam = sal_True; if ( bBool1 ) aCommand.AppendAscii( "true" ); else aCommand.AppendAscii( "false" ); } aCommand.AppendAscii( "\n" ); aWriteStringHdl.Call( &aCommand ); } break; default: OSL_TRACE( "Unbekannter Return Code: %iu", nRet ); break; } break; } case SIReturnError: { String aString; rtl::OString aUId; if ( pRetStream->GetNextType() == BinString ) { String aUStrId; // UniqueStringID Used for Mozilla Integration pRetStream->Read( aUStrId ); // FIXME: HELPID #if 0 aUId = rtl::OString( aUStrId ); #endif } else { comm_ULONG nUId; pRetStream->Read( nUId ); // bei Sequence einfach die Sequence // FIXME: HELPID #if 0 aUId = rtl::OString( nUId ); #endif } pRetStream->Read( aString ); ReplaceNumbers (aString); String aShortName; aShortName = pShortNames->GetName(aUId); aShortName.AppendAscii( " : " ); String aTmpStr(aShortName); aTmpStr += aString; ADD_ERROR(SbxERR_BAD_ACTION, aTmpStr/*, nNr*/); break; } default: OSL_TRACE( "Unbekannter Request im Return Stream Nr: %iu", nId ); break; } if( !pIn->IsEof() ) pRetStream->Read( nId ); else { OSL_FAIL( "truncated input stream" ); } } delete pRetStream; if ( bSequenceOK ) { nSequence++; pShortNames->Invalidate( nClearSequence - KEEP_SEQUENCES ); } bReturnOK = sal_True; return sal_True; } // RetService::Request() String TestToolObj::GetMethodName( sal_uLong nMethodId ) { sal_uInt16 nElement; if ( !Controls::pClasses ) // Ist static, wird also nur einmal geladen ReadFlatArray( Controls::arClasses, Controls::pClasses ); if ( Controls::pClasses ) { // FIXME: HELPID #if 0 for ( nElement = 0 ; nElement < Controls::pClasses->Count() ; nElement++ ) if ( Controls::pClasses->GetObject(nElement)->pData->aUId.Matches( nMethodId ) ) return Controls::pClasses->GetObject(nElement)->pData->Kurzname; #else (void)nElement; (void)nMethodId; #endif } return String(); } String TestToolObj::GetKeyName( sal_uInt16 nKeyCode ) { sal_uInt16 nElement; if ( !CmdStream::pKeyCodes ) // Ist static, wird also nur einmal geladen ReadFlatArray( CmdStream::arKeyCodes, CmdStream::pKeyCodes ); if ( CmdStream::pKeyCodes ) { // FIXME: HELPID #if 0 for ( nElement = 0 ; nElement < CmdStream::pKeyCodes->Count() ; nElement++ ) if ( CmdStream::pKeyCodes->GetObject(nElement)->pData->aUId.Matches( nKeyCode ) ) return CmdStream::pKeyCodes->GetObject(nElement)->pData->Kurzname; #else (void)nElement; (void)nKeyCode; #endif } return CUniString( "UnknownKeyCode" ); } void TestToolObj::ReplaceNumbers(String &aText) { static ControlDefLoad const arRes_Type [] = #include "res_type.hxx" static CNames *pRTypes = NULL; xub_StrLen nStart = STRING_NOTFOUND; xub_StrLen nGleich = STRING_NOTFOUND; xub_StrLen nEnd = STRING_NOTFOUND; xub_StrLen nStartPos = 0; sal_uLong nNumber; String aType; String aResult; sal_Bool bFound; while ( (nStart = aText.Search(StartKenn,nStartPos)) != STRING_NOTFOUND && (nGleich = aText.SearchAscii("=",nStart+StartKenn.Len())) != STRING_NOTFOUND && (nEnd = aText.Search(EndKenn,nGleich+1)) != STRING_NOTFOUND) { aType = aText.Copy(nStart,nGleich-nStart); nNumber = (sal_uLong)aText.Copy(nGleich+1,nEnd-nGleich-1).ToInt64(); bFound = sal_False; if ( aType.CompareTo(UIdKenn) == COMPARE_EQUAL ) { // FIXME: HELPID aResult = pShortNames->GetName(rtl::OString(/*nNumber*/)); bFound = sal_True; } if ( aType.CompareTo(MethodKenn ) == COMPARE_EQUAL ) { bFound = sal_True; aResult = GetMethodName( nNumber ); } if ( aType.CompareTo(RcKenn ) == COMPARE_EQUAL ) { bFound = sal_True; if ( !pRCommands ) // Ist static, wird also nur einmal geladen ReadFlatArray( arR_Cmds, pRCommands ); sal_uInt16 nElement; if ( pRCommands ) { // FIXME: HELPID #if 0 for ( nElement = 0 ; nElement < pRCommands->Count() ; nElement++ ) if ( pRCommands->GetObject(nElement)->pData->aUId.Matches( nNumber ) ) { aResult = pRCommands->GetObject(nElement)->pData->Kurzname; nElement = pRCommands->Count(); } #else (void)nElement; #endif } } if ( aType.CompareTo(TypeKenn ) == COMPARE_EQUAL ) { bFound = sal_True; if ( !pRTypes ) // Ist static, wird also nur einmal geladen ReadFlatArray( arRes_Type, pRTypes ); sal_uInt16 nElement; if ( pRTypes ) { // FIXME: HELPID #if 0 for ( nElement = 0 ; nElement < pRTypes->Count() ; nElement++ ) if ( pRTypes->GetObject(nElement)->pData->aUId.Matches( nNumber ) ) { aResult = pRTypes->GetObject(nElement)->pData->Kurzname; nElement = pRTypes->Count(); } #else (void)nElement; #endif } } if ( aType.CompareTo(SlotKenn ) == COMPARE_EQUAL ) { // FIXME: HELPID aResult = pShortNames->GetName(rtl::OString(/*nNumber*/)); bFound = sal_True; } if ( aType.CompareTo(TabKenn ) == COMPARE_EQUAL ) { if ( nNumber > nStart ) aResult.Fill( (sal_uInt16)nNumber - nStart +1 ); else aResult = CUniString(" "); bFound = sal_True; } nStartPos = nStart; if ( bFound ) { aText.Erase(nStart,nEnd+EndKenn.Len()-nStart); aText.Insert(aResult,nStart); nStartPos = nStartPos + aResult.Len(); } else nStartPos = nStartPos + StartKenn.Len(); } } SbTextType TestToolObj::GetSymbolType( const String &rSymbol, sal_Bool bWasControl ) { if ( rSymbol.CompareToAscii( "try" ) == COMPARE_EQUAL || rSymbol.CompareToAscii( "catch" ) == COMPARE_EQUAL || rSymbol.CompareToAscii( "endcatch" ) == COMPARE_EQUAL || rSymbol.CompareToAscii( "testcase" ) == COMPARE_EQUAL || rSymbol.CompareToAscii( "endcase" ) == COMPARE_EQUAL ) { return TT_KEYWORD; } ControlDef WhatName( rSymbol, rtl::OString() ); if ( bWasControl ) { if ( !Controls::pClasses ) // Ist static, wird also nur einmal geladen ReadFlatArray( Controls::arClasses, Controls::pClasses ); if ( (Controls::pClasses && Controls::pClasses->Seek_Entry( &WhatName )) || rSymbol.EqualsIgnoreCaseAscii( "ID" ) || rSymbol.EqualsIgnoreCaseAscii( "Name" ) ) return TT_METHOD; else return TT_NOMETHOD; } // Die Controls durchsuchen if ( m_pControls ) { sal_uInt16 nWin; for ( nWin = 0 ; nWin < m_pControls->Count() ; nWin++ ) { if ( ((ControlDef*)m_pControls->GetObject( nWin ))->SonSeek_Entry( &WhatName ) ) return TT_CONTROL; } } // Die Slots durchsuchen if ( m_pSIds && m_pSIds->Seek_Entry( &WhatName ) ) return TT_SLOT; // Ist es ein RemoteCommand if ( !pRCommands ) // Ist static, wird also nur einmal geladen ReadFlatArray( arR_Cmds, pRCommands ); if ( pRCommands && pRCommands->Seek_Entry( &WhatName ) ) return TT_REMOTECMD; // Wenns sonst nix war, dann vielleicht ein Lokales Kommando SbxVariable *pVar = SbxObject::Find( rSymbol, SbxCLASS_DONTCARE ); if ( pVar && ( pVar->ISA(SbxMethod) || pVar->ISA(SbxProperty) ) ) { return TT_LOCALCMD; } return SB_SYMBOL; // Alles was hier landet ist vom Typ SB_SYMBOL und bleibt es auch } #undef P_FEHLERLISTE #define P_FEHLERLISTE TestToolObj::pFehlerListe Controls::Controls( String aCName ) : SbxObject( aCName) { pMethodVar = new SbxTransportMethod( SbxVARIANT ); pMethodVar->SetName( CUniString("Dummy") ); Insert( pMethodVar ); } Controls::~Controls() {} void Controls::ChangeListener( SbxObject* parent ) { EndListening( pMethodVar->GetBroadcaster(), sal_True ); parent->StartListening( pMethodVar->GetBroadcaster(), sal_True ); } void Controls::SFX_NOTIFY( SfxBroadcaster&, const TypeId&, const SfxHint&, const TypeId& ) {} SbxVariable* Controls::Find( const String& aStr, SbxClassType aType) { if ( !pClasses ) // Ist static, wird also nur einmal geladen ReadFlatArray( arClasses, pClasses ); if ( GetUserData() == ID_ErrorDummy ) { pMethodVar->SetName(UniString(GetName()).AppendAscii(".").Append(aStr)); pMethodVar->SetUserData( ID_ErrorDummy ); return pMethodVar; } sal_uInt16 nElement; ControlDef WhatName(aStr,rtl::OString()); if (pClasses && pClasses->Seek_Entry(&WhatName,&nElement)) { pMethodVar->SetName(aStr); // FIXME: HELPID sal_uLong nUId = 0;//pClasses->GetObject(nElement)->pData->aUId.GetNum(); pMethodVar->nValue = nUId; pMethodVar->SetUserData( GetUserData() ); return pMethodVar; } else { // mainly for ID and name SbxVariableRef Old = SbxObject::Find(aStr, aType ); if (Old) return Old; else if ( aStr.EqualsIgnoreCaseAscii("ID") ) return NULL; // suppress generation of error in this case } ADD_ERROR(SbxERR_BAD_METHOD,GEN_RES_STR2(S_UNKNOWN_METHOD, GetName(), aStr)); return NULL; } String TTFormat::ms2s( sal_uLong nMilliSeconds ) { if ( nMilliSeconds < 100000 ) // 100 Sekunden return String::CreateFromInt64( nMilliSeconds ); if ( nMilliSeconds < 100000*60 ) // 100 Minuten return String::CreateFromInt32( nMilliSeconds / 1000 ).AppendAscii("Sec"); return String::CreateFromInt32( nMilliSeconds / 1000 / 60 ).AppendAscii("Min"); } /* vim:set shiftwidth=4 softtabstop=4 expandtab: */