summaryrefslogtreecommitdiffstats
path: root/ms
diff options
context:
space:
mode:
authorAndy Polyakov <appro@openssl.org>2005-05-17 00:08:28 +0000
committerAndy Polyakov <appro@openssl.org>2005-05-17 00:08:28 +0000
commitea1b02db6ab4864befde88ed03099f075cf7db76 (patch)
tree6aa77dcf5934d6197d9fafa59d3ce55f4eb019f4 /ms
parent2c4b354d32b1f34314f1a3ebeee0d0fcfb7505a0 (diff)
OPENSSL_Applink update.
Diffstat (limited to 'ms')
-rw-r--r--ms/applink.c44
-rw-r--r--ms/uplink.c176
-rw-r--r--ms/uplink.h25
-rwxr-xr-xms/uplink.pl31
4 files changed, 148 insertions, 128 deletions
diff --git a/ms/applink.c b/ms/applink.c
index 4333d2639d..e2d066bc1e 100644
--- a/ms/applink.c
+++ b/ms/applink.c
@@ -8,21 +8,38 @@
#define APPLINK_FSETMOD 8
#define APPLINK_FEOF 9
#define APPLINK_FCLOSE 10 /* should not be used */
-#define APPLINK_MAX 10 /* always same as last macro */
+
+#define APPLINK_FOPEN 11 /* solely for completeness */
+#define APPLINK_FSEEK 12
+#define APPLINK_FTELL 13
+#define APPLINK_FFLUSH 14
+#define APPLINK_FERROR 15
+#define APPLINK_CLEARERR 16
+#define APPLINK_FILENO 17 /* to be used with below */
+
+#define APPLINK_OPEN 18 /* formally can't be used, as flags can vary */
+#define APPLINK_READ 19
+#define APPLINK_WRITE 20
+#define APPLINK_LSEEK 21
+#define APPLINK_CLOSE 22
+#define APPLINK_MAX 22 /* always same as last macro */
#ifndef APPMACROS_ONLY
#include <stdio.h>
#include <io.h>
#include <fcntl.h>
-static void *app_stdin() { return stdin; }
-static void *app_stdout() { return stdout; }
-static void *app_stderr() { return stderr; }
-static int app_feof(FILE *fp) { return feof(fp); }
+static void *app_stdin(void) { return stdin; }
+static void *app_stdout(void) { return stdout; }
+static void *app_stderr(void) { return stderr; }
+static int app_feof(FILE *fp) { return feof(fp); }
+static int app_ferror(FILE *fp) { return ferror(fp); }
+static void app_clearerr(FILE *fp) { clearerr(fp); }
+static int app_fileno(FILE *fp) { return _fileno(fp); }
static int app_fsetmod(FILE *fp,char mod)
{ return _setmode (_fileno(fp),mod=='b'?_O_BINARY:_O_TEXT); }
-__declspec(dllexport) void **OPENSSL_Applink()
+__declspec(dllexport) void **OPENSSL_Applink(void)
{ static int once=1;
static void *OPENSSL_ApplinkTable[APPLINK_MAX+1]={(void *)APPLINK_MAX};
@@ -37,6 +54,21 @@ __declspec(dllexport) void **OPENSSL_Applink()
OPENSSL_ApplinkTable[APPLINK_FSETMOD] = app_fsetmod;
OPENSSL_ApplinkTable[APPLINK_FEOF] = app_feof;
OPENSSL_ApplinkTable[APPLINK_FCLOSE] = fclose;
+
+ OPENSSL_ApplinkTable[APPLINK_FOPEN] = fopen;
+ OPENSSL_ApplinkTable[APPLINK_FSEEK] = fseek;
+ OPENSSL_ApplinkTable[APPLINK_FTELL] = ftell;
+ OPENSSL_ApplinkTable[APPLINK_FFLUSH] = fflush;
+ OPENSSL_ApplinkTable[APPLINK_FERROR] = app_ferror;
+ OPENSSL_ApplinkTable[APPLINK_CLEARERR] = app_clearerr;
+ OPENSSL_ApplinkTable[APPLINK_FILENO] = app_fileno;
+
+ OPENSSL_ApplinkTable[APPLINK_OPEN] = _open;
+ OPENSSL_ApplinkTable[APPLINK_READ] = _read;
+ OPENSSL_ApplinkTable[APPLINK_WRITE] = _write;
+ OPENSSL_ApplinkTable[APPLINK_LSEEK] = _lseek;
+ OPENSSL_ApplinkTable[APPLINK_CLOSE] = _close;
+
once = 0;
}
diff --git a/ms/uplink.c b/ms/uplink.c
index c839f9b087..8e2eaa8ffd 100644
--- a/ms/uplink.c
+++ b/ms/uplink.c
@@ -1,4 +1,4 @@
-#if defined(_WIN64) && !defined(UNICODE)
+#if (defined(_WIN64) || defined(_WIN32_WCE)) && !defined(UNICODE)
#define UNICODE
#endif
#if defined(UNICODE) && !defined(_UNICODE)
@@ -7,146 +7,90 @@
#if defined(_UNICODE) && !defined(UNICODE)
#define UNICODE
#endif
-#if defined(_MSC_VER) && !defined(_WIN32_WINNT)
-#define _WIN32_WINNT 0x0333 /* 3.51 */
-#endif
#include <windows.h>
#include <tchar.h>
#include <stdio.h>
-#include <malloc.h>
#include "uplink.h"
-
-#ifdef _MSC_VER
-#pragma comment(lib,"delayimp")
-/*
- * CL command line should also be complemented with following:
- *
- * /link /delayload:advapi32.dll /delayload:user32.dll
- *
- * This is required if/as we want to support Win9x. With delayloaded
- * DLLs in question all we have to do is to make sure NT-specific
- * functions are not actually called under Win9x.
- */
-#endif
-
-#if defined(_WIN32_WINNT) && _WIN32_WINNT>=0x0333
-int IsService()
-{ HWINSTA h;
- DWORD len;
- WCHAR *name;
-
- GetDesktopWindow(); /* return value is ignored */
-
- h = GetProcessWindowStation();
- if (h==NULL) return -1;
-
- if (GetUserObjectInformationW (h,UOI_NAME,NULL,0,&len) ||
- GetLastError() != ERROR_INSUFFICIENT_BUFFER)
- return -1;
-
- if (len>512) return -1; /* paranoia */
- len++,len&=~1; /* paranoia */
-#ifdef _MSC_VER
- name=(WCHAR *)_alloca(len+sizeof(WCHAR));
-#else
- name=(WCHAR *)alloca(len+sizeof(WCHAR));
-#endif
- if (!GetUserObjectInformationW (h,UOI_NAME,name,len,&len))
- return -1;
-
- len++,len&=~1; /* paranoia */
- name[len/sizeof(WCHAR)]=L'\0'; /* paranoia */
-#if 1
- /* This doesn't cover "interactive" services [working with real
- * WinSta0's] nor programs started non-interactively by Task
- * Scheduler [those are working with SAWinSta]. */
- if (wcsstr(name,L"Service-0x")) return 1;
-#else
- /* This covers all non-interactive programs such as services. */
- if (!wcsstr(name,L"WinSta0")) return 1;
-#endif
- else return 0;
-}
-#endif
+void OPENSSL_showfatal(const char *,...);
static TCHAR msg[128];
-static void unimplemented ()
-{
-#if defined(_WIN32_WINNT) && _WIN32_WINNT>=0x0333
- /* this -------------v--- guards NT-specific calls */
- if (GetVersion() < 0x80000000 && IsService())
- { HANDLE h = RegisterEventSource(0,_T("OPENSSL"));
- TCHAR *pmsg=msg;
- ReportEvent(h,EVENTLOG_ERROR_TYPE,0,0,0,1,0,&pmsg,0);
- DeregisterEventSource(h);
- }
- else
-#endif
- { MSGBOXPARAMS m;
-
- m.cbSize = sizeof(m);
- m.hwndOwner = NULL;
- m.lpszCaption = _T("OpenSSL: FATAL");
- m.dwStyle = MB_OK;
- m.hInstance = NULL;
- m.lpszIcon = IDI_ERROR;
- m.dwContextHelpId = 0;
- m.lpfnMsgBoxCallback = NULL;
- m.dwLanguageId = MAKELANGID(LANG_ENGLISH,SUBLANG_ENGLISH_US);
- m.lpszText = msg;
-
- MessageBoxIndirect (&m);
- }
+static void unimplemented (void)
+{ OPENSSL_showfatal (sizeof(TCHAR)==sizeof(char)?"%s\n":"%S\n",msg);
ExitProcess (1);
}
-void OPENSSL_Uplink (void **table, int index)
-{ static HMODULE app=NULL;
- static void **applinktable=NULL;
+void OPENSSL_Uplink (volatile void **table, int index)
+{ static HMODULE volatile apphandle=NULL;
+ static void ** volatile applinktable=NULL;
int len;
-
- len = _stprintf (msg,_T("OPENSSL_Uplink(%p,%02X): "),table,index);
- _tcscpy (msg+len,_T("unimplemented function"));
- table [index] = unimplemented;
-
- if (app==NULL && (app=GetModuleHandle(NULL))==NULL)
- { app=(HMODULE)-1; _tcscpy (msg+len,_T("no host application"));
- return;
- }
- else if (app==(HMODULE)-1) { return; }
-
- if (applinktable==NULL)
- { void**(*applink)();
-
- applink=(void**(*)())GetProcAddress(app,"OPENSSL_Applink");
- if (applink==NULL)
- { app=(HMODULE)-1; _tcscpy (msg+len,_T("no OPENSSL_Applink"));
- return;
+ void (*func)(void)=unimplemented;
+ HANDLE h;
+ void **p;
+
+ /* Note that the below code is not MT-safe in respect to msg
+ * buffer, but what's the worst thing that can happen? Error
+ * message might be misleading or corrupted. As error condition
+ * is fatal and should never be risen, I accept the risk... */
+ /* One can argue that I should have used InterlockedExchangePointer
+ * or something to update static variables and table[]. Well,
+ * store instructions are as atomic as they can get and assigned
+ * values are effectively constant... So that volatile qualifier
+ * should be sufficient [it prohibits compiler to reorder memory
+ * access instructions]. */
+ do {
+ len = _stprintf (msg,_T("OPENSSL_Uplink(%p,%02X): "),table,index);
+ _tcscpy (msg+len,_T("unimplemented function"));
+
+ if ((h=apphandle)==NULL)
+ { if ((h=GetModuleHandle(NULL))==NULL)
+ { apphandle=(HMODULE)-1;
+ _tcscpy (msg+len,_T("no host application"));
+ break;
+ }
+ apphandle = h;
}
- applinktable = (*applink)();
+ if ((h=apphandle)==(HMODULE)-1) /* revalidate */
+ break;
+
if (applinktable==NULL)
- { app=(HMODULE)-1; _tcscpy (msg+len,_T("no ApplinkTable"));
- return;
+ { void**(*applink)();
+
+ applink=(void**(*)())GetProcAddress(h,"OPENSSL_Applink");
+ if (applink==NULL)
+ { apphandle=(HMODULE)-1;
+ _tcscpy (msg+len,_T("no OPENSSL_Applink"));
+ break;
+ }
+ p = (*applink)();
+ if (p==NULL)
+ { apphandle=(HMODULE)-1;
+ _tcscpy (msg+len,_T("no ApplinkTable"));
+ break;
+ }
+ applinktable = p;
}
- }
- if (index > (int)applinktable[0]) { return; }
+ if (index > (int)p[0])
+ break;
+
+ if (p[index]) func = p[index];
+ } while (0);
- if (applinktable[index]) table[index] = applinktable[index];
+ table[index] = func;
}
-#if defined(_MSC_VER) && defined(_M_IX86)
+#if defined(_MSC_VER) && defined(_M_IX86) && !defined(OPENSSL_NO_INLINE_ASM)
#define LAZY(i) \
-__declspec(naked) static void lazy##i () { \
+__declspec(naked) static void lazy##i (void) { \
_asm push i \
_asm push OFFSET OPENSSL_UplinkTable \
_asm call OPENSSL_Uplink \
_asm add esp,8 \
_asm jmp OPENSSL_UplinkTable+4*i }
-#if APPLINK_MAX>20
+#if APPLINK_MAX>25
#error "Add more stubs..."
#endif
/* make some in advance... */
@@ -154,12 +98,14 @@ LAZY(1) LAZY(2) LAZY(3) LAZY(4) LAZY(5)
LAZY(6) LAZY(7) LAZY(8) LAZY(9) LAZY(10)
LAZY(11) LAZY(12) LAZY(13) LAZY(14) LAZY(15)
LAZY(16) LAZY(17) LAZY(18) LAZY(19) LAZY(20)
+LAZY(21) LAZY(22) LAZY(23) LAZY(24) LAZY(25)
void *OPENSSL_UplinkTable[] = {
(void *)APPLINK_MAX,
lazy1, lazy2, lazy3, lazy4, lazy5,
lazy6, lazy7, lazy8, lazy9, lazy10,
lazy11,lazy12,lazy13,lazy14,lazy15,
lazy16,lazy17,lazy18,lazy19,lazy20,
+ lazy21,lazy22,lazy23,lazy24,lazy25,
};
#endif
diff --git a/ms/uplink.h b/ms/uplink.h
index 3e9911ab93..a4a67d3c14 100644
--- a/ms/uplink.h
+++ b/ms/uplink.h
@@ -2,13 +2,28 @@
#include "applink.c"
extern void *OPENSSL_UplinkTable[];
-#define UP_stdin (*(void *(*)())OPENSSL_UplinkTable[APPLINK_STDIN])()
-#define UP_stdout (*(void *(*)())OPENSSL_UplinkTable[APPLINK_STDOUT])()
-#define UP_stderr (*(void *(*)())OPENSSL_UplinkTable[APPLINK_STDERR])()
+
+#define UP_stdin (*(void *(*)(void))OPENSSL_UplinkTable[APPLINK_STDIN])()
+#define UP_stdout (*(void *(*)(void))OPENSSL_UplinkTable[APPLINK_STDOUT])()
+#define UP_stderr (*(void *(*)(void))OPENSSL_UplinkTable[APPLINK_STDERR])()
#define UP_fprintf (*(int (*)(void *,const char *,...))OPENSSL_UplinkTable[APPLINK_FPRINTF])
#define UP_fgets (*(char *(*)(char *,int,void *))OPENSSL_UplinkTable[APPLINK_FGETS])
#define UP_fread (*(size_t (*)(void *,size_t,size_t,void *))OPENSSL_UplinkTable[APPLINK_FREAD])
-#define UP_fwrite (*(size_t (*)(void *,size_t,size_t,void *))OPENSSL_UplinkTable[APPLINK_FWRITE])
+#define UP_fwrite (*(size_t (*)(const void *,size_t,size_t,void *))OPENSSL_UplinkTable[APPLINK_FWRITE])
#define UP_fsetmod (*(int (*)(void *,char))OPENSSL_UplinkTable[APPLINK_FSETMOD])
#define UP_feof (*(int (*)(void *))OPENSSL_UplinkTable[APPLINK_FEOF])
-#define UP_fclose (*(int (*)(void *))OPENSSL_Uplink[APPLINK_FCLOSE])
+#define UP_fclose (*(int (*)(void *))OPENSSL_UplinkTable[APPLINK_FCLOSE])
+
+#define UP_fopen (*(void *(*)(const char *,const char *))OPENSSL_UplinkTable[APPLINK_FOPEN])
+#define UP_fseek (*(int (*)(void *,long,int))OPENSSL_UplinkTable[APPLINK_FSEEK])
+#define UP_ftell (*(long (*)(void *))OPENSSL_UplinkTable[APPLINK_FTELL])
+#define UP_fflush (*(int (*)(void *))OPENSSL_UplinkTable[APPLINK_FFLUSH])
+#define UP_ferror (*(int (*)(void *))OPENSSL_UplinkTable[APPLINK_FERROR])
+#define UP_clearerr (*(void (*)(void *))OPENSSL_UplinkTable[APPLINK_CLEARERR])
+#define UP_fileno (*(int (*)(void *))OPENSSL_UplinkTable[APPLINK_FILENO])
+
+#define UP_open (*(int (*)(const char *,int,...))OPENSSL_UplinkTable[APPLINK_OPEN])
+#define UP_read (*(ssize_t (*)(int,void *,size_t))OPENSSL_UplinkTable[APPLINK_READ])
+#define UP_write (*(ssize_t (*)(int,const void *,size_t))OPENSSL_UplinkTable[APPLINK_WRITE])
+#define UP_lseek (*(long (*)(int,long,int))OPENSSL_UplinkTable[APPLINK_LSEEK])
+#define UP_close (*(int (*)(int))OPENSSL_UplinkTable[APPLINK_CLOSE])
diff --git a/ms/uplink.pl b/ms/uplink.pl
index 801f6e01fa..cd9d37f56f 100755
--- a/ms/uplink.pl
+++ b/ms/uplink.pl
@@ -29,10 +29,37 @@ $arg = shift;
if ($arg =~ /win32n/) { ia32nasm(); }
elsif ($arg =~ /win32/) { ia32masm(); }
-elsif ($arg =~ /ia64/) { ia64ias(); }
-elsif ($arg =~ /amd64/) { amd64masm(); }
+elsif ($arg =~ /coff/) { ia32gas(); }
+elsif ($arg =~ /win64i/ or $arg =~ /ia64/) { ia64ias(); }
+elsif ($arg =~ /win64a/ or $arg =~ /amd64/) { amd64masm(); }
else { die "nonsense $arg"; }
+sub ia32gas() {
+print <<___;
+.text
+___
+for ($i=1;$i<=$N;$i++) {
+print <<___;
+.def .Lazy$i; .scl 3; .type 32; .endef
+.align 4
+.Lazy$i:
+ pushl \$$i
+ pushl _OPENSSL_UplinkTable
+ call _OPENSSL_Uplink
+ addl \$8,%esp
+ jmp *(_OPENSSL_UplinkTable+4*$i)
+___
+}
+print <<___;
+.data
+.align 4
+.globl _OPENSSL_UplinkTable
+_OPENSSL_UplinkTable:
+ .long $N
+___
+for ($i=1;$i<=$N;$i++) { print " .long .Lazy$i\n"; }
+}
+
sub ia32masm() {
print <<___;
.386P