Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Win64 unicode #332

Merged
merged 36 commits into from
Jan 2, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
36 commits
Select commit Hold shift + click to select a range
ea3d51e
Handle both an ASCII (UTF8) and a WIDE (UTF16) version of image/vm na…
nicolas-cellier-aka-nice Dec 29, 2018
8bdd0b6
DropPlugin: modernize OpenFile/_lwrite/_lclose API
nicolas-cellier-aka-nice Dec 30, 2018
cb32e41
Drop plugin: let tempPathName be Wide
nicolas-cellier-aka-nice Dec 30, 2018
85e0883
Fix 2 potential buffer overrun in sqWin32Service.c
nicolas-cellier-aka-nice Dec 30, 2018
f689145
Setting fp flags _MCW_PC and _MCW_IC is not supported on ARM nor X64
nicolas-cellier-aka-nice Dec 29, 2018
49eff31
The pageSize and pageMask are too short on WIN64
nicolas-cellier-aka-nice Dec 30, 2018
627bc5e
Use the eventually true UNICODE imageNameT if -DUNICODE
nicolas-cellier-aka-nice Dec 30, 2018
98fc85d
interpret pluginName as UTF8 rather than pure ASCII
nicolas-cellier-aka-nice Dec 30, 2018
4f6f191
refactor sqMessageBox to void using toUnicode
nicolas-cellier-aka-nice Dec 30, 2018
545ec0a
Discard now unused toUnicode fromUnicode fromSqueak fromSqueak2 lstrrchr
nicolas-cellier-aka-nice Dec 30, 2018
2024d43
#if 0 ? YAGNI ! we now use builtin _WIN32 _WIN64 anyway
nicolas-cellier-aka-nice Dec 30, 2018
e1e83f7
which SetUpPreferences()? There is no SetUpPreferences()!
nicolas-cellier-aka-nice Dec 30, 2018
8638522
RegisterWindowMessage takes a TCHAR *
nicolas-cellier-aka-nice Dec 30, 2018
1893512
Platform specific knowledge: WIN32_FILE and STD_FILE are mutually exc…
nicolas-cellier-aka-nice Dec 30, 2018
f250415
We can't compare a TCHAR*windowClassName with a char*buf
nicolas-cellier-aka-nice Dec 30, 2018
84a8d17
Tu quoque NewspeakVM, frustra TEXT macro...
nicolas-cellier-aka-nice Dec 31, 2018
7d3264e
gai_strerror returns a TCHAR*, we cannot simply fprintf it...
nicolas-cellier-aka-nice Dec 31, 2018
6ff9625
Let lookup account for NULL terminating a WCHAR*
nicolas-cellier-aka-nice Dec 31, 2018
32840ac
Revert to ASCII only version of DnsInfo
nicolas-cellier-aka-nice Dec 31, 2018
475d84c
iconPath is char*, LoadImage expects a TCHAR*
nicolas-cellier-aka-nice Dec 31, 2018
ef245b6
And account for the fact that iconPath is not NULL-TERMINATED!
nicolas-cellier-aka-nice Dec 31, 2018
07ff6a6
DPRINTF must take a TCHAR*fmt because wvsprintf does!
nicolas-cellier-aka-nice Dec 31, 2018
dfe4d09
NOTIFYICONDATA.szTip maybe a WCHAR* if -DUNICODE
nicolas-cellier-aka-nice Dec 31, 2018
db33158
_DISPLAY_DEVICE.DeviceString may be a WCHAR* if -DUNICODE, we cannot …
nicolas-cellier-aka-nice Dec 31, 2018
46bd992
VM_VERSION_TEXT is a TCHAR*, we cannot simply fprintf
nicolas-cellier-aka-nice Dec 31, 2018
c5f207c
iniName, manufacturer and model may be WCHAR* if -DUNICODE
nicolas-cellier-aka-nice Dec 31, 2018
d9b3927
Information queried in Registry can be WideChar if -DUNICODE
nicolas-cellier-aka-nice Dec 31, 2018
8b14fbf
Make stderrName and stdoutName be WCHAR*
nicolas-cellier-aka-nice Dec 31, 2018
643a5e3
Retract support for Windows95 (no you don't dream it's nearly 2019!)
nicolas-cellier-aka-nice Dec 31, 2018
1f61637
Handle UTF16 logName and serviceName
nicolas-cellier-aka-nice Dec 31, 2018
e5cd4fb
Fix 3 potential buffer overrun
nicolas-cellier-aka-nice Jan 1, 2019
4ded318
Fix my own confusion about wcsncat
nicolas-cellier-aka-nice Jan 1, 2019
af19ed7
Fix: Shlemiel the painter needs to paint strncat too
nicolas-cellier-aka-nice Jan 1, 2019
bf3840c
Fix a TCHAR*crashInfo trying to mix a char*msg
nicolas-cellier-aka-nice Jan 1, 2019
252e2a8
Fix another potential Buffer overrun in sqWin32MIDI.c
nicolas-cellier-aka-nice Jan 2, 2019
3e51616
fixup: skip only 18 WCHAR if keyName begins with \\registry\\machine
nicolas-cellier-aka-nice Jan 2, 2019
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
78 changes: 47 additions & 31 deletions platforms/win32/plugins/DropPlugin/sqWin32Drop.c
Original file line number Diff line number Diff line change
Expand Up @@ -212,19 +212,26 @@ HANDLE DibFromBitmap (
}

