scanf problem

Troy Rollo wine at troy.rollo.name
Wed Feb 18 16:28:13 CST 2004


On Thu, 19 Feb 2004 08:27, Eric Pouech wrote:
> Ivan Leo Murray-Smith a écrit :
> > Apparently there is a problem with wine's scanf. this code

> the main issue is that MSVCRT_scanf calls MSVCRT_fscanf while it thinks
> it's actually fvscanf. All the scanf internal functions should be
> implemented as vscanf not scanf
> A+

What he said, except they should all be implemented using vfscanf. There's no 
reason to have all of the *scanf functions listed using the macro tricks 
currently used (dlls/msvcrt/scanf.h) - all these should be capable of being 
turned into a call to vfscanf or vwscanf (this might still justify the macro 
tricks, but only once for vfscanf and once for vwscanf, as is done in glibc. 
In the case of sscanf and vsscanf, this is done by creating a dummy FILE 
instance that has the string as its buffer.

Try the following patch (compiles, but not tested - I don't use msvcrt).
-------------- next part --------------
? dlls/msvcrt/.file.c.swp
? dlls/msvcrt/.scanf.c.swp
? dlls/msvcrt/.scanf.h.swp
? include/msvcrt/.stdio.h.swp
Index: dlls/msvcrt/file.c
===================================================================
RCS file: /home/wine/wine/dlls/msvcrt/file.c,v
retrieving revision 1.62
diff -u -r1.62 file.c
--- dlls/msvcrt/file.c	13 Jan 2004 05:45:05 -0000	1.62
+++ dlls/msvcrt/file.c	18 Feb 2004 22:24:44 -0000
@@ -2383,7 +2383,7 @@
   int res;
 
   va_start(valist, format);
-  res = MSVCRT_fscanf(MSVCRT_stdin, format, valist);
+  res = MSVCRT_vfscanf(MSVCRT_stdin, format, valist);
   va_end(valist);
   return res;
 }
@@ -2397,7 +2397,7 @@
   int res;
 
   va_start(valist, format);
-  res = MSVCRT_fwscanf(MSVCRT_stdin, format, valist);
+  res = MSVCRT_vfwscanf(MSVCRT_stdin, format, valist);
   va_end(valist);
   return res;
 }
Index: dlls/msvcrt/scanf.c
===================================================================
RCS file: /home/wine/wine/dlls/msvcrt/scanf.c,v
retrieving revision 1.5
diff -u -r1.5 scanf.c
--- dlls/msvcrt/scanf.c	5 Sep 2003 23:08:35 -0000	1.5
+++ dlls/msvcrt/scanf.c	18 Feb 2004 22:24:44 -0000
@@ -67,6 +67,7 @@
 #undef WIDE_SCANF
 #undef CONSOLE
 #undef STRING
+#undef VECTOR
 #include "scanf.h"
 
 /*********************************************************************
@@ -75,6 +76,25 @@
 #define WIDE_SCANF 1
 #undef CONSOLE
 #undef STRING
+#undef VECTOR
+#include "scanf.h"
+
+/*********************************************************************
+ *		vfscanf (MSVCRT.@)
+ */
+#undef WIDE_SCANF
+#undef CONSOLE
+#undef STRING
+#define VECTOR 1
+#include "scanf.h"
+
+/*********************************************************************
+ *		vfwscanf (MSVCRT.@)
+ */
+#define WIDE_SCANF 1
+#undef CONSOLE
+#undef STRING
+#define VECTOR 1
 #include "scanf.h"
 
 /*********************************************************************
@@ -83,6 +103,7 @@
 #undef WIDE_SCANF
 #undef CONSOLE
 #define STRING 1
+#undef VECTOR
 #include "scanf.h"
 
 /*********************************************************************
@@ -91,6 +112,7 @@
 #define WIDE_SCANF 1
 #undef CONSOLE
 #define STRING 1
+#undef VECTOR
 #include "scanf.h"
 
 /*********************************************************************
@@ -99,4 +121,5 @@
 #undef WIDE_SCANF
 #define CONSOLE 1
 #undef STRING
+#undef VECTOR
 #include "scanf.h"
Index: dlls/msvcrt/scanf.h
===================================================================
RCS file: /home/wine/wine/dlls/msvcrt/scanf.h,v
retrieving revision 1.14
diff -u -r1.14 scanf.h
--- dlls/msvcrt/scanf.h	6 Jan 2004 21:36:10 -0000	1.14
+++ dlls/msvcrt/scanf.h	18 Feb 2004 22:24:44 -0000
@@ -61,6 +61,17 @@
 #define _FUNCTION_ MSVCRT_sscanf(const char *file, const char *format, ...)
 #endif /* WIDE_SCANF */
 #else /* STRING */
