applied patch from Roland Schwingel to fix the problem with file names in

* xmlIO.c: applied patch from Roland Schwingel to fix the problem
  with file names in UTF-8 on Windows, and compat on older win9x
  versions.
Daniel
diff --git a/xmlIO.c b/xmlIO.c
index 60e0a50..58b3feb 100644
--- a/xmlIO.c
+++ b/xmlIO.c
@@ -207,13 +207,13 @@
 
 	if (u8String)
 	{
-		int wLen = MultiByteToWideChar(CP_UTF8,0,u8String,-1,NULL,0);
+		int wLen = MultiByteToWideChar(CP_UTF8,MB_ERR_INVALID_CHARS,u8String,-1,NULL,0);
 		if (wLen)
 		{
 			wString = malloc((wLen+1) * sizeof(wchar_t));
 			if (wString)
 			{
-				if (MultiByteToWideChar(CP_UTF8,0,u8String,-1,wString,wLen+1) == 0)
+				if (MultiByteToWideChar(CP_UTF8,MB_ERR_INVALID_CHARS,u8String,-1,wString,wLen+1) == 0)
 				{
 					free(wString);
 					wString = NULL;
@@ -224,6 +224,73 @@
 	
 	return wString;
 }
+
+/**
+ * __xmlIOWin32GetWcharFunc:
+ * @name:  name of function
+ *
+ * returns function pointer to certain wide character functions
+ * contained in msvcrt.dll on Windows NT or better. 
+ * There is no (really working) support for it on win95/98/Me
+ * but to retain compatibility on ascii basis the capabilities
+ * of the os are depicted during runtime (see use of this function in this file)
+ */
+static void *
+__xmlIOWin32GetWcharFunc(const char *name)
+{
+	void *function = NULL;
+	static HANDLE msvcrt = INVALID_HANDLE_VALUE;
+	static HANDLE winMutex = INVALID_HANDLE_VALUE;
+
+	// create Mutex if not already there
+	if (winMutex == INVALID_HANDLE_VALUE)
+	{
+		winMutex = CreateMutexA(NULL, FALSE, "__xmlIOWin32GetWcharFunc mutex");
+		if (!winMutex)
+			return NULL;
+	}
+
+	// Be atomic
+	if (WaitForSingleObject(winMutex, INFINITE) == WAIT_OBJECT_0)
+	{
+		if (msvcrt == INVALID_HANDLE_VALUE)
+		{
+			msvcrt = NULL; // ensure to enter this code just once
+			OSVERSIONINFOEX osvi;
+	 
+	    	ZeroMemory(&osvi,sizeof(OSVERSIONINFOEX));
+	   	osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFOEX);
+	
+			// Get Operatingsystemversion. If something is wrong here, the system
+			// is heavily damaged. Refuse to deliver pointers in this case.
+	   	if (!GetVersionEx((OSVERSIONINFO *)&osvi))
+	   	{
+	      	osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
+	      	if (!GetVersionEx((OSVERSIONINFO *)&osvi))
+	      	{
+	      		ReleaseMutex(winMutex);
+	         	return NULL;
+	         }
+	   	}
+	
+			// Only continue on NT or better
+			if (osvi.dwPlatformId == VER_PLATFORM_WIN32_NT)
+			{
+				unsigned int oldErrorMode = SetErrorMode(SEM_FAILCRITICALERRORS|SEM_NOOPENFILEERRORBOX);
+		
+				msvcrt = LoadLibraryA("msvcrt.dll");
+				SetErrorMode(oldErrorMode);
+			}
+		}
+	
+		if (msvcrt && name)
+			function = (void *)GetProcAddress(msvcrt,name);
+			
+		ReleaseMutex(winMutex);
+	}
+	
+	return function;
+}
 #endif
 
 /**
@@ -589,7 +656,7 @@
 int
 xmlCheckFilename (const char *path)
 {
-#ifdef HAVE_STAT
+#if defined(HAVE_STAT) && !defined(WIN32)
 	struct stat stat_buffer;
 #endif
 	if (path == NULL)
@@ -598,23 +665,47 @@
 #if defined(WIN32) || defined (__DJGPP__) && !defined (__CYGWIN__)
 	{
 		int retval = 0;
-	
-		wchar_t *wPath = __xmlIOWin32UTF8ToWChar(path);
-		if (wPath)
+
+		// One-time autodetect presence of _wstat. Not available for Win9x
+		static int (*winwstat)(const wchar_t *path,struct _stat *buffer) = INVALID_HANDLE_VALUE;
+
+		if (winwstat == INVALID_HANDLE_VALUE)
+			winwstat = (int (*)(const wchar_t *,struct _stat *))__xmlIOWin32GetWcharFunc("_wstat");
+
+		// Try utf-8 path first on systems capable
+		if (winwstat)
 		{
-			struct _stat stat_buffer;
-			
-			if (_wstat(wPath,&stat_buffer) == 0)
+			wchar_t *wPath = __xmlIOWin32UTF8ToWChar(path);
+			if (wPath)
 			{
-				retval = 1;
+				struct _stat stat_buffer;
 				
-				if (((stat_buffer.st_mode & S_IFDIR) == S_IFDIR))
-					retval = 2;
+				if (winwstat(wPath,&stat_buffer) == 0)
+				{
+					retval = 1;
+					
+					if (((stat_buffer.st_mode & S_IFDIR) == S_IFDIR))
+						retval = 2;
+				}
+		
+				free(wPath);
 			}
-	
-			free(wPath);
 		}
 
+		// Fallback: Path in utf-8 representation not present or win9x		
+		if ((winwstat == NULL) || (retval == 0))
+		{
+				struct _stat stat_buffer;
+				
+				if (_stat(path,&stat_buffer) == 0)
+				{
+					retval = 1;
+					
+					if (((stat_buffer.st_mode & S_IFDIR) == S_IFDIR))
+						retval = 2;
+				}
+		}
+		
 		return retval;
 	}
 #else
@@ -720,7 +811,7 @@
 static void *
 xmlFileOpen_real (const char *filename) {
     const char *path = NULL;
-    FILE *fd;
+    FILE *fd = NULL;
 
     if (filename == NULL)
         return(NULL);
@@ -752,21 +843,28 @@
 
 #if defined(WIN32) || defined (__DJGPP__) && !defined (__CYGWIN__)
 	{
-		wchar_t *wPath = __xmlIOWin32UTF8ToWChar(path);
-		if (wPath)
+		// One-time autodetect presence of _wfopen. Not available for Win9x
+		static FILE *(*winwfopen)(const wchar_t *path,const wchar_t *mode) = INVALID_HANDLE_VALUE;
+
+		if (winwfopen == INVALID_HANDLE_VALUE)
+			winwfopen = (FILE *(*)(const wchar_t *,const wchar_t *))__xmlIOWin32GetWcharFunc("_wfopen");
+
+		// Try to open file unicode path safe. If not available or win9x fall thru to non-unicode safe fopen()
+		if (winwfopen)
 		{
-			fd = _wfopen(wPath, L"rb");
-			free(wPath);
+			wchar_t *wPath = __xmlIOWin32UTF8ToWChar(path);
+			if (wPath)
+			{
+				fd = winwfopen(wPath, L"rb");
+				free(wPath);
+	   	}
    	}
-   	else
-   	{
-   	   fd = fopen(path, "rb");
-	   }
 	}	
-#else
-    fd = fopen(path, "r");
 #endif /* WIN32 */
-    if (fd == NULL) xmlIOErr(0, path);
+
+	if (fd == NULL)
+    	fd = fopen(path, "r");
+   if (fd == NULL) xmlIOErr(0, path);
     return((void *) fd);
 }
 
@@ -807,7 +905,7 @@
 static void *
 xmlFileOpenW (const char *filename) {
     const char *path = NULL;
-    FILE *fd;
+    FILE *fd = NULL;
 
     if (!strcmp(filename, "-")) {
 	fd = stdout;
@@ -834,21 +932,28 @@
 
 #if defined(WIN32) || defined (__DJGPP__) && !defined (__CYGWIN__)
 	{
-		wchar_t *wPath = __xmlIOWin32UTF8ToWChar(path);
-		if (wPath)
+		// One-time autodetect presence of _wfopen. Not available for Win9x
+		static FILE *(*winwfopen)(const wchar_t *path,const wchar_t *mode) = INVALID_HANDLE_VALUE;
+
+		if (winwfopen == INVALID_HANDLE_VALUE)
+			winwfopen = (FILE *(*)(const wchar_t *,const wchar_t *))__xmlIOWin32GetWcharFunc("_wfopen");
+
+		// Try to open file unicode path safe. If not available or win9x fall thru to non-unicode safe fopen()
+		if (winwfopen)
 		{
-			fd = _wfopen(wPath, L"wb");
-			free(wPath);
-   	}
-   	else
-   	{
-	  	   fd = fopen(path, "wb");
-	  	}
+			wchar_t *wPath = __xmlIOWin32UTF8ToWChar(path);
+			if (wPath)
+			{
+				fd = winwfopen(wPath, L"wb");
+				free(wPath);
+	   	}
+	   }
 	}
-#else
-  	   fd = fopen(path, "wb");
 #endif /* WIN32 */
 
+	if (fd == NULL)
+  	   fd = fopen(path, "wb");
+
 	 if (fd == NULL) xmlIOErr(0, path);
     return((void *) fd);
 }
@@ -3499,10 +3604,7 @@
     return(ret);
 }
 
