1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: extendloaderenvironment.cxx,v $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 #include "precompiled_desktop.hxx"
32 #include "sal/config.h"
36 #define WIN32_LEAN_AND_MEAN
38 #pragma warning(push, 1)
46 #include "tools/pathutils.hxx"
48 #include "extendloaderenvironment.hxx"
55 FORMAT_MESSAGE_ALLOCATE_BUFFER
| FORMAT_MESSAGE_FROM_SYSTEM
, NULL
,
56 GetLastError(), 0, reinterpret_cast< LPWSTR
>(&buf
), 0, NULL
);
57 MessageBoxW(NULL
, buf
, NULL
, MB_OK
| MB_ICONERROR
);
59 TerminateProcess(GetCurrentProcess(), 255);
62 bool contains(WCHAR
const * paths
, WCHAR
const * path
, WCHAR
const * pathEnd
) {
63 WCHAR
const * q
= path
;
64 for (WCHAR
const * p
= paths
;; ++p
) {
77 if (q
!= pathEnd
&& *q
== c
) {
90 namespace desktop_win32
{
92 void extendLoaderEnvironment(WCHAR
* binPath
, WCHAR
* iniDirectory
) {
93 if (!GetModuleFileNameW(NULL
, iniDirectory
, MAX_PATH
)) {
96 WCHAR
* iniDirEnd
= tools::filename(iniDirectory
);
97 WCHAR name
[MAX_PATH
+ MY_LENGTH(L
".bin")];
98 // hopefully std::size_t is large enough to not overflow
99 WCHAR
* nameEnd
= name
;
100 for (WCHAR
* p
= iniDirEnd
; *p
!= L
'\0'; ++p
) {
103 if (!(nameEnd
- name
>= 4 && nameEnd
[-4] == L
'.' &&
104 (nameEnd
[-3] == L
'E' || nameEnd
[-3] == L
'e') &&
105 (nameEnd
[-2] == L
'X' || nameEnd
[-2] == L
'x') &&
106 (nameEnd
[-1] == L
'E' || nameEnd
[-1] == L
'e')))
114 tools::buildPath(binPath
, iniDirectory
, iniDirEnd
, name
, nameEnd
- name
);
116 WCHAR path
[MAX_PATH
];
117 WCHAR
* pathEnd
= tools::buildPath(
118 path
, iniDirectory
, iniDirEnd
, MY_STRING(L
"..\\basis-link"));
119 if (pathEnd
== NULL
) {
122 std::size_t const maxEnv
= 32767;
123 WCHAR pad
[2 * MAX_PATH
+ maxEnv
];
124 // hopefully std::size_t is large enough to not overflow
125 WCHAR
* padEnd
= NULL
;
127 DWORD n
= GetEnvironmentVariableW(L
"PATH", env
, maxEnv
);
128 if (n
>= maxEnv
|| n
== 0 && GetLastError() != ERROR_ENVVAR_NOT_FOUND
) {
133 pathEnd
= tools::resolveLink(path
);
134 if (pathEnd
== NULL
) {
135 if (GetLastError() != ERROR_FILE_NOT_FOUND
) {
138 // This path is only taken by testtool.exe in basis program directory;
139 // its PATH needs to include the brand program directory:
140 pathEnd
= tools::buildPath(
141 path
, iniDirectory
, iniDirEnd
, MY_STRING(L
".."));
142 if (pathEnd
== NULL
) {
145 padEnd
= tools::buildPath(
146 pad
, path
, pathEnd
, MY_STRING(L
"\\..\\program"));
147 if (padEnd
== NULL
) {
150 exclude1
= contains(env
, pad
, padEnd
);
154 WCHAR
* pad2
= exclude1
? pad
: padEnd
+ 1;
155 pathEnd
= tools::buildPath(path
, path
, pathEnd
, MY_STRING(L
"\\ure-link"));
156 if (pathEnd
== NULL
) {
159 pathEnd
= tools::resolveLink(path
);
160 if (pathEnd
== NULL
) {
163 padEnd
= tools::buildPath(pad2
, path
, pathEnd
, MY_STRING(L
"\\bin"));
164 if (padEnd
== NULL
) {
167 bool exclude2
= contains(env
, pad2
, padEnd
);
168 if (!(exclude1
&& exclude2
)) {
169 if (!(exclude1
|| exclude2
)) {
172 WCHAR
* p
= exclude2
? pad2
- 1 : padEnd
;
176 for (DWORD i
= 0; i
<= n
; ++i
) {
179 if (!SetEnvironmentVariableW(L
"PATH", pad
)) {