OLD | NEW |
| (Empty) |
1 // Copyright 2003-2010 Google Inc. | |
2 // | |
3 // Licensed under the Apache License, Version 2.0 (the "License"); | |
4 // you may not use this file except in compliance with the License. | |
5 // You may obtain a copy of the License at | |
6 // | |
7 // http://www.apache.org/licenses/LICENSE-2.0 | |
8 // | |
9 // Unless required by applicable law or agreed to in writing, software | |
10 // distributed under the License is distributed on an "AS IS" BASIS, | |
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
12 // See the License for the specific language governing permissions and | |
13 // limitations under the License. | |
14 // ======================================================================== | |
15 | |
16 #include "omaha/base/app_util.h" | |
17 #include <shlwapi.h> | |
18 #include <atlsecurity.h> | |
19 #include <vector> | |
20 #include "omaha/base/cgi.h" | |
21 #include "omaha/base/constants.h" | |
22 #include "omaha/base/debug.h" | |
23 #include "omaha/base/error.h" | |
24 #include "omaha/base/file.h" | |
25 #include "omaha/base/file_ver.h" | |
26 #include "omaha/base/logging.h" | |
27 #include "omaha/base/path.h" | |
28 #include "omaha/base/reg_key.h" | |
29 #include "omaha/base/string.h" | |
30 #include "omaha/base/utils.h" | |
31 | |
32 namespace omaha { | |
33 | |
34 namespace app_util { | |
35 | |
36 HMODULE GetModuleHandleFromAddress(void* address) { | |
37 MEMORY_BASIC_INFORMATION mbi = {0}; | |
38 DWORD result = ::VirtualQuery(address, &mbi, sizeof(mbi)); | |
39 ASSERT1(result == sizeof(mbi)); | |
40 return static_cast<HMODULE>(mbi.AllocationBase); | |
41 } | |
42 | |
43 HMODULE GetCurrentModuleHandle() { | |
44 return GetModuleHandleFromAddress(GetCurrentModuleHandle); | |
45 } | |
46 | |
47 | |
48 CString GetModulePath(HMODULE module_handle) { | |
49 ASSERT1(IsModuleHandleValid(module_handle)); | |
50 CString mod_path; | |
51 | |
52 DWORD result = ::GetModuleFileName(module_handle, | |
53 mod_path.GetBufferSetLength(MAX_PATH), | |
54 MAX_PATH); | |
55 mod_path.ReleaseBuffer(); | |
56 ASSERT1(result == static_cast<DWORD>(mod_path.GetLength())); | |
57 | |
58 return mod_path; | |
59 } | |
60 | |
61 CString GetModuleDirectory(HMODULE module_handle) { | |
62 ASSERT1(IsModuleHandleValid(module_handle)); | |
63 return GetDirectoryFromPath(GetModulePath(module_handle)); | |
64 } | |
65 | |
66 CString GetModuleName(HMODULE module_handle) { | |
67 ASSERT1(IsModuleHandleValid(module_handle)); | |
68 CString app_name(GetFileFromPath(GetModulePath(module_handle))); | |
69 | |
70 UTIL_LOG(L5, (_T("[GetModuleName][module 0x%08x][path '%s'][name '%s']"), | |
71 module_handle, GetModulePath(module_handle), app_name)); | |
72 | |
73 return app_name; | |
74 } | |
75 | |
76 CString GetModuleNameWithoutExtension(HMODULE module_handle) { | |
77 ASSERT1(IsModuleHandleValid(module_handle)); | |
78 CString module_name(GetPathRemoveExtension(GetModuleName(module_handle))); | |
79 | |
80 UTIL_LOG(L5, (_T("[GetModuleNameWithoutExtension]") | |
81 _T("[module 0x%08x][module '%s'][name '%s']"), | |
82 module_handle, GetModulePath(module_handle), module_name)); | |
83 | |
84 return module_name; | |
85 } | |
86 | |
87 CString GetCurrentModulePath() { | |
88 return GetModulePath(GetCurrentModuleHandle()); | |
89 } | |
90 | |
91 CString GetCurrentModuleDirectory() { | |
92 return GetModuleDirectory(GetCurrentModuleHandle()); | |
93 } | |
94 | |
95 CString GetCurrentModuleName() { | |
96 return GetModuleName(GetCurrentModuleHandle()); | |
97 } | |
98 | |
99 CString GetCurrentModuleNameWithoutExtension() { | |
100 return GetModuleNameWithoutExtension(GetCurrentModuleHandle()); | |
101 } | |
102 | |
103 bool IsAddressInCurrentModule(void* address) { | |
104 return GetCurrentModuleHandle() == GetModuleHandleFromAddress(address); | |
105 } | |
106 | |
107 CString GetHostName() { | |
108 CString hostName; | |
109 DWORD name_len = MAX_COMPUTERNAME_LENGTH + 1; | |
110 bool result = !!::GetComputerName(hostName.GetBufferSetLength(name_len), | |
111 &name_len); | |
112 ASSERT1(result); | |
113 hostName.ReleaseBuffer(); | |
114 ASSERT1(name_len == static_cast<DWORD>(hostName.GetLength())); | |
115 | |
116 return hostName; | |
117 } | |
118 | |
119 CString GetWindowsDir() { | |
120 CString windows_path; | |
121 | |
122 DWORD result = ::GetWindowsDirectory( | |
123 windows_path.GetBufferSetLength(MAX_PATH), MAX_PATH); | |
124 windows_path.ReleaseBuffer(); | |
125 ASSERT1(result == static_cast<DWORD>(windows_path.GetLength())); | |
126 | |
127 return windows_path; | |
128 } | |
129 | |
130 CString GetSystemDir() { | |
131 CString systemPath; | |
132 | |
133 DWORD result = ::GetSystemDirectory(systemPath.GetBufferSetLength(MAX_PATH), | |
134 MAX_PATH); | |
135 systemPath.ReleaseBuffer(); | |
136 ASSERT1(result == static_cast<DWORD>(systemPath.GetLength())); | |
137 | |
138 return systemPath; | |
139 } | |
140 | |
141 CString GetTempDir() { | |
142 CString tempPath; | |
143 | |
144 DWORD result = ::GetTempPath(MAX_PATH, tempPath.GetBufferSetLength(MAX_PATH)); | |
145 tempPath.ReleaseBuffer(); | |
146 ASSERT1(result == static_cast<DWORD>(tempPath.GetLength())); | |
147 | |
148 return tempPath; | |
149 } | |
150 | |
151 bool IsModuleHandleValid(HMODULE module_handle) { | |
152 if (!module_handle) { | |
153 return true; | |
154 } | |
155 return module_handle == GetModuleHandleFromAddress(module_handle); | |
156 } | |
157 | |
158 DWORD DllGetVersion(const CString& dll_path) { | |
159 HINSTANCE hInst = ::GetModuleHandle(dll_path); | |
160 ASSERT(hInst, | |
161 (_T("[GetModuleHandle failed][%s][%d]"), dll_path, ::GetLastError())); | |
162 DWORD dwVersion = 0; | |
163 DLLGETVERSIONPROC pfn = reinterpret_cast<DLLGETVERSIONPROC>( | |
164 ::GetProcAddress(hInst, "DllGetVersion")); | |
165 if (pfn != NULL) { | |
166 DLLVERSIONINFO dvi = {0}; | |
167 dvi.cbSize = sizeof(dvi); | |
168 HRESULT hr = (*pfn)(&dvi); | |
169 if (SUCCEEDED(hr)) { | |
170 // Since we're fitting both the major and minor versions into a DWORD, | |
171 // let's sanity check that we're not in an overflow situation here | |
172 ASSERT1(dvi.dwMajorVersion <= 0xFFFF); | |
173 ASSERT1(dvi.dwMinorVersion <= 0xFFFF); | |
174 dwVersion = MAKELONG(dvi.dwMinorVersion, dvi.dwMajorVersion); | |
175 } | |
176 } | |
177 return dwVersion; | |
178 } | |
179 | |
180 DWORD SystemDllGetVersion(const TCHAR* dll_name) { | |
181 ASSERT1(dll_name); | |
182 CString full_dll_path(String_MakeEndWith(GetSystemDir(), _T("\\"), false) + | |
183 dll_name); | |
184 ASSERT1(File::Exists(full_dll_path)); | |
185 return DllGetVersion(full_dll_path); | |
186 } | |
187 | |
188 ULONGLONG GetVersionFromModule(HMODULE instance) { | |
189 TCHAR module_path[MAX_PATH] = {0}; | |
190 if (!::GetModuleFileName(instance, module_path, MAX_PATH) != 0) { | |
191 return 0; | |
192 } | |
193 | |
194 return GetVersionFromFile(module_path); | |
195 } | |
196 | |
197 ULONGLONG GetVersionFromFile(const CString& file_path) { | |
198 FileVer existing_file_ver; | |
199 if (!existing_file_ver.Open(file_path)) { | |
200 return 0; | |
201 } | |
202 | |
203 return existing_file_ver.GetFileVersionAsULONGLONG(); | |
204 } | |
205 | |
206 // Returns a temporary dir for the impersonated user and an empty string if | |
207 // the user is not impersonated or an error occurs. | |
208 CString GetTempDirForImpersonatedUser() { | |
209 CAccessToken access_token; | |
210 if (!access_token.GetThreadToken(TOKEN_READ)) { | |
211 return NULL; | |
212 } | |
213 | |
214 CString temp_dir; | |
215 if (::ExpandEnvironmentStringsForUser(access_token.GetHandle(), | |
216 _T("%TMP%"), | |
217 CStrBuf(temp_dir, MAX_PATH), | |
218 MAX_PATH)) { | |
219 return temp_dir; | |
220 } | |
221 if (::ExpandEnvironmentStringsForUser(access_token.GetHandle(), | |
222 _T("%TEMP%"), | |
223 CStrBuf(temp_dir, MAX_PATH), | |
224 MAX_PATH)) { | |
225 return temp_dir; | |
226 } | |
227 | |
228 const int kCsIdl = CSIDL_LOCAL_APPDATA | CSIDL_FLAG_DONT_VERIFY; | |
229 if (SUCCEEDED(GetFolderPath(kCsIdl, &temp_dir)) && | |
230 ::PathAppend(CStrBuf(temp_dir, MAX_PATH), LOCAL_APPDATA_REL_TEMP_DIR)) { | |
231 return temp_dir; | |
232 } | |
233 | |
234 return NULL; | |
235 } | |
236 | |
237 | |
238 CString GetTempDirForImpersonatedOrCurrentUser() { | |
239 CString temp_dir_for_impersonated_user(GetTempDirForImpersonatedUser()); | |
240 if (!temp_dir_for_impersonated_user.IsEmpty()) { | |
241 CStrBuf string_buffer(temp_dir_for_impersonated_user, MAX_PATH); | |
242 if (::PathAddBackslash(string_buffer)) { | |
243 return temp_dir_for_impersonated_user; | |
244 } | |
245 } | |
246 return app_util::GetTempDir(); | |
247 } | |
248 | |
249 } // namespace app_util | |
250 | |
251 } // namespace omaha | |
252 | |
OLD | NEW |