-static int xmlSysIDExists(const char *URL) {
-#ifdef HAVE_STAT
-    int ret;
-    struct stat info;
+static int xmlNoNetExists(const char *URL) {
     const char *path;
 
     if (URL == NULL)
@@ -3522,11 +3624,8 @@
 #endif
     } else 
 	path = URL;
-    ret = stat(path, &info);
-    if (ret == 0)
-	return(1);
-#endif
-    return(0);
+	
+    return xmlCheckFilename(path);
 }
 
 /**
@@ -3570,7 +3669,7 @@
      */
     pref = xmlCatalogGetDefaults();
 
-    if ((pref != XML_CATA_ALLOW_NONE) && (!xmlSysIDExists(URL))) {
+    if ((pref != XML_CATA_ALLOW_NONE) && (!xmlNoNetExists(URL))) {
         /*
          * Do a local lookup
          */
@@ -3597,7 +3696,7 @@
          * TODO: do an URI lookup on the reference
          */
         if ((resource != NULL)
-            && (!xmlSysIDExists((const char *) resource))) {
+            && (!xmlNoNetExists((const char *) resource))) {
             xmlChar *tmp = NULL;
 
             if ((ctxt != NULL) && (ctxt->catalogs != NULL) &&
@@ -3674,7 +3773,7 @@
 xmlParserInputPtr
 xmlLoadExternalEntity(const char *URL, const char *ID,
                       xmlParserCtxtPtr ctxt) {
-    if ((URL != NULL) && (xmlSysIDExists(URL) == 0)) {
+    if ((URL != NULL) && (xmlNoNetExists(URL) == 0)) {
 	char *canonicFilename;
 	xmlParserInputPtr ret;
 
@@ -3697,40 +3796,6 @@
  * 									*
  ************************************************************************/
 
-#ifdef LIBXML_CATALOG_ENABLED
-static int
-xmlNoNetExists(const char *URL)
-{
-#ifdef HAVE_STAT
-    int ret;
-    struct stat info;
-    const char *path;
-
-    if (URL == NULL)
-        return (0);
-
-    if (!xmlStrncasecmp(BAD_CAST URL, BAD_CAST "file://localhost/", 17))
-#if defined (_WIN32) || defined (__DJGPP__) && !defined(__CYGWIN__)
-	path = &URL[17];
-#else
-	path = &URL[16];
-#endif
-    else if (!xmlStrncasecmp(BAD_CAST URL, BAD_CAST "file:///", 8)) {
-#if defined (_WIN32) || defined (__DJGPP__) && !defined(__CYGWIN__)
-        path = &URL[8];
-#else
-        path = &URL[7];
-#endif
-    } else
-        path = URL;
-    ret = stat(path, &info);
-    if (ret == 0)
-        return (1);
-#endif
-    return (0);
-}
-#endif
-
 /**
  * xmlNoNetExternalEntityLoader:
  * @URL:  the URL for the entity to load