Commit 0a98de97 authored by Clinton Stimpson's avatar Clinton Stimpson

KWSys: Port to use wide character Windows APIs throughout.

Change-Id: Icb357202c5591819b9f44b4e4f1376e7c4f7b7b3
parent 8abbad82
......@@ -132,18 +132,29 @@ ENDIF(KWSYS_STANDALONE OR CMake_SOURCE_DIR)
# Enforce component dependencies.
IF(KWSYS_USE_SystemTools)
SET(KWSYS_USE_Directory 1)
SET(KWSYS_USE_FStream 1)
SET(KWSYS_USE_Encoding 1)
ENDIF(KWSYS_USE_SystemTools)
IF(KWSYS_USE_Glob)
SET(KWSYS_USE_Directory 1)
SET(KWSYS_USE_SystemTools 1)
SET(KWSYS_USE_RegularExpression 1)
SET(KWSYS_USE_FStream 1)
SET(KWSYS_USE_Encoding 1)
ENDIF(KWSYS_USE_Glob)
IF(KWSYS_USE_Process)
SET(KWSYS_USE_System 1)
SET(KWSYS_USE_Encoding 1)
ENDIF(KWSYS_USE_Process)
IF(KWSYS_USE_SystemInformation)
SET(KWSYS_USE_Process 1)
ENDIF(KWSYS_USE_SystemInformation)
IF(KWSYS_USE_System)
SET(KWSYS_USE_Encoding 1)
ENDIF(KWSYS_USE_System)
IF(KWSYS_USE_Directory)
SET(KWSYS_USE_Encoding 1)
ENDIF(KWSYS_USE_Directory)
IF(KWSYS_USE_FStream)
SET(KWSYS_USE_Encoding 1)
ENDIF(KWSYS_USE_FStream)
......
......@@ -14,6 +14,8 @@
#include KWSYS_HEADER(Configure.hxx)
#include KWSYS_HEADER(Encoding.hxx)
#include KWSYS_HEADER(stl/string)
#include KWSYS_HEADER(stl/vector)
......@@ -22,6 +24,7 @@
#if 0
# include "Directory.hxx.in"
# include "Configure.hxx.in"
# include "Encoding.hxx.in"
# include "kwsys_stl.hxx.in"
# include "kwsys_stl_string.hxx.in"
# include "kwsys_stl_vector.hxx.in"
......@@ -120,10 +123,10 @@ bool Directory::Load(const char* name)
buf = new char[n + 2 + 1];
sprintf(buf, "%s/*", name);
}
struct _finddata_t data; // data of current file
struct _wfinddata_t data; // data of current file
// Now put them into the file array
srchHandle = _findfirst(buf, &data);
srchHandle = _wfindfirst((wchar_t*)Encoding::ToWide(buf).c_str(), &data);
delete [] buf;
if ( srchHandle == -1 )
......@@ -134,9 +137,9 @@ bool Directory::Load(const char* name)
// Loop through names
do
{
this->Internal->Files.push_back(data.name);
this->Internal->Files.push_back(Encoding::ToNarrow(data.name));
}
while ( _findnext(srchHandle, &data) != -1 );
while ( _wfindnext(srchHandle, &data) != -1 );
this->Internal->Path = name;
return _findclose(srchHandle) != -1;
}
......@@ -160,10 +163,10 @@ unsigned long Directory::GetNumberOfFilesInDirectory(const char* name)
buf = new char[n + 2 + 1];
sprintf(buf, "%s/*", name);
}
struct _finddata_t data; // data of current file
struct _wfinddata_t data; // data of current file
// Now put them into the file array
srchHandle = _findfirst(buf, &data);
srchHandle = _wfindfirst((wchar_t*)Encoding::ToWide(buf).c_str(), &data);
delete [] buf;
if ( srchHandle == -1 )
......@@ -177,7 +180,7 @@ unsigned long Directory::GetNumberOfFilesInDirectory(const char* name)
{
count++;
}
while ( _findnext(srchHandle, &data) != -1 );
while ( _wfindnext(srchHandle, &data) != -1 );
_findclose(srchHandle);
return count;
}
......
......@@ -186,13 +186,12 @@ namespace KWSYS_NAMESPACE
DynamicLoader::LibraryHandle DynamicLoader::OpenLibrary(const char* libname)
{
DynamicLoader::LibraryHandle lh;
#ifdef UNICODE
wchar_t libn[MB_CUR_MAX];
mbstowcs(libn, libname, MB_CUR_MAX);
lh = LoadLibrary(libn);
#else
lh = LoadLibrary(libname);
#endif
int length = MultiByteToWideChar(CP_UTF8, 0, libname, -1, NULL, 0);
wchar_t* wchars = new wchar_t[length+1];
wchars[0] = '\0';
MultiByteToWideChar(CP_UTF8, 0, libname, -1, wchars, length);
lh = LoadLibraryW(wchars);
delete [] wchars;
return lh;
}
......@@ -238,13 +237,7 @@ DynamicLoader::SymbolPointer DynamicLoader::GetSymbolAddress(
#else
const char *rsym = sym;
#endif
#ifdef UNICODE
wchar_t wsym[MB_CUR_MAX];
mbstowcs(wsym, rsym, MB_CUR_MAX);
result = GetProcAddress(lib, wsym);
#else
result = (void*)GetProcAddress(lib, rsym);
#endif
#if defined(__BORLANDC__) || defined(__WATCOMC__)
delete[] rsym;
#endif
......
......@@ -12,12 +12,14 @@
#include "kwsysPrivate.h"
#include KWSYS_HEADER(Process.h)
#include KWSYS_HEADER(System.h)
#include KWSYS_HEADER(Encoding.h)
/* Work-around CMake dependency scanning limitation. This must
duplicate the above list of headers. */
#if 0
# include "Process.h.in"
# include "System.h.in"
# include "Encoding_c.h.in"
#endif
/*
......@@ -88,9 +90,10 @@ typedef LARGE_INTEGER kwsysProcessTime;
typedef struct kwsysProcessCreateInformation_s
{
/* Windows child startup control data. */
STARTUPINFO StartupInfo;
STARTUPINFOW StartupInfo;
} kwsysProcessCreateInformation;
/*--------------------------------------------------------------------------*/
typedef struct kwsysProcessPipeData_s kwsysProcessPipeData;
static DWORD WINAPI kwsysProcessPipeThreadRead(LPVOID ptd);
......@@ -197,14 +200,14 @@ struct kwsysProcess_s
int State;
/* The command lines to execute. */
char** Commands;
wchar_t** Commands;
int NumberOfCommands;
/* The exit code of each command. */
DWORD* CommandExitCodes;
/* The working directory for the child process. */
char* WorkingDirectory;
wchar_t* WorkingDirectory;
/* Whether to create the child as a detached process. */
int OptionDetach;
......@@ -299,7 +302,7 @@ struct kwsysProcess_s
/* Real working directory of our own process. */
DWORD RealWorkingDirectoryLength;
char* RealWorkingDirectory;
wchar_t* RealWorkingDirectory;
};
/*--------------------------------------------------------------------------*/
......@@ -546,7 +549,7 @@ int kwsysProcess_SetCommand(kwsysProcess* cp, char const* const* command)
int kwsysProcess_AddCommand(kwsysProcess* cp, char const* const* command)
{
int newNumberOfCommands;
char** newCommands;
wchar_t** newCommands;
/* Make sure we have a command to add. */
if(!cp || !command || !*command)
......@@ -554,9 +557,10 @@ int kwsysProcess_AddCommand(kwsysProcess* cp, char const* const* command)
return 0;
}
/* Allocate a new array for command pointers. */
newNumberOfCommands = cp->NumberOfCommands + 1;
if(!(newCommands = (char**)malloc(sizeof(char*) * newNumberOfCommands)))
if(!(newCommands = (wchar_t**)malloc(sizeof(wchar_t*) * newNumberOfCommands)))
{
/* Out of memory. */
return 0;
......@@ -585,8 +589,8 @@ int kwsysProcess_AddCommand(kwsysProcess* cp, char const* const* command)
/* Allocate enough space for the command. We do not need an extra
byte for the terminating null because we allocated a space for
the first argument that we will not use. */
newCommands[cp->NumberOfCommands] = (char*)malloc(length);
if(!newCommands[cp->NumberOfCommands])
char* new_cmd = malloc(length);
if(!new_cmd)
{
/* Out of memory. */
free(newCommands);
......@@ -595,9 +599,13 @@ int kwsysProcess_AddCommand(kwsysProcess* cp, char const* const* command)
/* Construct the command line in the allocated buffer. */
kwsysProcessComputeCommandLine(cp, command,
newCommands[cp->NumberOfCommands]);
new_cmd);
newCommands[cp->NumberOfCommands] = kwsysEncoding_DupToWide(new_cmd);
free(new_cmd);
}
/* Save the new array of commands. */
free(cp->Commands);
cp->Commands = newCommands;
......@@ -633,22 +641,26 @@ int kwsysProcess_SetWorkingDirectory(kwsysProcess* cp, const char* dir)
}
if(dir && dir[0])
{
wchar_t* wdir = kwsysEncoding_DupToWide(dir);
/* We must convert the working directory to a full path. */
DWORD length = GetFullPathName(dir, 0, 0, 0);
DWORD length = GetFullPathNameW(wdir, 0, 0, 0);
if(length > 0)
{
cp->WorkingDirectory = (char*)malloc(length);
if(!cp->WorkingDirectory)
wchar_t* work_dir = malloc(length*sizeof(wchar_t));
if(!work_dir)
{
free(wdir);
return 0;
}
if(!GetFullPathName(dir, length, cp->WorkingDirectory, 0))
if(!GetFullPathNameW(wdir, length, work_dir, 0))
{
free(cp->WorkingDirectory);
cp->WorkingDirectory = 0;
free(work_dir);
free(wdir);
return 0;
}
cp->WorkingDirectory = work_dir;
}
free(wdir);
}
return 1;
}
......@@ -879,13 +891,13 @@ void kwsysProcess_Execute(kwsysProcess* cp)
to make pipe file paths evaluate correctly. */
if(cp->WorkingDirectory)
{
if(!GetCurrentDirectory(cp->RealWorkingDirectoryLength,
if(!GetCurrentDirectoryW(cp->RealWorkingDirectoryLength,
cp->RealWorkingDirectory))
{
kwsysProcessCleanup(cp, 1);
return;
}
SetCurrentDirectory(cp->WorkingDirectory);
SetCurrentDirectoryW(cp->WorkingDirectory);
}
/* Initialize startup info data. */
......@@ -1003,7 +1015,7 @@ void kwsysProcess_Execute(kwsysProcess* cp)
/* Restore the working directory. */
if(cp->RealWorkingDirectory)
{
SetCurrentDirectory(cp->RealWorkingDirectory);
SetCurrentDirectoryW(cp->RealWorkingDirectory);
free(cp->RealWorkingDirectory);
cp->RealWorkingDirectory = 0;
}
......@@ -1507,10 +1519,10 @@ int kwsysProcessInitialize(kwsysProcess* cp)
/* Allocate space to save the real working directory of this process. */
if(cp->WorkingDirectory)
{
cp->RealWorkingDirectoryLength = GetCurrentDirectory(0, 0);
cp->RealWorkingDirectoryLength = GetCurrentDirectoryW(0, 0);
if(cp->RealWorkingDirectoryLength > 0)
{
cp->RealWorkingDirectory = (char*)malloc(cp->RealWorkingDirectoryLength);
cp->RealWorkingDirectory = malloc(cp->RealWorkingDirectoryLength * sizeof(wchar_t));
if(!cp->RealWorkingDirectory)
{
return 0;
......@@ -1547,9 +1559,11 @@ int kwsysProcessCreate(kwsysProcess* cp, int index,
else if(cp->PipeFileSTDIN)
{
/* Create a handle to read a file for stdin. */
HANDLE fin = CreateFile(cp->PipeFileSTDIN, GENERIC_READ|GENERIC_WRITE,
wchar_t* wstdin = kwsysEncoding_DupToWide(cp->PipeFileSTDIN);
HANDLE fin = CreateFileW(wstdin, GENERIC_READ|GENERIC_WRITE,
FILE_SHARE_READ|FILE_SHARE_WRITE,
0, OPEN_EXISTING, 0, 0);
free(wstdin);
if(fin == INVALID_HANDLE_VALUE)
{
return 0;
......@@ -1655,7 +1669,7 @@ int kwsysProcessCreate(kwsysProcess* cp, int index,
/* Create the child in a suspended state so we can wait until all
children have been created before running any one. */
if(!CreateProcess(0, cp->Commands[index], 0, 0, TRUE, CREATE_SUSPENDED, 0,
if(!CreateProcessW(0, cp->Commands[index], 0, 0, TRUE, CREATE_SUSPENDED, 0,
0, &si->StartupInfo, &cp->ProcessInformation[index]))
{
return 0;
......@@ -1729,6 +1743,7 @@ void kwsysProcessDestroy(kwsysProcess* cp, int event)
int kwsysProcessSetupOutputPipeFile(PHANDLE phandle, const char* name)
{
HANDLE fout;
wchar_t* wname;
if(!name)
{
return 1;
......@@ -1738,8 +1753,10 @@ int kwsysProcessSetupOutputPipeFile(PHANDLE phandle, const char* name)
kwsysProcessCleanupHandle(phandle);
/* Create a handle to write a file for the pipe. */
fout = CreateFile(name, GENERIC_WRITE, FILE_SHARE_READ, 0,
wname = kwsysEncoding_DupToWide(name);
fout = CreateFileW(wname, GENERIC_WRITE, FILE_SHARE_READ, 0,
CREATE_ALWAYS, 0, 0);
free(wname);
if(fout == INVALID_HANDLE_VALUE)
{
return 0;
......@@ -1883,10 +1900,13 @@ void kwsysProcessCleanup(kwsysProcess* cp, int error)
{
/* Format the error message. */
DWORD original = GetLastError();
DWORD length = FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM |
wchar_t err_msg[KWSYSPE_PIPE_BUFFER_SIZE];
DWORD length = FormatMessageW(FORMAT_MESSAGE_FROM_SYSTEM |
FORMAT_MESSAGE_IGNORE_INSERTS, 0, original,
MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
cp->ErrorMessage, KWSYSPE_PIPE_BUFFER_SIZE, 0);
err_msg, KWSYSPE_PIPE_BUFFER_SIZE, 0);
WideCharToMultiByte(CP_UTF8, 0, err_msg, -1, cp->ErrorMessage,
KWSYSPE_PIPE_BUFFER_SIZE, NULL, NULL);
if(length < 1)
{
/* FormatMessage failed. Use a default message. */
......@@ -1924,7 +1944,7 @@ void kwsysProcessCleanup(kwsysProcess* cp, int error)
/* Restore the working directory. */
if(cp->RealWorkingDirectory)
{
SetCurrentDirectory(cp->RealWorkingDirectory);
SetCurrentDirectoryW(cp->RealWorkingDirectory);
}
}
......@@ -2222,7 +2242,7 @@ static void kwsysProcessSetExitException(kwsysProcess* cp, int code)
case STATUS_NO_MEMORY:
default:
cp->ExitException = kwsysProcess_Exception_Other;
sprintf(cp->ExitExceptionString, "Exit code 0x%x\n", code);
_snprintf(cp->ExitExceptionString, KWSYSPE_PIPE_BUFFER_SIZE, "Exit code 0x%x\n", code);
break;
}
}
......@@ -2430,7 +2450,7 @@ static int kwsysProcess_List__New_NT4(kwsysProcess_List* self)
loaded in this program. This does not actually increment the
reference count to the module so we do not need to close the
handle. */
HMODULE hNT = GetModuleHandle("ntdll.dll");
HMODULE hNT = GetModuleHandleW(L"ntdll.dll");
if(hNT)
{
/* Get pointers to the needed API functions. */
......@@ -2534,7 +2554,7 @@ static int kwsysProcess_List__New_Snapshot(kwsysProcess_List* self)
loaded in this program. This does not actually increment the
reference count to the module so we do not need to close the
handle. */
HMODULE hKernel = GetModuleHandle("kernel32.dll");
HMODULE hKernel = GetModuleHandleW(L"kernel32.dll");
if(hKernel)
{
self->P_CreateToolhelp32Snapshot =
......
......@@ -2454,8 +2454,8 @@ bool SystemInformationImplementation::RetrieveCPUClockSpeed()
if (!retrieved)
{
HKEY hKey = NULL;
LONG err = RegOpenKeyEx(HKEY_LOCAL_MACHINE,
"HARDWARE\\DESCRIPTION\\System\\CentralProcessor\\0", 0,
LONG err = RegOpenKeyExW(HKEY_LOCAL_MACHINE,
L"HARDWARE\\DESCRIPTION\\System\\CentralProcessor\\0", 0,
KEY_READ, &hKey);
if (ERROR_SUCCESS == err)
......@@ -2464,7 +2464,7 @@ bool SystemInformationImplementation::RetrieveCPUClockSpeed()
DWORD data = 0;
DWORD dwSize = sizeof(DWORD);
err = RegQueryValueEx(hKey, "~MHz", 0,
err = RegQueryValueExW(hKey, L"~MHz", 0,
&dwType, (LPBYTE) &data, &dwSize);
if (ERROR_SUCCESS == err)
......@@ -5017,19 +5017,19 @@ bool SystemInformationImplementation::QueryOSInformation()
this->OSName = "Windows";
OSVERSIONINFOEX osvi;
OSVERSIONINFOEXW osvi;
BOOL bIsWindows64Bit;
BOOL bOsVersionInfoEx;
char operatingSystem[256];
// Try calling GetVersionEx using the OSVERSIONINFOEX structure.
ZeroMemory (&osvi, sizeof (OSVERSIONINFOEX));
osvi.dwOSVersionInfoSize = sizeof (OSVERSIONINFOEX);
bOsVersionInfoEx = GetVersionEx ((OSVERSIONINFO *) &osvi);
ZeroMemory (&osvi, sizeof (OSVERSIONINFOEXW));
osvi.dwOSVersionInfoSize = sizeof (OSVERSIONINFOEXW);
bOsVersionInfoEx = GetVersionExW ((OSVERSIONINFOW*)&osvi);
if (!bOsVersionInfoEx)
{
osvi.dwOSVersionInfoSize = sizeof (OSVERSIONINFO);
if (!GetVersionEx ((OSVERSIONINFO *) &osvi))
osvi.dwOSVersionInfoSize = sizeof (OSVERSIONINFOW);
if (!GetVersionExW((OSVERSIONINFOW*)&osvi))
{
return false;
}
......@@ -5115,19 +5115,19 @@ bool SystemInformationImplementation::QueryOSInformation()
#endif // VER_NT_WORKSTATION
{
HKEY hKey;
char szProductType[80];
wchar_t szProductType[80];
DWORD dwBufLen;
// Query the registry to retrieve information.
RegOpenKeyEx (HKEY_LOCAL_MACHINE, "SYSTEM\\CurrentControlSet\\Control\\ProductOptions", 0, KEY_QUERY_VALUE, &hKey);
RegQueryValueEx (hKey, "ProductType", NULL, NULL, (LPBYTE) szProductType, &dwBufLen);
RegOpenKeyExW(HKEY_LOCAL_MACHINE, L"SYSTEM\\CurrentControlSet\\Control\\ProductOptions", 0, KEY_QUERY_VALUE, &hKey);
RegQueryValueExW(hKey, L"ProductType", NULL, NULL, (LPBYTE) szProductType, &dwBufLen);
RegCloseKey (hKey);
if (lstrcmpi ("WINNT", szProductType) == 0)
if (lstrcmpiW(L"WINNT", szProductType) == 0)
{
this->OSRelease += " Professional";
}
if (lstrcmpi ("LANMANNT", szProductType) == 0)
if (lstrcmpiW(L"LANMANNT", szProductType) == 0)
{
// Decide between Windows 2000 Advanced Server and Windows .NET Enterprise Server.
if (osvi.dwMajorVersion == 5 && osvi.dwMinorVersion == 1)
......@@ -5139,7 +5139,7 @@ bool SystemInformationImplementation::QueryOSInformation()
this->OSRelease += " Server";
}
}
if (lstrcmpi ("SERVERNT", szProductType) == 0)
if (lstrcmpiW(L"SERVERNT", szProductType) == 0)
{
// Decide between Windows 2000 Advanced Server and Windows .NET Enterprise Server.
if (osvi.dwMajorVersion == 5 && osvi.dwMinorVersion == 1)
......@@ -5172,7 +5172,7 @@ bool SystemInformationImplementation::QueryOSInformation()
LPFNPROC DLLProc;
// Load the Kernel32 DLL.
hKernelDLL = LoadLibrary ("kernel32");
hKernelDLL = LoadLibraryW(L"kernel32");
if (hKernelDLL != NULL) {
// Only XP and .NET Server support IsWOW64Process so... Load dynamically!
DLLProc = (LPFNPROC) GetProcAddress (hKernelDLL, "IsWow64Process");
......
This diff is collapsed.
......@@ -24,6 +24,8 @@
// Required for va_list
#include <stdarg.h>
// Required for FILE*
#include <stdio.h>
#if @KWSYS_NAMESPACE@_STL_HAVE_STD && !defined(va_list)
// Some compilers move va_list into the std namespace and there is no way to
// tell that this has been done. Playing with things being included before or
......@@ -492,6 +494,11 @@ public:
* -----------------------------------------------------------------
*/
/**
* Open a file considering unicode.
*/
static FILE* Fopen(const char* file, const char* mode);
/**
* Make a new directory if it is not there. This function
* can make a full path even if none of the directories existed
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment