GME  13
MgaLauncher.cpp
Go to the documentation of this file.
00001 
00002 #include "stdafx.h"
00003 #include "htmlhelp.h"
00004 #include "MgaLauncher.h"
00005 
00006 #include "MetaDlg.h"
00007 #include "GmeDlg.h"
00008 #include "CompDlg.h"
00009 #include "RegistryBrowserDlg.h"
00010 #include "AnnotationBrowserDlg.h"
00011 #include "CommonComponent.h"
00012 
00013 #include <comutil.h>
00014 #include <comdef.h>
00015 
00016 #include "CrashRpt.h"
00017 #ifdef _DEBUG
00018 #pragma comment(lib, "CrashRptd.lib")
00019 #else
00020 #pragma comment(lib, "CrashRpt.lib")
00021 #endif
00022 
00023 
00024 /* Deprecated Web based help
00025 #define GME_UMAN_HOME                           "http://www.isis.vanderbilt.edu/projects/GME/Doc/UsersManual/"
00026 #define GME_UMAN_CONTENTS                       "helpcontents1.htm"
00027 #define GME_UMAN_MODEL                          "models.htm"
00028 #define GME_UMAN_ATOM                           "atoms.htm"
00029 #define GME_UMAN_REFERENCE                      "references.htm"
00030 #define GME_UMAN_SET                            "sets.htm"
00031 #define GME_UMAN_CONNECTION                     "connectionsandlinks.htm"
00032 #pragma bookmark ( change when folders.htm exists for documentation )
00033 #define GME_UMAN_FOLDER                         "themodelbrowser.htm"
00034 */
00035 
00036 #define GME_UMAN_HOME                           "Doc/GME Manual and User Guide.chm::/"
00037 #define GME_UMAN_CONTENTS                       "index.html"
00038 #define GME_UMAN_MODEL                          "models.html"
00039 #define GME_UMAN_ATOM                           "atoms.html"
00040 #define GME_UMAN_REFERENCE                      "references.html"
00041 #define GME_UMAN_SET                            "sets.html"
00042 #define GME_UMAN_CONNECTION                     "connectionsandlinks.html"
00043 #pragma bookmark ( change when folders.htm exists for documentation )
00044 #define GME_UMAN_FOLDER                         "themodelbrowser.html"
00045 
00046 
00047 // --------------------------- CMgaLauncher
00048 
00049 STDMETHODIMP CMgaLauncher::put_ParadigmName(BSTR p)
00050 {
00051         COMTRY
00052         {
00053                 paradigmname = p;
00054         }
00055         COMCATCH(;)
00056 }
00057 
00058 STDMETHODIMP CMgaLauncher::put_Parameter(VARIANT p)
00059 {
00060         COMTRY
00061         {
00062                 parameter = p;
00063         }
00064         COMCATCH(;)
00065 }
00066 
00067 STDMETHODIMP CMgaLauncher::put_ComponentType(componenttype_enum type)
00068 {
00069         comptype = type;
00070 
00071         return S_OK;
00072 }
00073 
00074 STDMETHODIMP CMgaLauncher::get_ParadigmName(BSTR *p)
00075 {
00076         CHECK_OUT(p);
00077 
00078         COMTRY
00079         {
00080             CopyTo(paradigmname, p);
00081         }
00082         COMCATCH(;)
00083 }
00084 
00085 STDMETHODIMP CMgaLauncher::get_ConnStr(BSTR *p)
00086 {
00087         CHECK_OUT(p);
00088 
00089         COMTRY
00090         {
00091                 CopyTo(connstr, p);
00092         }
00093         COMCATCH(;)
00094 }
00095 
00096 STDMETHODIMP CMgaLauncher::get_ProgID(BSTR *p)
00097 {
00098         CHECK_OUT(p);
00099 
00100         COMTRY
00101         {
00102                 CopyTo(progid, p);
00103         }
00104         COMCATCH(;)
00105 }
00106 
00107 STDMETHODIMP CMgaLauncher::get_Paradigm(IMgaMetaProject **p)
00108 {
00109         CHECK_OUT(p);
00110 
00111         COMTRY
00112         {
00113                 CopyTo(paradigm, p);
00114         }
00115         COMCATCH(;)
00116 }
00117 
00118 STDMETHODIMP CMgaLauncher::MetaDlg(metadlg_enum flags)
00119 {
00120         COMTRY
00121         {
00122                 AFX_MANAGE_STATE(AfxGetStaticModuleState());
00123 
00124                 connstr.Empty();
00125                 paradigm.Release();
00126 
00127                 CMetaDlg dlg;
00128 
00129                 dlg.name = paradigmname;
00130                 dlg.flags = flags;
00131 
00132                 if( dlg.DoModal() != IDOK )
00133                         COMRETURN(S_FALSE);
00134 
00135                 paradigmname = dlg.name;
00136                 if( paradigmname.IsEmpty() )
00137                         COMRETURN(S_FALSE);
00138 
00139                 connstr = dlg.connstr;
00140         }
00141         COMCATCH(;)
00142 }
00143 
00144 STDMETHODIMP CMgaLauncher::GmeDlg()
00145 {
00146         COMTRY
00147         {
00148                 AFX_MANAGE_STATE(AfxGetStaticModuleState());
00149 
00150                 CGmeDlg dlg;
00151 
00152                 if( dlg.DoModal() != IDOK )
00153                         COMRETURN(S_FALSE);
00154         } 
00155         COMCATCH(;)
00156 }
00157 
00158 STDMETHODIMP CMgaLauncher::ComponentDlg(componentdlg_enum flags)
00159 {
00160         COMTRY
00161         {
00162                 AFX_MANAGE_STATE(AfxGetStaticModuleState());
00163 
00164                 progid.Empty();
00165 
00166                 CCompDlg dlg;
00167 
00168                 dlg.paradigm = paradigmname;
00169                 dlg.type = comptype;
00170                 dlg.parameter = parameter;
00171 
00172                 if( dlg.DoModal() != IDOK )
00173                         COMRETURN(S_FALSE);
00174 
00175                 progid = dlg.progid;
00176                 if( progid.IsEmpty() )
00177                         COMRETURN(S_FALSE);
00178         }
00179         COMCATCH(;)
00180 }
00181 
00182 
00183 STDMETHODIMP CMgaLauncher::PropDlg(IMgaObject * obj)
00184 {
00185         AFX_MANAGE_STATE(AfxGetStaticModuleState());
00186 
00187         return E_NOTIMPL;
00188 }
00189 
00190 STDMETHODIMP CMgaLauncher::AttrDlg(IMgaObject * obj)
00191 {
00192         AFX_MANAGE_STATE(AfxGetStaticModuleState());
00193         
00194         COMTRY
00195         {
00196 
00197 #ifdef _DEBUG
00198                 AfxMessageBox(_T("dummy AttrDlg() implementation-- only in Debug version"));
00199 #endif
00200 
00201         }
00202         COMCATCH(;)
00203 }
00204 
00205 LONG GetRegKey(HKEY key, LPCTSTR subkey, LPTSTR retdata)
00206 {
00207         HKEY hKey;
00208     LONG lResult = RegOpenKeyEx(key, subkey, 0, KEY_QUERY_VALUE, &hKey); 
00209   
00210     if( lResult == ERROR_SUCCESS)
00211         {
00212          long lDataSize = MAX_PATH;
00213                 TCHAR data[MAX_PATH];
00214   
00215                 RegQueryValue( hKey, NULL, data, &lDataSize);
00216                 lstrcpy( retdata,data);
00217                 RegCloseKey( hKey);
00218     }
00219   
00220     return lResult;
00221 }
00222   
00223 HINSTANCE GotoURL(LPCTSTR url, int showcmd)
00224 {
00225 //      HtmlHelp(NULL, url, HH_DISPLAY_TOPIC, 0);
00226 //      return NULL;
00227 
00228         TCHAR key[MAX_PATH + MAX_PATH];
00229   
00230     // First try ShellExecute()
00231     HINSTANCE hResult = ShellExecute( NULL, _T("open"), url, NULL,NULL, showcmd);
00232 
00233     // If it failed, get the .htm regkey and lookup the program
00234         if( (UINT)hResult <= HINSTANCE_ERROR)
00235         {
00236                 if( GetRegKey( HKEY_CLASSES_ROOT, _T(".htm"), key) == ERROR_SUCCESS)
00237                 {
00238                         lstrcat( key, _T("\\shell\\open\\command")); 
00239   
00240             if( GetRegKey( HKEY_CLASSES_ROOT,key,key) == ERROR_SUCCESS)
00241                         {
00242                                 TCHAR *pos;
00243                 pos = _tcsstr( key, _T("\"%1\"")); 
00244   
00245                 if( pos == NULL)
00246                                 {
00247                                         // No quotes found
00248                     pos = _tcsstr( key, _T("%1")); // Check for % 1, without quotes
00249                     if( pos == NULL)    // No  parameter at all...
00250                         pos = key+lstrlen( key)-1;
00251                     else
00252                                                 *pos = '\0';    //  Remove the parameter
00253                 }
00254                 else
00255                                         *pos = '\0';
00256                                         // Remove the parameter
00257   
00258                 lstrcat(pos, _T(" "));
00259                 lstrcat(pos, url);
00260   
00261                                 // FIXME: should use CreateProcess
00262                                 hResult = (HINSTANCE)WinExec( CStringA(key),showcmd);
00263                         }
00264                 }
00265         }
00266   
00267         return hResult;
00268 }
00269 
00270 
00271 STDMETHODIMP CMgaLauncher::ShowHelp(IMgaObject* obj)
00272 {
00273         AFX_MANAGE_STATE(AfxGetStaticModuleState());
00274 
00275         COMTRY
00276         {
00277                 CComPtr<IMgaFolder> imf;
00278                 CComPtr<IMgaFCO> imfco;
00279                 CString url;
00280 
00281                 if (obj != NULL) 
00282                 {
00283                         if (FAILED(obj->QueryInterface(&imf)) &&
00284                                 FAILED(obj->QueryInterface(&imfco)))
00285                         {
00286                                 COMTHROW(E_INVALIDARG);
00287                         }
00288 
00289                         CComBSTR bstrVal;
00290                         CComBSTR bstr = L"help";
00291                         COMTHROW((imf != NULL) ? 
00292                                 imf->get_RegistryValue(bstr,&bstrVal)
00293                                 :
00294                                 imfco->get_RegistryValue(bstr,&bstrVal)
00295                                 );
00296 
00297                         
00298                         CopyTo(bstrVal,url);
00299 
00300                         // Resolving $PARADIGMDIR
00301                         CComPtr<IMgaProject> project;
00302                         if (imf)
00303                                 COMTHROW(imf->get_Project(&project));
00304                         else
00305                                 COMTHROW(imfco->get_Project(&project));
00306                         _bstr_t paradigmConnStr;
00307                         COMTHROW(project->get_ParadigmConnStr(paradigmConnStr.GetAddress()));
00308                         if (_wcsnicmp(_T("MGA="), paradigmConnStr, 4) == 0) 
00309                         {
00310                                 CString filename, dirname;
00311                                 GetFullPathName(CString(static_cast<const TCHAR*>(paradigmConnStr) + 4), filename, dirname);
00312 
00313                                 if (dirname != "")
00314                                 {
00315                                         url.Replace(_T("$PARADIGMDIR"), dirname);
00316                                 }
00317                         }
00318 
00319 
00320                         // Supporting one environment variable with $VARNAME$ syntax
00321                         int firstIdx = url.Find(_T('$'));
00322                         if(firstIdx  != -1 && url.GetLength() > firstIdx+2) // Reference to environment variable with a non-empty name
00323                         {
00324                                 int nextIdx = url.Find(_T('$'), firstIdx +1); // Finding the closing $
00325 
00326                                 if(nextIdx != -1 && nextIdx > firstIdx +1)
00327                                 {
00328                                         CString variableName = url.Mid(firstIdx+1, nextIdx - firstIdx -1);
00329                                         TCHAR* value = _tgetenv(variableName);
00330 
00331                                         if(value != NULL)
00332                                         {
00333                                                 CString variableString;
00334                                                 variableString.Format(_T("$%s$"), variableName);
00335                                                 url.Replace(variableString, value);
00336                                         }
00337 
00338                                 }
00339 
00340                         }
00341 
00342                         CString name;
00343                         COMTHROW(obj->get_Name(PutOut(name)));
00344                 }
00345 
00346                 if (!url.IsEmpty())
00347                 {
00348                         GotoURL(url,SW_SHOWMAXIMIZED);
00349                 }
00350                 else
00351                 {
00352                         if (obj == NULL)
00353                         {
00354                                 url = GME_UMAN_CONTENTS;
00355                         } 
00356                         else
00357                         {
00358                                 objtype_enum obj_t;
00359                                 COMTHROW( obj->get_ObjType(&obj_t) );
00360 
00361                                 switch (obj_t) {
00362 
00363                                         case OBJTYPE_MODEL : {
00364                                                 url = GME_UMAN_MODEL;
00365                                                 break;
00366                                         }
00367                                         case OBJTYPE_ATOM : {
00368                                                 url = GME_UMAN_ATOM;
00369                                                 break;
00370                                         }
00371                                         case OBJTYPE_REFERENCE : {
00372                                                 url = GME_UMAN_REFERENCE;
00373                                                 break;
00374                                         }
00375                                         case OBJTYPE_SET : {
00376                                                 url = GME_UMAN_SET;
00377                                                 break;
00378                                         }
00379                                         case OBJTYPE_CONNECTION : {
00380                                                 url = GME_UMAN_CONNECTION;
00381                                                 break;
00382                                         }
00383                                         case OBJTYPE_FOLDER : {
00384                                                 url = GME_UMAN_FOLDER;
00385                                                 break;
00386                                         }
00387                                 }
00388                         }
00389 
00390                         if (!url.IsEmpty())
00391                         {
00392                                 CString gmeRoot(_T("../"));
00393                                 // Use an absolute path based on the GME_ROOT environment variable, instead of a relative path if we can
00394                                 TCHAR* gme_root_env = NULL;
00395                                 gme_root_env = _tgetenv(_T("GME_ROOT"));
00396                                 if (gme_root_env) {
00397                                         long len = _tcslen(gme_root_env);
00398                                         bool hasSlashAtTheEnd = (gme_root_env[len - 1] == '\\' || gme_root_env[len - 1] == '/');
00399                                         gmeRoot = gme_root_env;
00400                                         if (!hasSlashAtTheEnd)
00401                                                 gmeRoot = gmeRoot + "/";
00402                                 }
00403                                 gmeRoot.Replace(_T("\\"), _T("/"));
00404                                 CString fullUrl = CString(_T("ms-its:")) + gmeRoot + GME_UMAN_HOME + url;
00405                                 CWnd* mainWnd = AfxGetMainWnd();
00406                                 HWND hwndCaller = NULL;
00407                                 if (mainWnd != NULL)
00408                                         hwndCaller = mainWnd->m_hWnd;
00409                                 HWND helpWnd = NULL;
00410 #ifndef _M_X64
00411                                 helpWnd = ::HtmlHelp(hwndCaller, fullUrl, HH_DISPLAY_TOPIC, 0);
00412                                 if (helpWnd == NULL && url != GME_UMAN_CONTENTS) {
00413                                         fullUrl = CString(_T("ms-its:")) + gmeRoot + GME_UMAN_HOME + GME_UMAN_CONTENTS;
00414                                         helpWnd = ::HtmlHelp(hwndCaller, fullUrl, HH_DISPLAY_TOPIC, 0);
00415                                 }
00416 #endif
00417                                 if (helpWnd == NULL)
00418                                         AfxMessageBox(_T("Couldn't find help file or help topic: ") + fullUrl, MB_OK | MB_ICONSTOP);
00419                         }
00420                         else
00421                         {
00422                                 AfxMessageBox(_T("No default help is available for selection!"), MB_OK | MB_ICONSTOP);
00423                         }
00424                 }
00425         }
00426         COMCATCH(;)
00427 }
00428 
00429 static int __stdcall nopExceptionFilter(unsigned int code, struct _EXCEPTION_POINTERS* ep) {
00430         // FIXME: if (ep->ExceptionRecord->ExceptionFlags & EXCEPTION_NONCONTINUABLE)
00431         return EXCEPTION_EXECUTE_HANDLER;
00432 }
00433 
00434 // returns 0 if an exception was caught
00435 bool __stdcall InvokeExWithCrashRpt(IMgaComponentEx* compex, IMgaProject* project, IMgaFCO* focusobj, IMgaFCOs* selectedobjs, long param, HRESULT& hr) {
00436         __try {
00437                 __try {
00438                         hr = compex->InvokeEx(project, focusobj, selectedobjs, param);
00439                 } __except(crExceptionFilter(GetExceptionCode(), GetExceptionInformation())) {
00440                         return 0;
00441                 }
00442                 // If run outside of GME, CrashRpt will not be set up, and crExceptionFilter will return EXCEPTION_CONTINUE_SEARCH
00443         } __except(nopExceptionFilter(GetExceptionCode(), GetExceptionInformation())) {
00444                 return 0;
00445         }
00446         return 1;
00447 }
00448 
00449 STDMETHODIMP CMgaLauncher::RunComponent(BSTR progid, IMgaProject *project, IMgaFCO *focusobj, IMgaFCOs *selectedobjs, long param)
00450 {
00451         if( project == NULL )
00452                 COMRETURN(E_POINTER);
00453 
00454         COMTRY
00455         {
00456                 AFX_MANAGE_STATE(AfxGetStaticModuleState());
00457 
00458                 CComObjPtr<IMgaRegistrar> registrar;
00459                 COMTHROW( registrar.CoCreateInstance(OLESTR("MGA.MgaRegistrar")) );
00460         
00461                 CComBSTR prgid = progid;
00462                 if (prgid.Length() == 0) {
00463                         CComObjPtr<IMgaMetaProject> paradigm;
00464                         COMTHROW( project->get_RootMeta(PutOut(paradigm)) );
00465                         ASSERT( paradigm != NULL );
00466         
00467                         CComBstrObj parname;
00468                         COMTHROW( paradigm->get_Name(PutOut(parname)) );
00469 
00470 
00471                         CComVariant v;
00472                         COMTHROW( registrar->get_AssociatedComponents(parname, 
00473                         COMPONENTTYPE_INTERPRETER, REGACCESS_BOTH, PutOut(v)) );
00474 
00475                         CStringArray comps;
00476                         CopyTo(v, comps);
00477 
00478                         if( comps.GetSize() == 0 )
00479                         {
00480                                 if( AfxMessageBox(_T("There are no registered interpreters for this paradigm. ")
00481                                         _T("Do you want to install your interpreter now?"), MB_YESNO) != IDYES )
00482                                         COMRETURN(S_FALSE);
00483                         }
00484                 
00485                         if( comps.GetSize() == 1 )
00486                                 prgid = comps[0];
00487                         else
00488                         {
00489                                 CCompDlg dlg;
00490                                 dlg.onOKoper = _T("Interpret...");
00491 
00492                                 dlg.paradigm = parname;
00493                                 dlg.type = COMPONENTTYPE_INTERPRETER;
00494 
00495                                 if( dlg.DoModal() != IDOK )
00496                                         COMRETURN(S_OK);
00497 
00498                                 prgid = dlg.progid;
00499                         }
00500 
00501                         if (prgid.Length() == 0)
00502                                 COMRETURN(S_FALSE);
00503                 }
00504 
00505 
00506                 componenttype_enum type;
00507                 if (FAILED(registrar->QueryComponent(prgid, &type, NULL, REGACCESS_PRIORITY)))
00508                         type = COMPONENTTYPE_INTERPRETER;
00509                 CComPtr<IMgaComponent> component;
00510                 // Before DispatchProxy: CComObjPtr<IMgaComponent> component;
00511                 CString compname = prgid;
00512                 if(type & COMPONENTTYPE_SCRIPT) {
00513                         CComBSTR engine, scriptfile;
00514                         COMTHROW(registrar->get_ComponentExtraInfo(REGACCESS_PRIORITY, prgid, CComBSTR(L"ExecEngine"), &engine));
00515                         COMTHROW(registrar->get_ComponentExtraInfo(REGACCESS_PRIORITY, prgid, CComBSTR(L"ScriptFile"), &scriptfile));
00516                         if(!engine || !scriptfile) {
00517                                 ThrowCOMError(E_FAIL, _T("Incomplete registration for script component ") + compname);
00518                         }
00519                         compname += _T(" (") + CString(engine) + _T(")");
00520                         COMTHROW( component.CoCreateInstance(engine) );
00521                         CComQIPtr<IMgaComponentEx> compex = component;
00522                         if(!compex) {
00523                                 ThrowCOMError(E_MGA_NOT_SUPPORTED, L"Exec.engine is only supported with extended component interface");
00524                         }
00525                         if(scriptfile) {
00526                                 compex->ComponentParameter[_bstr_t(L"script")] = CComVariant(scriptfile);
00527                         }
00528                 }
00529                 else
00530                 {
00531                         HRESULT hr = CreateMgaComponent(component, prgid);
00532                         if (FAILED(hr))
00533                                 return hr;
00534                 }
00535 
00536 
00537                 if(component == NULL) {
00538                         ThrowCOMError(E_FAIL, L"Could not start component '" + compname + "'");
00539                 }
00540                 else {
00541                         IGMEVersionInfoPtr vi = (IMgaComponent*) component;
00542                         if (vi)
00543                         {
00544                                 GMEInterfaceVersion vv = vi->version;
00545                                 if(vv != INTERFACE_VERSION) {
00546                                         CString aa;
00547                                         aa.Format(_T("The interface version number of this component (%d.%d) differs from the GME version (%d.%d)\n")
00548                                                                 _T("This will probably result in serious malfunctions\n")
00549                                                                 _T("Do you want to proceed anyway?"), vv/0x10000,vv%0x10000, INTERFACE_VERSION/0x10000, INTERFACE_VERSION%0x10000); 
00550                                         if(AfxMessageBox(aa, MB_YESNO) !=IDYES) return S_OK;
00551                                 }
00552                         }
00553                         if(parameter.vt != VT_BOOL || parameter.boolVal != VARIANT_TRUE) { 
00554                                 CComQIPtr<IMgaComponentEx> compex = component;
00555                                 if (compex) {
00556                                         CComQIPtr<ISupportErrorInfo> supportErrorInfo = component;
00557                                         HRESULT hr = component->Initialize(project);
00558                                         // Need to catch SEH exceptions (especially for Win7 x64: see GME-318)
00559                                         if (SUCCEEDED(hr) && !InvokeExWithCrashRpt(compex, project, focusobj, selectedobjs, param, hr)) {
00560                                                 if (project->ProjectStatus & 8)
00561                                                         project->AbortTransaction();
00562                                                 ThrowCOMError(E_POINTER, _T("An error has occurred in component ") + compname + _T(".\n")
00563                                                         _T("GME may not be in a stable state.\n")
00564                                                         _T("Please save your work and restart GME."));
00565                                         } else {
00566                                                 if (!SUCCEEDED(hr)) {
00567                                                         _bstr_t desc;
00568                                                         if (supportErrorInfo && GetErrorInfo(desc.GetAddress())) {
00569                                                                 CString msg = static_cast<const TCHAR*>(desc);
00570                                                                 msg = "Interpreter returned error: " + msg;
00571                                                                 ThrowCOMError(hr, msg);
00572                                                         } else {
00573                                                                 ThrowCOMError(hr, _T("Interpreter returned error"));
00574                                                         }
00575                                                 }
00576                                                 // Sometimes interpreters forget to close transactions, even when returning S_OK
00577                                                 if (project->ProjectStatus & 8)
00578                                                         project->AbortTransaction();
00579                                         }
00580                                 } else {
00581                                         try     {
00582                                                 COMTHROW(component->Initialize(project));
00583                                                 CComPtr<IMgaTerritory> terr;
00584                                                 COMTHROW(project->CreateTerritory(NULL, &terr, 0));
00585                                                 COMTHROW(project->BeginTransaction(terr, TRANSACTION_GENERAL));
00586                                                 try     {
00587                                                         COMTHROW( component->Invoke(project, selectedobjs, param) );
00588                                                         COMTHROW(project->CommitTransaction());
00589                                                 }
00590                                                 catch(...)
00591                                                 {
00592                                                         project->AbortTransaction();
00593                                                         throw;
00594                                                 }
00595                                         }
00596                                         catch(hresult_exception &e)     {
00597                                                 project->AbortTransaction();
00598                                                 ThrowCOMError(e.hr, _T("Interpreter returned error"));
00599                                         }
00600                                         catch(...)
00601                                         {
00602                                                 project->AbortTransaction();
00603                                                 AfxMessageBox(_T("An error has occurred in component ") + compname + _T(".\n")
00604                                                         _T("GME may not be in a stable state.\n")
00605                                                         _T("Please save your work and restart GME."));
00606                                         } 
00607                                 }
00608                         }
00609                         else {          // running unprotected
00610                                 try     {
00611                                         COMTHROW(component->Initialize(project));
00612                                         IMgaComponentExPtr compex = (IMgaComponent*)component;
00613                                         if(compex) {
00614                                                 compex->__InvokeEx(project, focusobj, CComQIPtr<IMgaFCOs>(selectedobjs), param);
00615                                         }
00616                                         else {
00617                                                 CComPtr<IMgaTerritory> terr;
00618                                                 COMTHROW(project->CreateTerritory(NULL, &terr, 0));
00619                                                 COMTHROW(project->BeginTransaction(terr, TRANSACTION_GENERAL));
00620                                                 try     {               
00621                                                         COMTHROW( component->Invoke(project, selectedobjs, param) );
00622                                                         COMTHROW(project->CommitTransaction());
00623                                                 }
00624                                                 catch(...)
00625                                                 {
00626                                                         project->AbortTransaction();
00627                                                         throw;
00628                                                 }
00629                                         }
00630                                 }
00631                                 catch(hresult_exception &e)     {
00632                                         DisplayError(_T("Interpreter returned error"), e.hr);
00633                                 }
00634                                 if (project->ProjectStatus & 8)
00635                                         project->AbortTransaction();
00636                         }                               
00637                 }
00638                 component.Release();
00639                 CoFreeUnusedLibraries();
00640         } COMCATCH(CoFreeUnusedLibraries(););
00641 }
00642 
00643 // ------ Helper functions
00644 
00645 CString CMgaLauncher::PruneConnectionString(const CString &conn)
00646 {
00647         CString ret;
00648 
00649         int p = 0;
00650         while( p < conn.GetLength() )
00651         {
00652                 int q = conn.Find(';', p);
00653                 if( q < 0 )
00654                         q = conn.GetLength();
00655 
00656                 CString part((const TCHAR*)conn + p, q-p);
00657 
00658                 int r = part.Find('=');
00659                 if( r < 0 )
00660                         r = part.GetLength();
00661 
00662                 CString key((const TCHAR*)part, r);
00663 
00664                 if( key == _T("UID") ||
00665                         key == _T("PWD") ||
00666                         key == _T("USER") ||
00667                         key == _T("PASSWORD") )
00668                 {
00669                         if( !ret.IsEmpty() )
00670                                 ret += _T(";");
00671 
00672                         ret += part;
00673                 }
00674 
00675                 p = q+1;
00676         }
00677 
00678         return ret;
00679 }
00680 
00681 
00682 STDMETHODIMP CMgaLauncher::RegistryBrowser(IMgaObject *obj)
00683 {
00684         AFX_MANAGE_STATE(AfxGetStaticModuleState());
00685 
00686         COMTRY
00687         {
00688                 
00689                 CRegistryBrowserDlg dlg(obj);
00690                 if (dlg.DoModal() == IDOK) {
00691                         dlg.UpdateRegistry();
00692                 }
00693         }
00694         COMCATCH(;)
00695 }
00696 
00697 STDMETHODIMP CMgaLauncher::AnnotationBrowser(IMgaObject *obj, IMgaRegNode *focus)
00698 {
00699         AFX_MANAGE_STATE(AfxGetStaticModuleState());
00700 
00701         COMTRY
00702         {
00703                 CComPtr<IMgaModel> model;
00704                 if ( SUCCEEDED( obj->QueryInterface(&model) )) {
00705                         CComPtr<IMgaRegNode> currAnn(focus);
00706                         CAnnotationBrowserDlg dlg(model, currAnn);
00707 
00708                         dlg.m_model = model;
00709                         if (dlg.DoModal() == IDOK) {
00710                                 dlg.UpdateAnnotations();
00711                         } else {
00712                                 return E_MGA_MUST_ABORT;        // JIRA GME-236: special ret code, indicating that the dialog was cancelled
00713                         }
00714                 }
00715                 else {
00716                         AfxMessageBox(_T("Unsupported object type for Annotation Browser."));
00717                 }
00718         }
00719         COMCATCH(;)
00720 }