154c06456SAndrew Rist /************************************************************** 2cdf0e10cSrcweir * 354c06456SAndrew Rist * Licensed to the Apache Software Foundation (ASF) under one 454c06456SAndrew Rist * or more contributor license agreements. See the NOTICE file 554c06456SAndrew Rist * distributed with this work for additional information 654c06456SAndrew Rist * regarding copyright ownership. The ASF licenses this file 754c06456SAndrew Rist * to you under the Apache License, Version 2.0 (the 854c06456SAndrew Rist * "License"); you may not use this file except in compliance 954c06456SAndrew Rist * with the License. You may obtain a copy of the License at 10cdf0e10cSrcweir * 1154c06456SAndrew Rist * http://www.apache.org/licenses/LICENSE-2.0 12cdf0e10cSrcweir * 1354c06456SAndrew Rist * Unless required by applicable law or agreed to in writing, 1454c06456SAndrew Rist * software distributed under the License is distributed on an 1554c06456SAndrew Rist * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 1654c06456SAndrew Rist * KIND, either express or implied. See the License for the 1754c06456SAndrew Rist * specific language governing permissions and limitations 1854c06456SAndrew Rist * under the License. 19cdf0e10cSrcweir * 2054c06456SAndrew Rist *************************************************************/ 2154c06456SAndrew Rist 2254c06456SAndrew Rist 23cdf0e10cSrcweir 24cdf0e10cSrcweir // Use UNICODE Windows and C API. 25cdf0e10cSrcweir #define _UNICODE 26cdf0e10cSrcweir #define UNICODE 27cdf0e10cSrcweir 28cdf0e10cSrcweir #ifdef _MSC_VER 29cdf0e10cSrcweir #pragma warning(push, 1) 30cdf0e10cSrcweir #endif 31cdf0e10cSrcweir #include <windows.h> 32cdf0e10cSrcweir #include "uno/environment.hxx" 33cdf0e10cSrcweir #ifdef _MSC_VER 34cdf0e10cSrcweir #pragma warning(pop) 35cdf0e10cSrcweir #endif 36cdf0e10cSrcweir 37cdf0e10cSrcweir #include <tchar.h> 38cdf0e10cSrcweir 39cdf0e10cSrcweir #include "native_share.h" 40cdf0e10cSrcweir 41cdf0e10cSrcweir #include "rtl/bootstrap.hxx" 42cdf0e10cSrcweir #include "com/sun/star/uno/XComponentContext.hpp" 43cdf0e10cSrcweir #include "cppuhelper/bootstrap.hxx" 44cdf0e10cSrcweir #include <delayimp.h> 45cdf0e10cSrcweir #include <stdio.h> 46cdf0e10cSrcweir 47cdf0e10cSrcweir using namespace ::rtl; 48cdf0e10cSrcweir using namespace ::com::sun::star; 49cdf0e10cSrcweir using namespace ::com::sun::star::uno; 50cdf0e10cSrcweir 51cdf0e10cSrcweir namespace cli_ure { 52cdf0e10cSrcweir WCHAR * resolveLink(WCHAR * path); 53cdf0e10cSrcweir } 54cdf0e10cSrcweir 55ff3f4ebcSOliver-Rainer Wittmann // INSTALL_PATH value needs to correspond to the Windows registry subkey 56ff3f4ebcSOliver-Rainer Wittmann // in main\scp2\source\ooo\registryitem_ooo.scp 57599cc5b4SOliver-Rainer Wittmann #define INSTALL_PATH L"Software\\OpenOffice\\UNO\\InstallPath" 583889e2e9SJürgen Schmidt #define INSTALL_PATH_64 L"Software\\Wow6432Node\\OpenOffice\\UNO\\InstallPath" 59cdf0e10cSrcweir #define UNO_PATH L"UNO_PATH" 60cdf0e10cSrcweir 61cdf0e10cSrcweir namespace 62cdf0e10cSrcweir { 63cdf0e10cSrcweir 64cdf0e10cSrcweir /* 65cdf0e10cSrcweir * Gets the installation path from the Windows Registry for the specified 66cdf0e10cSrcweir * registry key. 67cdf0e10cSrcweir * 68cdf0e10cSrcweir * @param hroot open handle to predefined root registry key 69cdf0e10cSrcweir * @param subKeyName name of the subkey to open 70cdf0e10cSrcweir * 71cdf0e10cSrcweir * @return the installation path or NULL, if no installation was found or 72*07a3d7f1SPedro Giffuni * if an error occurred 73cdf0e10cSrcweir */ 74cdf0e10cSrcweir WCHAR* getPathFromRegistryKey( HKEY hroot, LPCWSTR subKeyName ) 75cdf0e10cSrcweir { 76cdf0e10cSrcweir HKEY hkey; 77cdf0e10cSrcweir DWORD type; 78cdf0e10cSrcweir TCHAR* data = NULL; 79cdf0e10cSrcweir DWORD size; 80cdf0e10cSrcweir 81cdf0e10cSrcweir /* open the specified registry key */ 82cdf0e10cSrcweir if ( RegOpenKeyEx( hroot, subKeyName, 0, KEY_READ, &hkey ) != ERROR_SUCCESS ) 83cdf0e10cSrcweir { 84cdf0e10cSrcweir return NULL; 85cdf0e10cSrcweir } 86cdf0e10cSrcweir 87cdf0e10cSrcweir /* find the type and size of the default value */ 88cdf0e10cSrcweir if ( RegQueryValueEx( hkey, NULL, NULL, &type, NULL, &size) != ERROR_SUCCESS ) 89cdf0e10cSrcweir { 90cdf0e10cSrcweir RegCloseKey( hkey ); 91cdf0e10cSrcweir return NULL; 92cdf0e10cSrcweir } 93cdf0e10cSrcweir 94cdf0e10cSrcweir /* get memory to hold the default value */ 95cdf0e10cSrcweir data = new WCHAR[size]; 96cdf0e10cSrcweir 97cdf0e10cSrcweir /* read the default value */ 98cdf0e10cSrcweir if ( RegQueryValueEx( hkey, NULL, NULL, &type, (LPBYTE) data, &size ) != ERROR_SUCCESS ) 99cdf0e10cSrcweir { 100cdf0e10cSrcweir RegCloseKey( hkey ); 101cdf0e10cSrcweir return NULL; 102cdf0e10cSrcweir } 103cdf0e10cSrcweir 104cdf0e10cSrcweir /* release registry key handle */ 105cdf0e10cSrcweir RegCloseKey( hkey ); 106cdf0e10cSrcweir 107cdf0e10cSrcweir return data; 108cdf0e10cSrcweir } 109cdf0e10cSrcweir 110cdf0e10cSrcweir /* Returns the path to the program folder of the brand layer, 111cdf0e10cSrcweir for example c:/openoffice.org 3/program 112cdf0e10cSrcweir This path is either obtained from the environment variable UNO_PATH 113cdf0e10cSrcweir or the registry item 114599cc5b4SOliver-Rainer Wittmann "Software\\OpenOffice\\UNO\\InstallPath" 115cdf0e10cSrcweir either in HKEY_CURRENT_USER or HKEY_LOCAL_MACHINE 116cdf0e10cSrcweir The return value must be freed with delete[] 117cdf0e10cSrcweir */ 118cdf0e10cSrcweir WCHAR * getInstallPath() 119cdf0e10cSrcweir { 120cdf0e10cSrcweir WCHAR * szInstallPath = NULL; 121cdf0e10cSrcweir 122cdf0e10cSrcweir DWORD cChars = GetEnvironmentVariable(UNO_PATH, NULL, 0); 123cdf0e10cSrcweir if (cChars > 0) 124cdf0e10cSrcweir { 12538e1b26aSJürgen Schmidt szInstallPath = new WCHAR[cChars+1]; 12638e1b26aSJürgen Schmidt cChars = GetEnvironmentVariable(UNO_PATH, szInstallPath, cChars+1); 127cdf0e10cSrcweir //If PATH is not set then it is no error 128cdf0e10cSrcweir if (cChars == 0) 129cdf0e10cSrcweir { 130cdf0e10cSrcweir delete[] szInstallPath; 131cdf0e10cSrcweir return NULL; 132cdf0e10cSrcweir } 133cdf0e10cSrcweir } 134cdf0e10cSrcweir 135cdf0e10cSrcweir if (! szInstallPath) 136cdf0e10cSrcweir { 137cdf0e10cSrcweir szInstallPath = getPathFromRegistryKey( HKEY_CURRENT_USER, INSTALL_PATH ); 138cdf0e10cSrcweir if ( szInstallPath == NULL ) 139cdf0e10cSrcweir { 1403889e2e9SJürgen Schmidt /* read the key's default value from HKEY_LOCAL_USER */ 14138e1b26aSJürgen Schmidt szInstallPath = getPathFromRegistryKey( HKEY_CURRENT_USER, INSTALL_PATH_64 ); 1423889e2e9SJürgen Schmidt } 14338e1b26aSJürgen Schmidt if ( szInstallPath == NULL ) 1443889e2e9SJürgen Schmidt { 145cdf0e10cSrcweir /* read the key's default value from HKEY_LOCAL_MACHINE */ 146cdf0e10cSrcweir szInstallPath = getPathFromRegistryKey( HKEY_LOCAL_MACHINE, INSTALL_PATH ); 147cdf0e10cSrcweir } 14838e1b26aSJürgen Schmidt if ( szInstallPath == NULL ) 1493889e2e9SJürgen Schmidt { 1503889e2e9SJürgen Schmidt /* read the key's default value from HKEY_LOCAL_MACHINE */ 1513889e2e9SJürgen Schmidt szInstallPath = getPathFromRegistryKey( HKEY_LOCAL_MACHINE, INSTALL_PATH_64 ); 1523889e2e9SJürgen Schmidt } 153cdf0e10cSrcweir } 154cdf0e10cSrcweir return szInstallPath; 155cdf0e10cSrcweir } 156cdf0e10cSrcweir 157cdf0e10cSrcweir 158cdf0e10cSrcweir /*We extend the path to contain the Ure/bin folder, 159cdf0e10cSrcweir so that components can use osl_loadModule with arguments, such as 160cdf0e10cSrcweir "reg3.dll". That is, the arguments are only the library names. 161cdf0e10cSrcweir */ 162cdf0e10cSrcweir void extendPath(LPCWSTR szUreBinPath) 163cdf0e10cSrcweir { 164cdf0e10cSrcweir if (!szUreBinPath) 165cdf0e10cSrcweir return; 166cdf0e10cSrcweir 167cdf0e10cSrcweir WCHAR * sEnvPath = NULL; 168cdf0e10cSrcweir DWORD cChars = GetEnvironmentVariable(L"PATH", sEnvPath, 0); 169cdf0e10cSrcweir if (cChars > 0) 170cdf0e10cSrcweir { 171cdf0e10cSrcweir sEnvPath = new WCHAR[cChars]; 172cdf0e10cSrcweir cChars = GetEnvironmentVariable(L"PATH", sEnvPath, cChars); 173cdf0e10cSrcweir //If PATH is not set then it is no error 174cdf0e10cSrcweir if (cChars == 0 && GetLastError() != ERROR_ENVVAR_NOT_FOUND) 175cdf0e10cSrcweir { 176cdf0e10cSrcweir delete[] sEnvPath; 177cdf0e10cSrcweir return; 178cdf0e10cSrcweir } 179cdf0e10cSrcweir } 180cdf0e10cSrcweir //prepare the new PATH. Add the Ure/bin directory at the front. 181cdf0e10cSrcweir //note also adding ';' 182cdf0e10cSrcweir WCHAR * sNewPath = new WCHAR[lstrlen(sEnvPath) + lstrlen(szUreBinPath) + 2]; 183cdf0e10cSrcweir sNewPath[0] = L'\0'; 184cdf0e10cSrcweir lstrcat(sNewPath, szUreBinPath); 185cdf0e10cSrcweir if (lstrlen(sEnvPath)) 186cdf0e10cSrcweir { 187cdf0e10cSrcweir lstrcat(sNewPath, L";"); 188cdf0e10cSrcweir lstrcat(sNewPath, sEnvPath); 189cdf0e10cSrcweir } 190cdf0e10cSrcweir BOOL bSet = SetEnvironmentVariable(L"PATH", sNewPath); 191cdf0e10cSrcweir 192cdf0e10cSrcweir delete[] sEnvPath; 193cdf0e10cSrcweir delete[] sNewPath; 194cdf0e10cSrcweir } 195cdf0e10cSrcweir 196cdf0e10cSrcweir 197cdf0e10cSrcweir HMODULE loadFromPath(LPCWSTR sLibName) 198cdf0e10cSrcweir { 199cdf0e10cSrcweir if (sLibName == NULL) 200cdf0e10cSrcweir return NULL; 201cdf0e10cSrcweir 2023889e2e9SJürgen Schmidt WCHAR * szUreBinPath = getInstallPath(); 203cdf0e10cSrcweir if (!szUreBinPath) 204cdf0e10cSrcweir return NULL; 205cdf0e10cSrcweir 206cdf0e10cSrcweir extendPath(szUreBinPath); 207cdf0e10cSrcweir 208cdf0e10cSrcweir WCHAR* szFullPath = new WCHAR[lstrlen(sLibName) + lstrlen(szUreBinPath) + 2]; 209cdf0e10cSrcweir szFullPath[0] = L'\0'; 210cdf0e10cSrcweir lstrcat(szFullPath, szUreBinPath); 211cdf0e10cSrcweir lstrcat(szFullPath, L"\\"); 212cdf0e10cSrcweir lstrcat(szFullPath, sLibName); 213cdf0e10cSrcweir HMODULE handle = LoadLibraryEx(szFullPath, NULL, 214cdf0e10cSrcweir LOAD_WITH_ALTERED_SEARCH_PATH); 215cdf0e10cSrcweir 216cdf0e10cSrcweir delete[] szFullPath; 217cdf0e10cSrcweir delete[] szUreBinPath; 218cdf0e10cSrcweir return handle; 219cdf0e10cSrcweir } 220cdf0e10cSrcweir 221cdf0e10cSrcweir /*Hook for delayed loading of libraries which this library is linked with. 222cdf0e10cSrcweir This is a failure hook. That is, it is only called when the loading of 223cdf0e10cSrcweir a library failed. It will be called when loading of cppuhelper failed. 224cdf0e10cSrcweir Because we extend the PATH to the URE/bin folder while this function is 225cdf0e10cSrcweir executed (see extendPath), all other libraries are found. 226cdf0e10cSrcweir */ 227cdf0e10cSrcweir extern "C" FARPROC WINAPI delayLoadHook( 228cdf0e10cSrcweir unsigned dliNotify, 229cdf0e10cSrcweir PDelayLoadInfo pdli 230cdf0e10cSrcweir ) 231cdf0e10cSrcweir { 232cdf0e10cSrcweir if (dliNotify == dliFailLoadLib) 233cdf0e10cSrcweir { 234cdf0e10cSrcweir LPWSTR szLibName = NULL; 235cdf0e10cSrcweir //Convert the ansi file name to wchar_t* 236cdf0e10cSrcweir int size = MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED, pdli->szDll, -1, NULL, 0); 237cdf0e10cSrcweir if (size > 0) 238cdf0e10cSrcweir { 239cdf0e10cSrcweir szLibName = new WCHAR[size]; 240cdf0e10cSrcweir if (! MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED, pdli->szDll, -1, szLibName, size)) 241cdf0e10cSrcweir { 242cdf0e10cSrcweir return 0; 243cdf0e10cSrcweir } 244cdf0e10cSrcweir } 245cdf0e10cSrcweir HANDLE h = loadFromPath(szLibName); 246cdf0e10cSrcweir delete[] szLibName; 247cdf0e10cSrcweir return (FARPROC) h; 248cdf0e10cSrcweir } 249cdf0e10cSrcweir return 0; 250cdf0e10cSrcweir } 251cdf0e10cSrcweir } 252cdf0e10cSrcweir 253cdf0e10cSrcweir ExternC 254cdf0e10cSrcweir PfnDliHook __pfnDliFailureHook2 = delayLoadHook; 255cdf0e10cSrcweir 256cdf0e10cSrcweir namespace uno 257cdf0e10cSrcweir { 258cdf0e10cSrcweir namespace util 259cdf0e10cSrcweir { 260cdf0e10cSrcweir 261cdf0e10cSrcweir /** Bootstrapping native UNO. 262cdf0e10cSrcweir 263cdf0e10cSrcweir Bootstrapping requires the existence of many libraries which are contained 264cdf0e10cSrcweir in an URE installation. To find and load these libraries the Windows 26538e1b26aSJürgen Schmidt registry keys HKEY_CURRENT_USER\Software\OpenOffice\UNO\InstallPath 26638e1b26aSJürgen Schmidt and HKEY_LOCAL_MACHINE\Software\OpenOffice\UNO\InstallPath are examined. 26738e1b26aSJürgen Schmidt The default value contain the path to the office prgoram dir. No seaparate URE 26838e1b26aSJürgen Schmidt anymore. 269cdf0e10cSrcweir */ 270cdf0e10cSrcweir public __sealed __gc class Bootstrap 271cdf0e10cSrcweir { 272cdf0e10cSrcweir inline Bootstrap() {} 273cdf0e10cSrcweir 274cdf0e10cSrcweir public: 275cdf0e10cSrcweir 276cdf0e10cSrcweir /** Bootstraps the initial component context from a native UNO installation. 277cdf0e10cSrcweir 278cdf0e10cSrcweir @see cppuhelper/bootstrap.hxx:defaultBootstrap_InitialComponentContext() 279cdf0e10cSrcweir */ 280cdf0e10cSrcweir static ::unoidl::com::sun::star::uno::XComponentContext * 281cdf0e10cSrcweir defaultBootstrap_InitialComponentContext(); 282cdf0e10cSrcweir 283cdf0e10cSrcweir /** Bootstraps the initial component context from a native UNO installation. 284cdf0e10cSrcweir 285cdf0e10cSrcweir @param ini_file 286cdf0e10cSrcweir a file URL of an ini file, e.g. uno.ini/unorc. (The ini file must 287cdf0e10cSrcweir reside next to the cppuhelper library) 288cdf0e10cSrcweir @param bootstrap_parameters 289cdf0e10cSrcweir bootstrap parameters (maybe null) 290cdf0e10cSrcweir 291cdf0e10cSrcweir @see cppuhelper/bootstrap.hxx:defaultBootstrap_InitialComponentContext() 292cdf0e10cSrcweir */ 293cdf0e10cSrcweir static ::unoidl::com::sun::star::uno::XComponentContext * 294cdf0e10cSrcweir defaultBootstrap_InitialComponentContext( 295cdf0e10cSrcweir ::System::String * ini_file, 296cdf0e10cSrcweir ::System::Collections::IDictionaryEnumerator * 297cdf0e10cSrcweir bootstrap_parameters ); 298cdf0e10cSrcweir 299cdf0e10cSrcweir /** Bootstraps the initial component context from a native UNO installation. 300cdf0e10cSrcweir 301cdf0e10cSrcweir @see cppuhelper/bootstrap.hxx:bootstrap() 302cdf0e10cSrcweir */ 303cdf0e10cSrcweir static ::unoidl::com::sun::star::uno::XComponentContext * 304cdf0e10cSrcweir bootstrap(); 305cdf0e10cSrcweir }; 306cdf0e10cSrcweir 307cdf0e10cSrcweir //______________________________________________________________________________ 308cdf0e10cSrcweir ::unoidl::com::sun::star::uno::XComponentContext * 309cdf0e10cSrcweir Bootstrap::defaultBootstrap_InitialComponentContext( 310cdf0e10cSrcweir ::System::String * ini_file, 311cdf0e10cSrcweir ::System::Collections::IDictionaryEnumerator * bootstrap_parameters ) 312cdf0e10cSrcweir { 313cdf0e10cSrcweir if (0 != bootstrap_parameters) 314cdf0e10cSrcweir { 315cdf0e10cSrcweir bootstrap_parameters->Reset(); 316cdf0e10cSrcweir while (bootstrap_parameters->MoveNext()) 317cdf0e10cSrcweir { 318cdf0e10cSrcweir OUString key( 319cdf0e10cSrcweir String_to_ustring( __try_cast< ::System::String * >( 320cdf0e10cSrcweir bootstrap_parameters->get_Key() ) ) ); 321cdf0e10cSrcweir OUString value( 322cdf0e10cSrcweir String_to_ustring( __try_cast< ::System::String * >( 323cdf0e10cSrcweir bootstrap_parameters->get_Value() ) ) ); 324cdf0e10cSrcweir 325cdf0e10cSrcweir ::rtl::Bootstrap::set( key, value ); 326cdf0e10cSrcweir } 327cdf0e10cSrcweir } 328cdf0e10cSrcweir 329cdf0e10cSrcweir // bootstrap native uno 330cdf0e10cSrcweir Reference< XComponentContext > xContext; 331cdf0e10cSrcweir if (0 == ini_file) 332cdf0e10cSrcweir { 333cdf0e10cSrcweir xContext = ::cppu::defaultBootstrap_InitialComponentContext(); 334cdf0e10cSrcweir } 335cdf0e10cSrcweir else 336cdf0e10cSrcweir { 337cdf0e10cSrcweir xContext = ::cppu::defaultBootstrap_InitialComponentContext( 338cdf0e10cSrcweir String_to_ustring( __try_cast< ::System::String * >( ini_file ) ) ); 339cdf0e10cSrcweir } 340cdf0e10cSrcweir 341cdf0e10cSrcweir return __try_cast< ::unoidl::com::sun::star::uno::XComponentContext * >( 342cdf0e10cSrcweir to_cli( xContext ) ); 343cdf0e10cSrcweir } 344cdf0e10cSrcweir 345cdf0e10cSrcweir //______________________________________________________________________________ 346cdf0e10cSrcweir ::unoidl::com::sun::star::uno::XComponentContext * 347cdf0e10cSrcweir Bootstrap::defaultBootstrap_InitialComponentContext() 348cdf0e10cSrcweir { 349cdf0e10cSrcweir return defaultBootstrap_InitialComponentContext( 0, 0 ); 350cdf0e10cSrcweir } 351cdf0e10cSrcweir 352cdf0e10cSrcweir ::unoidl::com::sun::star::uno::XComponentContext * Bootstrap::bootstrap() 353cdf0e10cSrcweir { 354cdf0e10cSrcweir Reference<XComponentContext> xContext = ::cppu::bootstrap(); 355cdf0e10cSrcweir return __try_cast< ::unoidl::com::sun::star::uno::XComponentContext * >( 356cdf0e10cSrcweir to_cli( xContext ) ); 357cdf0e10cSrcweir 358cdf0e10cSrcweir } 359cdf0e10cSrcweir 360cdf0e10cSrcweir } 361cdf0e10cSrcweir } 362