BOOL WriteDIB (
LPSTR szFile,
LPCWSTR szFile,
HANDLE hdib)
{
BITMAPFILEHEADER hdr;
LPBITMAPINFOHEADER lpbi;
HFILE fh;
OFSTRUCT of;
HANDLE fh;
DWORD nbwritten;

if (!hdib)
return FALSE;

fh = OpenFile(szFile, &of, (UINT)OF_CREATE|OF_READWRITE);
if (fh == -1)
fh = CreateFileW(szFile,
(GENERIC_READ | GENERIC_WRITE) ,
FILE_SHARE_READ ,
NULL, /* No security descriptor */
OPEN_ALWAYS ,
FILE_ATTRIBUTE_NORMAL,
NULL /* No template */);

if (fh == INVALID_HANDLE_VALUE)
return FALSE;

lpbi = (VOID FAR *)GlobalLock (hdib);
Expand All @@ -240,16 +247,16 @@ BOOL WriteDIB (
/* Write the file header */

/* write bfType*/
_lwrite(fh, (LPSTR)&hdr.bfType, (UINT)sizeof (WORD));
WriteFile(fh, (LPSTR)&hdr.bfType, (UINT)sizeof (WORD),&nbwritten,NULL);
/* now pass over extra word, and only write next 3 DWORDS!*/
_lwrite(fh, (LPSTR)&hdr.bfSize, sizeof(DWORD) * 3);
WriteFile(fh, (LPSTR)&hdr.bfSize, sizeof(DWORD) * 3, &nbwritten, NULL);

/* this struct already DWORD aligned!*/
/* Write the DIB header and the bits */
_lwrite (fh, (LPSTR)lpbi, GlobalSize (hdib));
WriteFile(fh, (LPSTR)lpbi, GlobalSize (hdib), &nbwritten, NULL);

GlobalUnlock (hdib);
_lclose(fh);
CloseHandle(fh);
return TRUE;
}

Expand Down Expand Up @@ -509,7 +516,7 @@ STDMETHODIMP DropTarget_Drop(DropTarget *dt,
DWORD i;

DPRINTF(("Success\n"));
numDropFiles = DragQueryFile(hDrop, -1, NULL, 0);
numDropFiles = DragQueryFileW(hDrop, -1, NULL, 0);
dropFiles = calloc(numDropFiles, sizeof(char*));
for(i=0; i<numDropFiles; i++) {
WCHAR *tmpPath;
Expand Down Expand Up @@ -546,17 +553,20 @@ STDMETHODIMP DropTarget_Drop(DropTarget *dt,

hRes = ido->lpVtbl->GetData(ido, &fmtetc, &medium);
if(hRes == S_OK) {
TCHAR tmpName[MAX_PATH+1];
WCHAR tmpNameW[MAX_PATH+1];
HANDLE hDib = medium.hGlobal;

DPRINTF(("Success\n"));

GetTempPath(MAX_PATH,tmpName);
strcat(tmpName,"$$squeak$$.bmp");
if(WriteDIB(tmpName, hDib)) {
numDropFiles = 1;
dropFiles = calloc(1, sizeof(void*));
dropFiles[0] = _strdup(tmpName);
GetTempPathW(MAX_PATH,tmpNameW);
wcscat(tmpNameW,L"$$squeak$$.bmp");
if(WriteDIB(tmpNameW, hDib)) {
char tmpNameA[MAX_PATH_UTF8 + 1];
if(WideCharToMultiByte(CP_UTF8, 0, tmpNameW, -1, tmpNameA, MAX_PATH_UTF8, NULL, NULL)) {
numDropFiles = 1;
dropFiles = calloc(1, sizeof(void*));
dropFiles[0] = _strdup(tmpNameA);
}
}
if(medium.pUnkForRelease == NULL) {
GlobalFree(hDib);
Expand All @@ -580,20 +590,23 @@ STDMETHODIMP DropTarget_Drop(DropTarget *dt,

hRes = ido->lpVtbl->GetData(ido, &fmtetc, &medium);
if(hRes == S_OK) {
TCHAR tmpName[MAX_PATH+1];
WCHAR tmpNameW[MAX_PATH+1];
HANDLE hDib;
HBITMAP hBM = medium.hBitmap;

DPRINTF(("Success\n"));

GetTempPath(MAX_PATH,tmpName);
strcat(tmpName,"$$squeak$$.bmp");
GetTempPathW(MAX_PATH,tmpNameW);
wcscat(tmpNameW,L"$$squeak$$.bmp");
hDib = DibFromBitmap(hBM, BI_RGB, 0, NULL);
if(hDib) {
if(WriteDIB(tmpName, hDib)) {
numDropFiles = 1;
dropFiles = calloc(1, sizeof(void*));
dropFiles[0] = _strdup(tmpName);
if(WriteDIB(tmpNameW, hDib)) {
char tmpNameA[MAX_PATH_UTF8 + 1];
if (WideCharToMultiByte(CP_UTF8, 0, tmpNameW, -1, tmpNameA, MAX_PATH_UTF8, NULL, NULL)) {
numDropFiles = 1;
dropFiles = calloc(1, sizeof(void*));
dropFiles[0] = _strdup(tmpNameA);
}
}
DeleteObject(hDib);
}
Expand All @@ -618,7 +631,7 @@ STDMETHODIMP DropTarget_Drop(DropTarget *dt,

hRes = ido->lpVtbl->GetData(ido, &fmtetc, &medium);
if(hRes == S_OK) {
TCHAR tmpName[MAX_PATH+1];
WCHAR tmpNameW[MAX_PATH+1];
HANDLE hMF = medium.hGlobal;
HANDLE hDib;
BITMAPINFO bmi;
Expand Down Expand Up @@ -661,12 +674,15 @@ STDMETHODIMP DropTarget_Drop(DropTarget *dt,
DeleteObject(hBM);
}

GetTempPath(MAX_PATH,tmpName);
strcat(tmpName,"$$squeak$$.bmp");
if(WriteDIB(tmpName, hDib)) {
numDropFiles = 1;
dropFiles = calloc(1, sizeof(void*));
dropFiles[0] = _strdup(tmpName);
GetTempPathW(MAX_PATH,tmpNameW);
wcscat(tmpNameW,L"$$squeak$$.bmp");
if(WriteDIB(tmpNameW, hDib)) {
char tmpNameA[MAX_PATH_UTF8 + 1];
if (WideCharToMultiByte(CP_UTF8, 0, tmpNameW, -1, tmpNameA, MAX_PATH_UTF8, NULL, NULL)) {
numDropFiles = 1;
dropFiles = calloc(1, sizeof(void*));
dropFiles[0] = _strdup(tmpNameA);
}
}
GlobalFree(hDib);
if(medium.pUnkForRelease == NULL) {
Expand Down
2 changes: 1 addition & 1 deletion platforms/win32/plugins/FilePlugin/sqWin32FilePrims.c
Original file line number Diff line number Diff line change
Expand Up @@ -517,7 +517,7 @@ size_t sqImageFileRead(void *ptr, size_t sz, size_t count, sqImageFile h)
ReadFile((HANDLE)(h-1), (LPVOID) ptr, count*sz, &dwReallyRead, NULL);
while(dwReallyRead != (DWORD)(count*sz)) {
DWORD err = GetLastError();
if(sqMessageBox(MB_ABORTRETRYIGNORE, TEXT("Squeak Warning"),"Image file read problem (%d out of %d bytes read)", dwReallyRead, count*sz)
if(sqMessageBox(MB_ABORTRETRYIGNORE, TEXT("Squeak Warning"),TEXT("Image file read problem (%d out of %d bytes read)"), dwReallyRead, count*sz)
== IDABORT) return (dwReallyRead / sz);
sqImageFileSeek(h, position);
ReadFile((HANDLE)(h-1), (LPVOID) ptr, count*sz, &dwReallyRead, NULL);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -415,12 +415,17 @@ sqInt ioSetTitleOfWindow(sqInt windowIndex, char * newTitle, sqInt sizeOfTitle)
* int size of new logo path. If one of the function is failing, the logo is not set.
*/
sqInt ioSetIconOfWindow(sqInt windowIndex, char * iconPath, sqInt sizeOfPath) {
WCHAR iconPathW[MAX_PATH + 1];
HWND hwnd = (windowIndex == 1 ? stWindow : ((HWND)windowIndex));
int len;
if (!IsWindow(hwnd)) return 0;
len = MultiByteToWideChar(CP_UTF8, 0, iconPath, sizeOfPath, iconPathW, MAX_PATH);
if(len <= 0) return -1; /* invalid UTF8 ? */
iconPathW[len] = 0;
//Check if file exists and have read rights
if (access(iconPath, 4) == -1) { return -1; };
if (_waccess(iconPath, 4) == -1) { return -1; };
//Load the image into an icon
HICON hIcon = (HICON)LoadImage(NULL, iconPath, IMAGE_ICON, 0, 0, LR_LOADFROMFILE);
HICON hIcon = (HICON)LoadImageW(NULL, iconPathW, IMAGE_ICON, 0, 0, LR_LOADFROMFILE);
if (hIcon == 0)
return -2;
SendMessage(hwnd, WM_SETICON, ICON_BIG, (LONG_PTR)hIcon);
Expand Down
2 changes: 1 addition & 1 deletion platforms/win32/plugins/MIDIPlugin/sqWin32MIDI.c
Original file line number Diff line number Diff line change
Expand Up @@ -605,7 +605,7 @@ int finishSysExCommand(sqMidiPort *port, char *bufferPtr, int count)
/* Return the port with the given number or NULL */
static sqMidiPort* GetPort(int portNum)
{
if(portNum > MAX_DEVICES || portNum < 0)
if(portNum >= MAX_DEVICES || portNum < 0)
{
success(false);
return NULL;
Expand Down
4 changes: 2 additions & 2 deletions platforms/win32/plugins/SocketPlugin/sqWin32NewNet.c
Original file line number Diff line number Diff line change
Expand Up @@ -2179,7 +2179,7 @@ void sqResolverGetAddressInfoHostSizeServiceSizeFlagsFamilyTypeProtocol(char *ho

if (gaiError)
{
fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(gaiError));
fwprintf(stderr, L"getaddrinfo: %s\n", gai_strerrorW(gaiError));
addrList= 0; /* succeed with zero results for impossible constraints */
}

Expand Down Expand Up @@ -2349,7 +2349,7 @@ void sqResolverGetNameInfoSizeFlags(char *addr, sqInt addrSize, sqInt flags)

if (gaiError)
{
fprintf(stderr, "getnameinfo: %s\n", gai_strerror(gaiError));
fwprintf(stderr, L"getnameinfo: %s\n", gai_strerrorW(gaiError));
lastError= gaiError;
goto fail;
}
Expand Down
1 change: 1 addition & 0 deletions platforms/win32/vm/sqPlatformSpecific.h
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@

#ifdef WIN32_FILE_SUPPORT

#define NO_STD_FILE_SUPPORT /* STD_FILE or WIN32_FILE are mutually exclusive options */
#undef sqImageFile
#undef sqImageFileClose
#undef sqImageFileOpen
Expand Down
82 changes: 37 additions & 45 deletions platforms/win32/vm/sqWin32.h
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,7 @@
/* Definition for Intel Processors */
#if defined(_M_IX86) || defined(i386)
# define WIN32_NAME "Win32"
# define WIN32_OS_NAME (fWindows95 ? "95" : "NT")
# define WIN32_OS_NAME "NT"
# define WIN32_PROCESSOR_NAME "IX86"

# if defined(X86)
Expand Down Expand Up @@ -143,16 +143,6 @@

#endif /* (_WIN32_WCE) */

/* THE FOLLOWING IS WRONG (& HENCE I'VE IF 0'ed IT OUT. WE CAN'T MERELY DEFINE
* WIN32 BECAUSE WE MAY BE ON WIN64. eem 2017/05/16
*/
#if 0
/* due to weird include orders, make sure WIN32 is defined */
# if !defined(WIN32)
# define WIN32 1
# endif
#endif

/* Experimental */
#ifdef MINIMAL
/* The hardcoded defs:
Expand Down Expand Up @@ -189,7 +179,6 @@ void SetupKeymap();
void SetupWindows();
void SetupPixmaps();
void SetupPrinter();
void SetupPreferences();
void SetupMIDI();

/********************************************************/
Expand Down Expand Up @@ -259,21 +248,46 @@ int reverse_image_words(unsigned int *dst, unsigned int *src,int depth, int widt
/********************************************************/
/* Declarations we may need by other modules */
/********************************************************/
extern char imageName[]; /* full path and name to image */
extern TCHAR imagePath[]; /* full path to image */
extern TCHAR vmPath[]; /* full path to interpreter's directory */
extern TCHAR vmName[]; /* name of the interpreter's executable */
extern char windowTitle[]; /* window title string */
extern char vmBuildString[]; /* the vm build string */
extern TCHAR windowClassName[]; /* class name for the window */

/* Note: a character can require up to 4 bytes in UTF8 encoding
But the expansion from UTF16 -> UTF8 is never more than 3 bytes for 1 short
U+ 0000-U+ 007F - 1byte in utf8, 1 short in utf16.
U+ 0080-U+ 07FF - 2byte in utf8, 1 short in utf16.
U+ 0800-U+ FFFF - 3byte in utf8, 1 short in utf16.
U+10000-U+10FFFF - 4byte in utf8, 2 short in utf16.
*/
#define MAX_PATH_UTF8 (MAX_PATH*3)

extern char imageName []; /* full path and name to image - UTF8 */
extern WCHAR imageNameW[]; /* full path and name to image - UTF16 */
extern char imagePathA[]; /* full path to image - UTF8 */
extern WCHAR imagePathW[]; /* full path to image - UTF16 */
extern char vmPathA[]; /* full path to interpreter's directory - UTF8 */
extern WCHAR vmPathW[]; /* full path to interpreter's directory - UTF16 */
extern char vmNameA[]; /* name of the interpreter's executable - UTF8 */
extern WCHAR vmNameW[]; /* name of the interpreter's executable - UTF16 */
extern char windowTitle[]; /* window title string - UTF8 */
extern char vmBuildString[]; /* the vm build string */
extern TCHAR windowClassName[]; /* class name for the window */

#ifdef UNICODE
#define imageNameT imageNameW /* define the generic TCHAR* version */
#define imagePath imagePathW
#define vmName vmNameW
#define vmPath vmPathW
#else
#define imageNameT imageName
#define imagePath imagePathA
#define vmName vmNameA
#define vmPath vmPathA
#endif

extern UINT SQ_LAUNCH_DROP;

extern const TCHAR U_ON[];
extern const TCHAR U_OFF[];
extern const TCHAR U_GLOBAL[];
extern const TCHAR U_SLASH[];
extern const TCHAR U_BACKSLASH[];
extern const WCHAR W_BACKSLASH[];

#ifndef NO_PREFERENCES
extern HMENU vmPrefsMenu; /* preferences menu */
Expand All @@ -293,7 +307,6 @@ extern BITMAPINFO *bmi4; /* 4 bit depth bitmap info */
extern BITMAPINFO *bmi8; /* 8 bit depth bitmap info */
extern BITMAPINFO *bmi16; /* 16 bit depth bitmap info */
extern BITMAPINFO *bmi32; /* 32 bit depth bitmap info */
extern BOOL fWindows95; /* Are we running on Win95 or NT? */
extern BOOL fIsConsole; /* Are we running as a console app? */

/* Startup options */
Expand Down Expand Up @@ -332,32 +345,11 @@ extern BOOL f3ButtonMouse; /* Should we use a real 3 button mouse mapping? */
extern BOOL fBufferMouse; /* Should we buffer mouse input? */


/******************************************************/
/* String conversions between Unicode / Ansi / Squeak */
/******************************************************/
/* Note: fromSqueak() and fromSqueak2() are inline conversions
but operate on two different buffers. The maximum length
of strings that can be converted is MAX_PATH */
TCHAR* fromSqueak(const char *sqPtr, int sqLen); /* Inline Squeak -> C */
TCHAR* fromSqueak2(const char *sqPtr, int sqLen); /* 2nd inline conversion */
/* Note: toUnicode() and fromUnicode() are inline conversions
with for at most MAX_PATH sized strings. If the VM
is not compiled with UNICODE defined they just return
the input strings. Also, toUnicode operates on the
same buffer as fromSqueak() */
TCHAR* toUnicode(const char *ptr); /* Inline Ansi -> Unicode */
char* fromUnicode(const TCHAR *ptr); /* Inline Unicode -> Ansi */
/* Note: toUnicodeNew and fromUnicodeNew malloc() new strings.
It is up to the caller to free these! */
TCHAR* toUnicodeNew(const char *ptr); /* Inline Ansi -> Unicode */
char* fromUnicodeNew(const TCHAR *ptr); /* Inline Unicode -> Ansi */
TCHAR *lstrrchr(TCHAR *source, TCHAR c);

/******************************************************/
/* Output stuff */
/******************************************************/
#ifndef sqMessageBox
int __cdecl sqMessageBox(DWORD dwFlags, const TCHAR *titleString, const char* fmt, ...);
int __cdecl sqMessageBox(DWORD dwFlags, const TCHAR *titleString, const TCHAR* fmt, ...);
#endif

#ifndef warnPrintf
Expand All @@ -380,7 +372,7 @@ void vprintLastError(TCHAR *fmt, ...);
/******************************************************/
/* Misc functions */
/******************************************************/
DWORD SqueakImageLength(TCHAR *fileName);
DWORD SqueakImageLength(WCHAR *fileName);
int isLocalFileName(TCHAR *fileName);

#ifndef NO_PLUGIN_SUPPORT
Expand Down
4 changes: 2 additions & 2 deletions platforms/win32/vm/sqWin32Alloc.c
Original file line number Diff line number Diff line change
Expand Up @@ -76,15 +76,15 @@ void *sqAllocateMemory(usqInt minHeapSize, usqInt desiredHeapSize)
} while(!pageBase);
if(!pageBase) {
sqMessageBox(MB_OK | MB_ICONSTOP, TEXT("VM Error:"),
"Unable to allocate memory (%d bytes requested)",
TEXT("Unable to allocate memory (%d bytes requested)"),
maxReserved);
return pageBase;
}
/* commit initial memory as requested */
commit = nowReserved;
if(!VirtualAlloc(pageBase, commit, MEM_COMMIT, PAGE_READWRITE)) {
sqMessageBox(MB_OK | MB_ICONSTOP, TEXT("VM Error:"),
"Unable to commit memory (%d bytes requested)",
TEXT("Unable to commit memory (%d bytes requested)"),
commit);
return NULL;
}
Expand Down