+#ifdef VECTOR
+#ifdef WIDE_SCANF
+#define _GETC_(file) (consumed++, MSVCRT_fgetwc(file))
+#define _UNGETC_(nch, file) do { MSVCRT_ungetwc(nch, file); consumed--; } while(0)
+#define _FUNCTION_ MSVCRT_vfwscanf(MSVCRT_FILE* file, const MSVCRT_wchar_t *format, va_list ap)
+#else /* WIDE_SCANF */
+#define _GETC_(file) (consumed++, MSVCRT_fgetc(file))
+#define _UNGETC_(nch, file) do { MSVCRT_ungetc(nch, file); consumed--; } while(0)
+#define _FUNCTION_ MSVCRT_vfscanf(MSVCRT_FILE* file, const char *format, va_list ap)
+#endif /* WIDE_SCANF */
+#else
 #ifdef WIDE_SCANF
 #define _GETC_(file) (consumed++, MSVCRT_fgetwc(file))
 #define _UNGETC_(nch, file) do { MSVCRT_ungetwc(nch, file); consumed--; } while(0)
@@ -70,6 +81,7 @@
 #define _UNGETC_(nch, file) do { MSVCRT_ungetc(nch, file); consumed--; } while(0)
 #define _FUNCTION_ MSVCRT_fscanf(MSVCRT_FILE* file, const char *format, ...)
 #endif /* WIDE_SCANF */
+#endif /* VECTOR */
 #endif /* STRING */
 #endif /* CONSOLE */
 
@@ -82,7 +94,9 @@
 int _FUNCTION_ {
     int rd = 0, consumed = 0;
     int nch;
+#ifndef VECTOR
     va_list ap;
+#endif /* VECTOR */
     if (!*format) return 0;
 #ifndef WIDE_SCANF
 #ifdef CONSOLE
@@ -98,7 +112,9 @@
     nch = _GETC_(file);
     if (nch == _EOF_) return _EOF_RET;
 
+#ifndef VECTOR
     va_start(ap, format);
+#endif /* VECTOR */
     while (*format) {
 	/* a whitespace character in the format string causes scanf to read,
 	 * but not store, all consecutive white-space characters in the input
@@ -512,7 +528,9 @@
     if (nch!=_EOF_) {
 	_UNGETC_(nch, file);
     }
+#ifndef VECTOR
     va_end(ap);
+#endif /* VECTOR */
     TRACE("returning %d\n", rd);
     return rd;
 }
Index: include/msvcrt/stdio.h
===================================================================
RCS file: /home/wine/wine/include/msvcrt/stdio.h,v
retrieving revision 1.15
diff -u -r1.15 stdio.h
--- include/msvcrt/stdio.h	24 Oct 2003 00:23:51 -0000	1.15
+++ include/msvcrt/stdio.h	18 Feb 2004 22:24:44 -0000
@@ -184,6 +184,7 @@
 MSVCRT(size_t) MSVCRT(fread)(void*,MSVCRT(size_t),MSVCRT(size_t),MSVCRT(FILE)*);
 MSVCRT(FILE)* MSVCRT(freopen)(const char*,const char*,MSVCRT(FILE)*);
 int         MSVCRT(fscanf)(MSVCRT(FILE)*,const char*,...);
+int         MSVCRT(fvscanf)(MSVCRT(FILE)*,const char*,va_list);
 int         MSVCRT(fseek)(MSVCRT(FILE)*,long,int);
 int         MSVCRT(fsetpos)(MSVCRT(FILE)*,MSVCRT(fpos_t)*);
 long        MSVCRT(ftell)(MSVCRT(FILE)*);
@@ -236,6 +237,7 @@
 int             MSVCRT(fwprintf)(MSVCRT(FILE)*,const MSVCRT(wchar_t)*,...);
 int             MSVCRT(fputws)(const MSVCRT(wchar_t)*,MSVCRT(FILE)*);
 int             MSVCRT(fwscanf)(MSVCRT(FILE)*,const MSVCRT(wchar_t)*,...);
+int             MSVCRT(vfwscanf)(MSVCRT(FILE)*,const MSVCRT(wchar_t)*,va_list);
 MSVCRT(wint_t)  MSVCRT(getwc)(MSVCRT(FILE)*);
 MSVCRT(wint_t)  MSVCRT(getwchar)(void);
 MSVCRT(wchar_t)*MSVCRT(getws)(MSVCRT(wchar_t)*);


More information about the wine-devel mailing list