?? newapis_fixed.h
字號(hào):
// == Following lines added by Erik:
#define COMPILE_NEWAPIS_STUBS
#define WANT_GETDISKFREESPACEEX_WRAPPER
#define WANT_GETLONGPATHNAME_WRAPPER
//#define WANT_GETFILEATTRIBUTESEX_WRAPPER
//#define WANT_ISDEBUGGERPRESENT_WRAPPER
// == End of lines added by Erik.
/*
Erik:
There were some errors in the original NewAPIs.h file.
The changes I made are below.
(1)
In this file I replaced all occurrences of:
SetLastError(ERROR_something);
to:
SetLastError((unsigned long)ERROR_something);
(2)
Near line 340 (this file) I changed this:
BOOL (CALLBACK *RealGetLongPathName)(LPCTSTR, LPTSTR, DWORD);
to:
DWORD (CALLBACK *RealGetLongPathName)(LPCTSTR, LPTSTR, DWORD);
*/
/*
* Copyright (c) 1997-1999, Microsoft Corporation
*
* Wrapper module that "stubs" APIs that were not implemented
* on Windows 95 or Windows NT versions less than 4.0 SP 3.
*
* By using this header, your code will run on older platforms.
*
* To enable a particular wrapper, define the corresponding symbol.
*
* Function Symbol
*
* GetDiskFreeSpaceEx WANT_GETDISKFREESPACEEX_WRAPPER
* GetLongPathName WANT_GETLONGPATHNAME_WRAPPER
* GetFileAttributesEx WANT_GETFILEATTRIBUTESEX_WRAPPER
* IsDebuggerPresent WANT_ISDEBUGGERPRESENT_WRAPPER
*
* Exactly one source file must include the line
*
* #define COMPILE_NEWAPIS_STUBS
*
* before including this file.
*
*/
#ifdef __cplusplus
extern "C" { /* Assume C declarations for C++ */
#endif /* __cplusplus */
/*****************************************************************************
*
* GetDiskFreeSpaceEx
*
*****************************************************************************/
#ifdef WANT_GETDISKFREESPACEEX_WRAPPER
#undef GetDiskFreeSpaceEx
#define GetDiskFreeSpaceEx _GetDiskFreeSpaceEx
extern BOOL (CALLBACK *GetDiskFreeSpaceEx)
(LPCTSTR, PULARGE_INTEGER, PULARGE_INTEGER, PULARGE_INTEGER);
/*
* Exactly one file should define this symbol.
*/
#ifdef COMPILE_NEWAPIS_STUBS
/*
* The version to use if we are forced to emulate.
*/
static BOOL WINAPI
Emulate_GetDiskFreeSpaceEx(LPCTSTR ptszRoot, PULARGE_INTEGER pliQuota,
PULARGE_INTEGER pliTotal, PULARGE_INTEGER pliFree)
{
DWORD dwSecPerClus, dwBytesPerSec, dwFreeClus, dwTotalClus;
BOOL fRc;
fRc = GetDiskFreeSpace(ptszRoot, &dwSecPerClus, &dwBytesPerSec,
&dwFreeClus, &dwTotalClus);
if (fRc) {
DWORD dwBytesPerClus = dwSecPerClus * dwBytesPerSec;
/*
* Curiously, of all the output parameters, only pliFree is
* allowed to be NULL.
*/
*(__int64 *)pliQuota = Int32x32To64(dwBytesPerClus, dwFreeClus);
if (pliFree) {
*pliFree = *pliQuota;
}
*(__int64 *)pliTotal = Int32x32To64(dwBytesPerClus, dwTotalClus);
}
return fRc;
}
/*
* The stub that probes to decide which version to use.
*/
static BOOL WINAPI
Probe_GetDiskFreeSpaceEx(LPCTSTR ptszRoot, PULARGE_INTEGER pliQuota,
PULARGE_INTEGER pliTotal, PULARGE_INTEGER pliFree)
{
HINSTANCE hinst;
FARPROC fp;
BOOL fRc;
BOOL (CALLBACK *RealGetDiskFreeSpaceEx)
(LPCTSTR, PULARGE_INTEGER, PULARGE_INTEGER, PULARGE_INTEGER);
hinst = GetModuleHandle(TEXT("KERNEL32"));
#ifdef UNICODE
fp = GetProcAddress(hinst, "GetDiskFreeSpaceExW");
#else
fp = GetProcAddress(hinst, "GetDiskFreeSpaceExA");
#endif
if (fp) {
*(FARPROC *)&RealGetDiskFreeSpaceEx = fp;
fRc = RealGetDiskFreeSpaceEx(ptszRoot, pliQuota, pliTotal, pliFree);
if (fRc || GetLastError() != ERROR_CALL_NOT_IMPLEMENTED) {
GetDiskFreeSpaceEx = RealGetDiskFreeSpaceEx;
} else {
GetDiskFreeSpaceEx = Emulate_GetDiskFreeSpaceEx;
fRc = GetDiskFreeSpaceEx(ptszRoot, pliQuota, pliTotal, pliFree);
}
} else {
GetDiskFreeSpaceEx = Emulate_GetDiskFreeSpaceEx;
fRc = GetDiskFreeSpaceEx(ptszRoot, pliQuota, pliTotal, pliFree);
}
return fRc;
}
BOOL (CALLBACK *GetDiskFreeSpaceEx)
(LPCTSTR, PULARGE_INTEGER, PULARGE_INTEGER, PULARGE_INTEGER) =
Probe_GetDiskFreeSpaceEx;
#endif /* COMPILE_NEWAPIS_STUBS */
#endif /* WANT_GETDISKFREESPACEEX_WRAPPER */
/*****************************************************************************
*
* GetLongPathName
*
*****************************************************************************/
#ifdef WANT_GETLONGPATHNAME_WRAPPER
#include <shlobj.h>
#undef GetLongPathName
#define GetLongPathName _GetLongPathName
extern DWORD (CALLBACK *GetLongPathName)(LPCTSTR, LPTSTR, DWORD);
/*
* Exactly one file should define this symbol.
*/
#ifdef COMPILE_NEWAPIS_STUBS
/*
* The version to use if we are forced to emulate.
*/
static DWORD WINAPI
Emulate_GetLongPathName(LPCTSTR ptszShort, LPTSTR ptszLong, DWORD ctchBuf)
{
LPSHELLFOLDER psfDesk;
HRESULT hr;
LPITEMIDLIST pidl;
TCHAR tsz[MAX_PATH]; /* Scratch TCHAR buffer */
DWORD dwRc;
LPMALLOC pMalloc;
/*
* The file had better exist. GetFileAttributes() will
* not only tell us, but it'll even call SetLastError()
* for us.
*/
if (GetFileAttributes(ptszShort) == 0xFFFFFFFF) {
return 0;
}
/*
* First convert from relative path to absolute path.
* This uses the scratch TCHAR buffer.
*/
dwRc = GetFullPathName(ptszShort, MAX_PATH, tsz, NULL);
if (dwRc == 0) {
/*
* Failed; GFPN already did SetLastError().
*/
} else if (dwRc >= MAX_PATH) {
/*
* Resulting path would be too long.
*/
SetLastError((unsigned long)ERROR_BUFFER_OVERFLOW); // (unsigned long) by Erik
dwRc = 0;
} else {
/*
* Just right.
*/
hr = SHGetDesktopFolder(&psfDesk);
if (SUCCEEDED(hr)) {
ULONG cwchEaten;
#ifdef UNICODE
#ifdef __cplusplus
hr = psfDesk->ParseDisplayName(NULL, NULL, tsz,
&cwchEaten, &pidl, NULL);
#else
hr = psfDesk->lpVtbl->ParseDisplayName(psfDesk, NULL, NULL, tsz,
&cwchEaten, &pidl, NULL);
#endif
#else
WCHAR wsz[MAX_PATH]; /* Scratch WCHAR buffer */
/*
* ParseDisplayName requires UNICODE, so we use
* the scratch WCHAR buffer during the conversion.
*/
dwRc = MultiByteToWideChar(
AreFileApisANSI() ? CP_ACP : CP_OEMCP,
0, tsz, -1, wsz, MAX_PATH);
if (dwRc == 0) {
/*
* Couldn't convert to UNICODE. MB2WC uses
* ERROR_INSUFFICIENT_BUFFER, which we convert
* to ERROR_BUFFER_OVERFLOW. Any other error
* we leave alone.
*/
if (GetLastError() == ERROR_INSUFFICIENT_BUFFER) {
SetLastError((unsigned long)ERROR_BUFFER_OVERFLOW);
}
dwRc = 0;
} else {
#ifdef __cplusplus
hr = psfDesk->ParseDisplayName(NULL, NULL, wsz,
&cwchEaten, &pidl, NULL);
#else
hr = psfDesk->lpVtbl->ParseDisplayName(psfDesk, NULL, NULL,
wsz, &cwchEaten, &pidl, NULL);
#endif
#endif
if (FAILED(hr)) {
/*
* Weird. Convert the result back to a Win32
* error code if we can. Otherwise, use the
* generic "duh" error code ERROR_INVALID_DATA.
*/
if (HRESULT_FACILITY(hr) == FACILITY_WIN32) {
SetLastError((unsigned long)HRESULT_CODE(hr));
} else {
SetLastError((unsigned long)ERROR_INVALID_DATA);
}
dwRc = 0;
} else {
/*
* Convert the pidl back to a filename in the
* TCHAR scratch buffer.
*/
dwRc = SHGetPathFromIDList(pidl, tsz);
if (dwRc == 0 && tsz[0]) {
/*
* Bizarre failure.
*/
SetLastError((unsigned long)ERROR_INVALID_DATA);
} else {
/*
* Copy the result back to the user's buffer.
*/
dwRc = lstrlen(tsz);
if (dwRc + 1 > ctchBuf) {
/*
* On buffer overflow, return necessary
* size including terminating null (+1).
?? 快捷鍵說明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號(hào)
Ctrl + =
減小字號(hào)
Ctrl + -