2 * Copyright 2011 André Hentschel
3 * Copyright 2013 Mislav Blažević
4 * Copyright 2015 Mark Jansen
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
21 #define WIN32_NO_STATUS
28 #include "wine/winternl.h"
31 #define DPFLTR_APPCOMPAT_ID 123
34 #define NT_SUCCESS(StatCode) ((NTSTATUS)(StatCode) >= 0)
37 ULONG g_ShimDebugLevel
= 0xffffffff;
39 void ApphelppInitDebugLevel(void)
41 UNICODE_STRING DebugKey
, DebugValue
;
43 ULONG NewLevel
= SHIM_ERR
;
46 RtlInitUnicodeString(&DebugKey
, L
"SHIM_DEBUG_LEVEL");
47 DebugValue
.MaximumLength
= sizeof(Buffer
);
48 DebugValue
.Buffer
= Buffer
;
49 DebugValue
.Length
= 0;
51 /* Hold the lock as short as possible. */
53 Status
= RtlQueryEnvironmentVariable_U(NULL
, &DebugKey
, &DebugValue
);
56 if (NT_SUCCESS(Status
))
58 if (!NT_SUCCESS(RtlUnicodeStringToInteger(&DebugValue
, 10, &NewLevel
)))
61 g_ShimDebugLevel
= NewLevel
;
64 BOOL WINAPI
DllMain( HINSTANCE hinst
, DWORD reason
, LPVOID reserved
)
69 case DLL_WINE_PREATTACH
:
70 return FALSE
; /* prefer native version */
72 case DLL_PROCESS_ATTACH
:
73 DisableThreadLibraryCalls( hinst
);
76 case DLL_PROCESS_DETACH
:
83 BOOL WINAPI
ApphelpCheckInstallShieldPackage(void* ptr
, LPCWSTR path
)
85 SHIM_WARN("stub: ptr=%p, path='%S'\r\n", ptr
, path
);
90 BOOL WINAPI
ApphelpCheckShellObject(REFCLSID ObjectCLSID
, BOOL bShimIfNecessary
, ULONGLONG
*pullFlags
)
92 WCHAR GuidString
[100];
93 if (!ObjectCLSID
|| !SdbGUIDToString(ObjectCLSID
, GuidString
, 100))
94 GuidString
[0] = L
'\0';
95 SHIM_WARN("stub: ObjectCLSID='%S', bShimIfNecessary=%d, pullFlags=%p)\n", GuidString
, bShimIfNecessary
, pullFlags
);
104 * Outputs diagnostic info.
106 * @param [in] Level The level to log this message with, choose any of [SHIM_ERR,
107 * SHIM_WARN, SHIM_INFO].
108 * @param [in] FunctionName The function this log should be attributed to.
109 * @param [in] Format The format string.
110 * @param ... Variable arguments providing additional information.
112 * @return Success: TRUE Failure: FALSE.
114 BOOL WINAPIV
ShimDbgPrint(SHIM_LOG_LEVEL Level
, PCSTR FunctionName
, PCSTR Format
, ...)
118 char* Current
= Buffer
;
119 const char* LevelStr
;
120 size_t Length
= sizeof(Buffer
);
122 if (g_ShimDebugLevel
== 0xffffffff)
123 ApphelppInitDebugLevel();
125 if (Level
> g_ShimDebugLevel
)
132 Level
= DPFLTR_MASK
| (1 << DPFLTR_ERROR_LEVEL
);
136 Level
= DPFLTR_MASK
| (1 << DPFLTR_WARNING_LEVEL
);
140 Level
= DPFLTR_MASK
| (1 << DPFLTR_INFO_LEVEL
);
144 Level
= DPFLTR_MASK
| (1 << DPFLTR_INFO_LEVEL
);
147 StringCchPrintfExA(Current
, Length
, &Current
, &Length
, STRSAFE_NULL_ON_FAILURE
, "[%s][%-20s] ", LevelStr
, FunctionName
);
148 va_start(ArgList
, Format
);
149 StringCchVPrintfExA(Current
, Length
, &Current
, &Length
, STRSAFE_NULL_ON_FAILURE
, Format
, ArgList
);
151 #if defined(APPCOMPAT_USE_DBGPRINTEX) && APPCOMPAT_USE_DBGPRINTEX
152 return NT_SUCCESS(DbgPrintEx(DPFLTR_APPCOMPAT_ID
, Level
, "%s", Buffer
));
154 OutputDebugStringA(Buffer
);