https://git.reactos.org/?p=reactos.git;a=commitdiff;h=063c818c729bd2eeb560c…
commit 063c818c729bd2eeb560c691fdbf1297c94a4d24
Author: Timo Kreuzer <timo.kreuzer(a)reactos.org>
AuthorDate: Thu Jan 30 12:42:59 2025 +0200
Commit: Timo Kreuzer <timo.kreuzer(a)reactos.org>
CommitDate: Wed Feb 12 16:54:45 2025 +0200
[MSVCRT_WINETEST] Sync to wine-10.0
---
modules/rostests/winetests/msvcrt/CMakeLists.txt | 17 +-
modules/rostests/winetests/msvcrt/cpp.c | 279 ++--
modules/rostests/winetests/msvcrt/data.c | 22 +-
modules/rostests/winetests/msvcrt/dir.c | 118 +-
modules/rostests/winetests/msvcrt/environ.c | 386 ++++--
modules/rostests/winetests/msvcrt/file.c | 694 +++++++++-
modules/rostests/winetests/msvcrt/heap.c | 103 +-
modules/rostests/winetests/msvcrt/locale.c | 227 ++-
modules/rostests/winetests/msvcrt/misc.c | 151 +-
modules/rostests/winetests/msvcrt/printf.c | 1191 ++++++----------
modules/rostests/winetests/msvcrt/scanf.c | 111 +-
modules/rostests/winetests/msvcrt/string.c | 1599 +++++++++++++++++++---
modules/rostests/winetests/msvcrt/time.c | 455 +++---
13 files changed, 3694 insertions(+), 1659 deletions(-)
diff --git a/modules/rostests/winetests/msvcrt/CMakeLists.txt
b/modules/rostests/winetests/msvcrt/CMakeLists.txt
index 53cb3a0067c..8ee88854dc9 100644
--- a/modules/rostests/winetests/msvcrt/CMakeLists.txt
+++ b/modules/rostests/winetests/msvcrt/CMakeLists.txt
@@ -1,4 +1,6 @@
+remove_definitions(-D_CRT_NON_CONFORMING_SWPRINTFS)
+
list(APPEND SOURCE
cpp.c
data.c
@@ -15,7 +17,7 @@ list(APPEND SOURCE
time.c)
list(APPEND PCH_SKIP_SOURCE
- printf.c # _CRT_NON_CONFORMING_SWPRINTFS
+ printf.c
testlist.c)
add_executable(msvcrt_winetest
@@ -25,6 +27,8 @@ add_executable(msvcrt_winetest
target_compile_definitions(msvcrt_winetest PRIVATE
WINETEST_USE_DBGSTR_LONGLONG
_CRT_NONSTDC_NO_DEPRECATE
+ _USE_MATH_DEFINES
+ WIN32_NO_STATUS=
__msvcrt_ulong=ULONG)
if(CMAKE_C_COMPILER_ID STREQUAL "GNU" OR CMAKE_C_COMPILER_ID STREQUAL
"Clang")
@@ -34,13 +38,14 @@ if(CMAKE_C_COMPILER_ID STREQUAL "GNU" OR CMAKE_C_COMPILER_ID
STREQUAL "Clang")
endif()
endif()
-set_module_type(msvcrt_winetest win32cui)
-add_importlibs(msvcrt_winetest advapi32 msvcrt kernel32)
-target_link_libraries(msvcrt_winetest oldnames)
-
if(MSVC)
- add_importlibs(msvcrt_winetest ntdll)
+ # 'swscanf' : unknown type field character '\xe1' in format
specifier
+ target_compile_options(msvcrt_winetest PRIVATE /wd4476)
endif()
+set_module_type(msvcrt_winetest win32cui)
+add_importlibs(msvcrt_winetest advapi32 msvcrt kernel32 ntdll)
+target_link_libraries(msvcrt_winetest oldnames)
+
add_pch(msvcrt_winetest precomp.h "${PCH_SKIP_SOURCE}")
add_rostests_file(TARGET msvcrt_winetest)
diff --git a/modules/rostests/winetests/msvcrt/cpp.c
b/modules/rostests/winetests/msvcrt/cpp.c
index 07b49ae755d..bfc092e0591 100644
--- a/modules/rostests/winetests/msvcrt/cpp.c
+++ b/modules/rostests/winetests/msvcrt/cpp.c
@@ -44,12 +44,8 @@ typedef struct __type_info
#endif
/* Function pointers. We need to use these to call these funcs as __thiscall */
-static HMODULE hMsvcrt;
-
-static void* (__cdecl *poperator_new)(unsigned int);
+static void* (__cdecl *poperator_new)(size_t);
static void (__cdecl *poperator_delete)(void*);
-static void* (__cdecl *pmalloc)(unsigned int);
-static void (__cdecl *pfree)(void*);
/* exception */
static void (__thiscall *pexception_ctor)(exception*,LPCSTR*);
@@ -112,9 +108,6 @@ static void* (__cdecl *p__RTDynamicCast)(void*,int,void*,void*,int);
static char* (__cdecl *p__unDName)(char*,const char*,int,void*,void*,unsigned short
int);
-/* _very_ early native versions have serious RTTI bugs, so we check */
-static void* bAncientVersion;
-
/* Emulate a __thiscall */
#ifdef __i386__
@@ -157,23 +150,12 @@ static void init_thiscall_thunk(void)
#endif /* __i386__ */
/* Some exports are only available in later versions */
-#define SETNOFAIL(x,y) x = (void*)GetProcAddress(hMsvcrt,y)
+#define SETNOFAIL(x,y) x = (void*)GetProcAddress(hmsvcrt,y)
#define SET(x,y) do { SETNOFAIL(x,y); ok(x != NULL, "Export '%s' not
found\n", y); } while(0)
static BOOL InitFunctionPtrs(void)
{
- hMsvcrt = GetModuleHandleA("msvcrt.dll");
- if (!hMsvcrt)
- hMsvcrt = GetModuleHandleA("msvcrtd.dll");
- ok(hMsvcrt != 0, "GetModuleHandleA failed\n");
- if (!hMsvcrt)
- {
- win_skip("Could not load msvcrt.dll\n");
- return FALSE;
- }
-
- SET(pmalloc, "malloc");
- SET(pfree, "free");
+ HMODULE hmsvcrt = GetModuleHandleA("msvcrt.dll");
SET(pexception_vtable, "??_7exception@@6B@");
SET(pbad_typeid_vtable, "??_7bad_typeid@@6B@");
@@ -187,7 +169,6 @@ static BOOL InitFunctionPtrs(void)
SET(p__unDName,"__unDName");
/* Extremely early versions export logic_error, and crash in RTTI */
- SETNOFAIL(bAncientVersion, "??0logic_error@@QAE@ABQBD@Z");
if (sizeof(void *) > sizeof(int)) /* 64-bit initialization */
{
SETNOFAIL(poperator_new, "??_U@YAPEAX_K@Z");
@@ -242,50 +223,50 @@ static BOOL InitFunctionPtrs(void)
SETNOFAIL(poperator_new, "??_U@YAPAXI@Z");
SETNOFAIL(poperator_delete, "??_V@YAXPAX@Z");
- SET(pexception_ctor, "??0exception@std@@QAA@ABQBD@Z");
- SET(pexception_copy_ctor, "??0exception@std@@QAA@ABV01@@Z");
- SET(pexception_default_ctor, "??0exception@std@@QAA@XZ");
- SET(pexception_dtor, "??1exception@std@@UAA@XZ");
- SET(pexception_opequals, "??4exception@std@@QAAAAV01@ABV01@@Z");
- SET(pexception_what, "?what@exception@std@@UBAPBDXZ");
- SET(pexception_vector_dtor, "??_Eexception@@UAEPAXI@Z");/**/
- SET(pexception_scalar_dtor, "??_Gexception@@UAEPAXI@Z");/**/
-
- SET(pbad_typeid_ctor, "??0bad_typeid@std@@QAA@PBD@Z");
- SETNOFAIL(pbad_typeid_ctor_closure, "??_Fbad_typeid@std@@QAAXXZ");
- SET(pbad_typeid_copy_ctor, "??0bad_typeid@std@@QAA@ABV01@@Z");
- SET(pbad_typeid_dtor, "??1bad_typeid@std@@UAA@XZ");
- SET(pbad_typeid_opequals, "??4bad_typeid@std@@QAAAAV01@ABV01@@Z");
- SET(pbad_typeid_what, "?what@exception@std@@UBAPBDXZ");
- SET(pbad_typeid_vector_dtor, "??_Ebad_cast@@UAEPAXI@Z");
- SET(pbad_typeid_scalar_dtor, "??_Gbad_cast@@UAEPAXI@Z");
+ SET(pexception_ctor, "??0exception@@QAA@ABQBD@Z");
+ SET(pexception_copy_ctor, "??0exception@@QAA@ABV0@@Z");
+ SET(pexception_default_ctor, "??0exception@@QAA@XZ");
+ SET(pexception_dtor, "??1exception@@UAA@XZ");
+ SET(pexception_opequals, "??4exception@@QAAAAV0@ABV0@@Z");
+ SET(pexception_what, "?what@exception@@UBAPBDXZ");
+ pexception_vector_dtor = (void*)pexception_vtable[0];
+ pexception_scalar_dtor = (void*)pexception_vtable[0];
+
+ SET(pbad_typeid_ctor, "??0bad_typeid@@QAA@PBD@Z");
+ SETNOFAIL(pbad_typeid_ctor_closure, "??_Fbad_typeid@@QAAXXZ");
+ SET(pbad_typeid_copy_ctor, "??0bad_typeid@@QAA@ABV0@@Z");
+ SET(pbad_typeid_dtor, "??1bad_typeid@@UAA@XZ");
+ SET(pbad_typeid_opequals, "??4bad_typeid@@QAAAAV0@ABV0@@Z");
+ SET(pbad_typeid_what, "?what@exception@@UBAPBDXZ");
+ pbad_typeid_vector_dtor = (void*)pbad_typeid_vtable[0];
+ pbad_typeid_scalar_dtor = (void*)pbad_typeid_vtable[0];
SETNOFAIL(pbad_cast_ctor, "??0bad_cast@@QAE@ABQBD@Z");
if (!pbad_cast_ctor)
- SET(pbad_cast_ctor, "??0bad_cast@std@@AAA@PBQBD@Z");
- SETNOFAIL(pbad_cast_ctor2, "??0bad_cast@std@@QAA@PBD@Z");
- SETNOFAIL(pbad_cast_ctor_closure, "??_Fbad_cast@std@@QAAXXZ");
- /* FIXME: No ARM equivalent for "??0bad_cast@@QAE@ABV0@@Z" */
- SET(pbad_cast_dtor, "??1bad_cast@std@@UAA@XZ");
- SET(pbad_cast_opequals, "??4bad_cast@std@@QAAAAV01@ABV01@@Z");
- SET(pbad_cast_what, "?what@exception@std@@UBAPBDXZ");
- SET(pbad_cast_vector_dtor, "??_Ebad_cast@@UAEPAXI@Z");
- SET(pbad_cast_scalar_dtor, "??_Gbad_cast@@UAEPAXI@Z");
+ SET(pbad_cast_ctor, "??0bad_cast@@AAA@PBQBD@Z");
+ SETNOFAIL(pbad_cast_ctor2, "??0bad_cast@@QAA@PBD@Z");
+ SETNOFAIL(pbad_cast_ctor_closure, "??_Fbad_cast@@QAAXXZ");
+ SET(pbad_cast_copy_ctor, "??0bad_cast@@QAA@ABV0@@Z");
+ SET(pbad_cast_dtor, "??1bad_cast@@UAA@XZ");
+ SET(pbad_cast_opequals, "??4bad_cast@@QAAAAV0@ABV0@@Z");
+ SET(pbad_cast_what, "?what@exception@@UBAPBDXZ");
+ pbad_cast_vector_dtor = (void*)pbad_cast_vtable[0];
+ pbad_cast_scalar_dtor = (void*)pbad_cast_vtable[0];
- SET(p__non_rtti_object_ctor, "??0__non_rtti_object@std@@QAA@PBD@Z");
- SET(p__non_rtti_object_copy_ctor,
"??0__non_rtti_object@std@@QAA@ABV01@@Z");
- SET(p__non_rtti_object_dtor, "??1__non_rtti_object@std@@UAA@XZ");
- SET(p__non_rtti_object_opequals,
"??4__non_rtti_object@std@@QAAAAV01@ABV01@@Z");
- SET(p__non_rtti_object_what, "?what@exception@std@@UBAPBDXZ");
- SET(p__non_rtti_object_vector_dtor,
"??_E__non_rtti_object@@UAEPAXI@Z");
- SET(p__non_rtti_object_scalar_dtor,
"??_G__non_rtti_object@@UAEPAXI@Z");
+ SET(p__non_rtti_object_ctor, "??0__non_rtti_object@@QAA@PBD@Z");
+ SET(p__non_rtti_object_copy_ctor,
"??0__non_rtti_object@@QAA@ABV0@@Z");
+ SET(p__non_rtti_object_dtor, "??1__non_rtti_object@@UAA@XZ");
+ SET(p__non_rtti_object_opequals,
"??4__non_rtti_object@@QAAAAV0@ABV0@@Z");
+ SET(p__non_rtti_object_what, "?what@exception@@UBAPBDXZ");
+ p__non_rtti_object_vector_dtor = (void*)p__non_rtti_object_vtable[0];
+ p__non_rtti_object_scalar_dtor = (void*)p__non_rtti_object_vtable[0];
SET(ptype_info_dtor, "??1type_info@@UAA@XZ");
SET(ptype_info_raw_name, "?raw_name@type_info@@QBAPBDXZ");
- SET(ptype_info_name, "?name@type_info@@QBEPBDXZ");
- SET(ptype_info_before, "?before@type_info@@QBA_NABV1@@Z");
- SET(ptype_info_opequals_equals, "??8type_info@@QBA_NABV0@@Z");
- SET(ptype_info_opnot_equals, "??9type_info@@QBA_NABV0@@Z");
+ SET(ptype_info_name, "?name@type_info@@QBAPBDXZ");
+ SET(ptype_info_before, "?before@type_info@@QBAHABV1@@Z");
+ SET(ptype_info_opequals_equals, "??8type_info@@QBAHABV0@@Z");
+ SET(ptype_info_opnot_equals, "??9type_info@@QBAHABV0@@Z");
#else
SETNOFAIL(poperator_new, "??_U@YAPAXI@Z");
SETNOFAIL(poperator_delete, "??_V@YAXPAX@Z");
@@ -338,9 +319,9 @@ static BOOL InitFunctionPtrs(void)
}
if (!poperator_new)
- poperator_new = pmalloc;
+ poperator_new = malloc;
if (!poperator_delete)
- poperator_delete = pfree;
+ poperator_delete = free;
init_thiscall_thunk();
return TRUE;
@@ -448,7 +429,7 @@ static void test_exception(void)
name = call_func1(pexception_what, &e);
ok(e.name == name, "Bad exception name from vtable e::what()\n");
- if (p__RTtypeid && !bAncientVersion)
+ if (p__RTtypeid)
{
/* Check the rtti */
type_info *ti = p__RTtypeid(&e);
@@ -571,7 +552,7 @@ static void test_bad_typeid(void)
name = call_func1(pbad_typeid_what, &e);
ok(e.name == name, "Bad bad_typeid name from vtable e::what()\n");
- if (p__RTtypeid && !bAncientVersion)
+ if (p__RTtypeid)
{
/* Check the rtti */
type_info *ti = p__RTtypeid(&e);
@@ -699,7 +680,7 @@ static void test_bad_cast(void)
name = call_func1(pbad_cast_what, &e);
ok(e.name == name, "Bad bad_cast name from vtable e::what()\n");
- if (p__RTtypeid && !bAncientVersion)
+ if (p__RTtypeid)
{
/* Check the rtti */
type_info *ti = p__RTtypeid(&e);
@@ -801,7 +782,7 @@ static void test___non_rtti_object(void)
name = call_func1(p__non_rtti_object_what, &e);
ok(e.name == name, "Bad __non_rtti_object name from vtable e::what()\n");
- if (p__RTtypeid && !bAncientVersion)
+ if (p__RTtypeid)
{
/* Check the rtti */
type_info *ti = p__RTtypeid(&e);
@@ -818,14 +799,14 @@ static void test_type_info(void)
char* name;
int res;
- if (!pmalloc || !pfree || !ptype_info_dtor || !ptype_info_raw_name ||
+ if (!ptype_info_dtor || !ptype_info_raw_name ||
!ptype_info_name || !ptype_info_before ||
!ptype_info_opequals_equals || !ptype_info_opnot_equals)
return;
/* Test calling the dtors */
call_func1(ptype_info_dtor, &t1); /* No effect, since name is NULL */
- t1.name = pmalloc(64);
+ t1.name = malloc(64);
strcpy(t1.name, "foo");
call_func1(ptype_info_dtor, &t1); /* Frees t1.name using 'free' */
@@ -888,7 +869,7 @@ static inline void/*rtti_object_locator*/ *get_obj_locator( void
*cppobj )
return (void *)vtable[-1];
}
-#ifndef __x86_64__
+#ifdef __i386__
#define DEFINE_RTTI_REF(type, name) type *name
#define RTTI_REF(instance, name) &instance.name
#define RTTI_REF_SIG0(instance, name, base) RTTI_REF(instance, name)
@@ -910,33 +891,36 @@ static void test_rtti(void)
DEFINE_RTTI_REF(void, object_locator);
} *obj_locator;
+ struct _rtti_base_descriptor
+ {
+ DEFINE_RTTI_REF(type_info, type_descriptor);
+ int num_base_classes;
+ struct {
+ int this_offset;
+ int vbase_descr;
+ int vbase_offset;
+ } this_ptr_offsets;
+ unsigned int attributes;
+ };
+
+ struct _rtti_base_array {
+ DEFINE_RTTI_REF(struct _rtti_base_descriptor, bases[4]);
+ };
+
+ struct _rtti_object_hierarchy {
+ unsigned int signature;
+ unsigned int attributes;
+ int array_len;
+ DEFINE_RTTI_REF(struct _rtti_base_array, base_classes);
+ };
+
struct rtti_data
{
type_info type_info[4];
- struct _rtti_base_descriptor
- {
- DEFINE_RTTI_REF(type_info, type_descriptor);
- int num_base_classes;
- struct {
- int this_offset;
- int vbase_descr;
- int vbase_offset;
- } this_ptr_offsets;
- unsigned int attributes;
- } base_descriptor[4];
-
- struct _rtti_base_array {
- DEFINE_RTTI_REF(struct _rtti_base_descriptor, bases[4]);
- } base_array;
-
- struct _rtti_object_hierarchy {
- unsigned int signature;
- unsigned int attributes;
- int array_len;
- DEFINE_RTTI_REF(struct _rtti_base_array, base_classes);
- } object_hierarchy;
-
+ struct _rtti_base_descriptor base_descriptor[4];
+ struct _rtti_base_array base_array;
+ struct _rtti_object_hierarchy object_hierarchy;
struct _object_locator object_locator;
} simple_class_rtti = {
{ {NULL, NULL, "simple_class"} },
@@ -962,11 +946,17 @@ static void test_rtti(void)
void *simple_class_vtbl[2] = {&simple_class_rtti.object_locator};
void *simple_class = &simple_class_vtbl[1];
void *child_class_vtbl[2] = {&child_class_rtti.object_locator};
- void *child_class = &child_class_vtbl[1];
+ struct {
+ void *vtbl;
+ char data[4];
+ } child_class = { &child_class_vtbl[1] };
void *simple_class_sig0_vtbl[2] = {&simple_class_sig0_rtti.object_locator};
void *simple_class_sig0 = &simple_class_sig0_vtbl[1];
void *child_class_sig0_vtbl[2] = {&child_class_sig0_rtti.object_locator};
- void *child_class_sig0 = &child_class_sig0_vtbl[1];
+ struct {
+ void *vtbl;
+ char data[4];
+ } child_class_sig0 = { &child_class_sig0_vtbl[1] };
void *virtual_base_class_vtbl[2] = {&virtual_base_class_rtti.object_locator};
int virtual_base_class_vbtbl[2] = {0, 0x100};
struct {
@@ -980,12 +970,11 @@ static void test_rtti(void)
exception e,b;
void *casted;
BOOL old_signature;
-#ifdef __x86_64__
+#ifndef __i386__
char *base = (char*)GetModuleHandleW(NULL);
#endif
- if (bAncientVersion ||
- !p__RTCastToVoid || !p__RTtypeid || !pexception_ctor || !pbad_typeid_ctor
+ if (!p__RTCastToVoid || !p__RTtypeid || !pexception_ctor || !pbad_typeid_ctor
|| !p__RTDynamicCast || !pexception_dtor || !pbad_typeid_dtor)
return;
@@ -1099,46 +1088,32 @@ static void test_demangle_datatype(void)
{
char * name;
struct _demangle demangle[]={
-/* { "BlaBla"," ?? ::Bla", FALSE}, */
- { "ABVVec4@ref2@dice@@","class dice::ref2::Vec4 const &",TRUE},
- { "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$0H@@@", "class
CDB_GEN_BIG_ENUM_FLAG<enum CDB_WYSIWYG_BITS_ENUM,7>", TRUE},
- { "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$0HO@@@", "class
CDB_GEN_BIG_ENUM_FLAG<enum CDB_WYSIWYG_BITS_ENUM,126>",TRUE},
- { "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$0HOA@@@", "class
CDB_GEN_BIG_ENUM_FLAG<enum CDB_WYSIWYG_BITS_ENUM,2016>",TRUE},
- { "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$0HOAA@@@", "class
CDB_GEN_BIG_ENUM_FLAG<enum CDB_WYSIWYG_BITS_ENUM,32256>",TRUE},
- { "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$01@@@",
"?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$01@@@", FALSE},
-/* { "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$011@@@",
"?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$011@@@",FALSE}, */
+ { "BlaBla"," ?? ::Bla", FALSE},
+ { "ABVVec4@ref2@dice@@", "class dice::ref2::Vec4 const
&", TRUE},
+ { "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$0H@@@",
+ "class CDB_GEN_BIG_ENUM_FLAG<enum CDB_WYSIWYG_BITS_ENUM,7>",
TRUE},
+ { "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$0HO@@@",
+ "class CDB_GEN_BIG_ENUM_FLAG<enum
CDB_WYSIWYG_BITS_ENUM,126>",TRUE},
+ { "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$0HOA@@@",
+ "class CDB_GEN_BIG_ENUM_FLAG<enum
CDB_WYSIWYG_BITS_ENUM,2016>",TRUE},
+ { "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$0HOAA@@@",
+ "class CDB_GEN_BIG_ENUM_FLAG<enum
CDB_WYSIWYG_BITS_ENUM,32256>",TRUE},
+ { "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$01@@@",
+ "?AV?$CDB_GEN_BIG_ENUM_FLAG@W4CDB_WYSIWYG_BITS_ENUM@@$01@@@",
FALSE},
+ { "P8test@@AACXZ", "signed char (__cdecl test::*)(void)",
TRUE},
+ { "P8test@@BACXZ", "signed char (__cdecl test::*)(void)const
", TRUE},
};
int i, num_test = ARRAY_SIZE(demangle);
for (i = 0; i < num_test; i++)
{
- name = p__unDName(0, demangle[i].mangled, 0, pmalloc, pfree, 0x2800);
+ name = p__unDName(0, demangle[i].mangled, 0, malloc, free, 0x2800);
todo_wine_if (!demangle[i].test_in_wine)
ok(name != NULL && !strcmp(name,demangle[i].result), "Got name
\"%s\" for %d\n", name, i);
- if(name)
- pfree(name);
+ free(name);
}
}
-/* Compare two strings treating multiple spaces (' ', ascii 0x20) in s2
- as single space. Needed for test_demangle as __unDName() returns sometimes
- two spaces instead of one in some older native msvcrt dlls. */
-static int strcmp_space(const char *s1, const char *s2)
-{
- const char* s2start = s2;
- do {
- while (*s1 == *s2 && *s1) {
- s1++;
- s2++;
- }
- if (*s2 == ' ' && s2 > s2start && *(s2 - 1) == '
')
- s2++;
- else
- break;
- } while (*s1 && *s2);
- return *s1 - *s2;
-}
-
static void test_demangle(void)
{
static struct {const char* in; const char* out; const char *broken; unsigned int
flags;} test[] = {
@@ -1202,7 +1177,7 @@ static void test_demangle(void)
/* 23 */ {"??0streambuf@@QAE@ABV0@@Z", "public: __thiscall
streambuf::streambuf(class streambuf const &)"},
/* 24 */ {"??0strstreambuf@@QAE@ABV0@@Z", "public: __thiscall
strstreambuf::strstreambuf(class strstreambuf const &)"},
/* 25 */ {"??0strstreambuf@@QAE@H@Z", "public: __thiscall
strstreambuf::strstreambuf(int)"},
-/* 26 */ {"??0strstreambuf@@QAE@P6APAXJ@ZP6AXPAX@Z@Z", "public: __thiscall
strstreambuf::strstreambuf(void * (__cdecl*)(long),void (__cdecl*)(void *))"},
+/* 26 */ {"??0strstreambuf@@QAE@Q6APAXJ@ZS6AXPAX@Z@Z", "public: __thiscall
strstreambuf::strstreambuf(void * (__cdecl*const)(long),void (__cdecl*const volatile)(void
*))"},
/* 27 */ {"??0strstreambuf@@QAE@PADH0@Z", "public: __thiscall
strstreambuf::strstreambuf(char *,int,char *)"},
/* 28 */ {"??0strstreambuf@@QAE@PAEH0@Z", "public: __thiscall
strstreambuf::strstreambuf(unsigned char *,int,unsigned char *)"},
/* 29 */ {"??0strstreambuf@@QAE@XZ", "public: __thiscall
strstreambuf::strstreambuf(void)"},
@@ -1237,7 +1212,7 @@ static void test_demangle(void)
/* 58 */
{"?do_get@?$num_get@DV?$istreambuf_iterator@DU?$char_traits@D@std@@@std@@@std@@MBE?AV?$istreambuf_iterator@DU?$char_traits@D@std@@@2@V32@0AAVios_base@2@AAHAAJ@Z",
"protected: virtual class std::istreambuf_iterator<char,struct
std::char_traits<char> > __thiscall std::num_get<char,class
std::istreambuf_iterator<char,struct std::char_traits<char> >
>::do_get(class std::istreambuf_iterator<char,struct std::char_traits<char>
>,class std::istreambuf_iterator<char,struct std::char_trai [...]
/* 59 */
{"?do_get@?$num_get@DV?$istreambuf_iterator@DU?$char_traits@D@std@@@std@@@std@@MBE?AV?$istreambuf_iterator@DU?$char_traits@D@std@@@2@V32@0AAVios_base@2@AAHAAK@Z",
"protected: virtual class std::istreambuf_iterator<char,struct
std::char_traits<char> > __thiscall std::num_get<char,class
std::istreambuf_iterator<char,struct std::char_traits<char> >
>::do_get(class std::istreambuf_iterator<char,struct std::char_traits<char>
>,class std::istreambuf_iterator<char,struct std::char_trai [...]
/* 60 */
{"?do_get@?$num_get@DV?$istreambuf_iterator@DU?$char_traits@D@std@@@std@@@std@@MBE?AV?$istreambuf_iterator@DU?$char_traits@D@std@@@2@V32@0AAVios_base@2@AAHAAM@Z",
"protected: virtual class std::istreambuf_iterator<char,struct
std::char_traits<char> > __thiscall std::num_get<char,class
std::istreambuf_iterator<char,struct std::char_traits<char> >
>::do_get(class std::istreambuf_iterator<char,struct std::char_traits<char>
>,class std::istreambuf_iterator<char,struct std::char_trai [...]
-/* 61 */ {"?_query_new_handler@@YAP6AHI@ZXZ", "int (__cdecl*__cdecl
_query_new_handler(void))(unsigned int)"},
+/* 61 */ {"?_query_new_handler@@YAR6AHI@ZXZ", "int (__cdecl*__cdecl
_query_new_handler(void))(unsigned int)"},
/* 62 */ {"?register_callback@ios_base@std@@QAEXP6AXW4event@12@AAV12@H@ZH@Z",
"public: void __thiscall std::ios_base::register_callback(void (__cdecl*)(enum
std::ios_base::event,class std::ios_base &,int),int)"},
/* 63 */
{"?seekg@?$basic_istream@DU?$char_traits@D@std@@@std@@QAEAAV12@JW4seekdir@ios_base@2@@Z",
"public: class std::basic_istream<char,struct std::char_traits<char> >
& __thiscall std::basic_istream<char,struct std::char_traits<char>
>::seekg(long,enum std::ios_base::seekdir)"},
/* 64 */
{"?seekg@?$basic_istream@DU?$char_traits@D@std@@@std@@QAEAAV12@V?$fpos@H@2@@Z",
"public: class std::basic_istream<char,struct std::char_traits<char> >
& __thiscall std::basic_istream<char,struct std::char_traits<char>
>::seekg(class std::fpos<int>)"},
@@ -1325,22 +1300,54 @@ static void test_demangle(void)
"??$run@XVTask_Render_Preview@@@QtConcurrent@@YA?AV?$QFuture@X@@PEAVTask_Render_Preview@@P82@EAAXXZ@Z"},
/* 130 */ {"??_E?$TStrArray@$$BY0BAA@D$0BA@@@UAEPAXI@Z",
"public: virtual void * __thiscall TStrArray<char
[256],16>::`vector deleting destructor'(unsigned int)"},
+/* 131 */ {"??_R0?AVCC@DD@@@8", "class DD::CC `RTTI Type
Descriptor'"},
+/* 132 */ {"??$meth@FD@DD@CC@@QAE_NK@Z", "public: bool __thiscall
CC::DD::meth<short,char>(unsigned long)"},
+/* 133 */ {"?func@@YAXPIFAH@Z", "void __cdecl func(int __unaligned *
__restrict)"},
+/* 135 */ {"?x@@3PAY02HA", "int (* x)[3]"},
+/* 136 */ {"?Qux@Bar@@0PAPAP6AHPAV1@AAH1PAH@ZA",
+ "private: static int (__cdecl** * Bar::Qux)(class Bar *,int &,int
&,int *)"}, /* variation of 105: note white space handling! */
+/* 137 */ {"?x@@3PAW4myenum@@A", "enum myenum * x"},
+/* 138 */ {"?pfunc@@3PAY0E@P6AXF@ZA", "void (__cdecl*(*
pfunc)[4])(short)"},
+/* 139 */
{"??$?0AEAVzzz@BB4@AA@@AEAV012@$0A@@?$pair@Vzzz@BB4@AA@@V123@@std@@QEAA@AEAVzzz@BB4@AA@@0@Z",
+ "public: __cdecl std::pair<class AA::BB4::zzz,class
AA::BB4::zzz>::pair<class AA::BB4::zzz,class AA::BB4::zzz><class AA::BB4::zzz
& __ptr64,class AA::BB4::zzz & __ptr64,0>(class AA::BB4::zzz &
__ptr64,class AA::BB4::zzz & __ptr64) __ptr64"},
+/* 140 */ {"??$?BH@?$foo@N@@QEAAHXZ", "public: __cdecl
foo<double>::operator<int> int(void) __ptr64"},
+/* 141 */ {"??Bcastop@@QAEHXZ", "public: __thiscall castop::operator
int(void)"},
+/* 142 */ {"??Bcastop@@QAE?BHXZ", "public: __thiscall castop::operator int
const (void)"},
+/* 143 */ {"?pfield@@3PTAA@@DT1@", "char const volatile AA::* const
volatile pfield"},
+/* 144 */ {"?ptititi1@@3PEQtititi@@IEQ1@", "unsigned int tititi::* __ptr64
__ptr64 ptititi1"},
+/* 145 */ {"?ptititi2@@3PERtititi@@IER1@", "unsigned int const tititi::*
__ptr64 const __ptr64 ptititi2"},
+/* 146 */ {"?ptititi3@@3PEStititi@@IES1@", "unsigned int volatile
tititi::* __ptr64 volatile __ptr64 ptititi3"},
+/* 147 */ {"?ptititi4@@3PETtititi@@IET1@", "unsigned int const volatile
tititi::* __ptr64 const volatile __ptr64 ptititi4"},
+/* 148 */ {"?ptititi4v@@3RETtititi@@IET1@", "unsigned int const volatile
tititi::* __ptr64 const volatile __ptr64 ptititi4v"},
+/* 149 */ {"?meth@AAA@@QFCEXXZ", "public: void __thiscall
AAA::meth(void)volatile __unaligned "},
+/* 150 */
{"?RegisterModuleUninitializer@<CrtImplementationDetails>@@YAXP$AAVEventHandler@System@@@Z",
+ "void __cdecl
<CrtImplementationDetails>::RegisterModuleUninitializer(class System::EventHandler
^)"},
+/* 151 */
{"?RegisterModuleUninitializer@<CrtImplementationDetails>@@YAXBE$AAVEventHandler@System@@@Z",
+ "void __cdecl
<CrtImplementationDetails>::RegisterModuleUninitializer(class System::EventHandler %
__ptr64 volatile)"},
+/* 152 */
{"??$forward@AEAUFFIValue@?1??call@FFIFunctionBinder@@CAHPEAUlua_State@@@Z@@std@@YAAEAUFFIValue@?1??call@"
+ "FFIFunctionBinder@@CAHPEAUxlua_State@@@Z@AEAU1?1??23@CAH0@Z@@Z",
+ "struct `private: static int __cdecl FFIFunctionBinder::call(struct
xlua_State * __ptr64)'::`2'::FFIValue & "
+ "__ptr64 __cdecl std::forward<struct `private: static int __cdecl
FFIFunctionBinder::call(struct lua_State "
+ "* __ptr64)'::`2'::FFIValue & __ptr64>(struct `private:
static int __cdecl FFIFunctionBinder::call(struct "
+ "xlua_State * __ptr64)'::`2'::FFIValue & __ptr64)"},
+/* 153 */ {"?$AAA@XX", "AAA<void,void>"},
+/* 154 */ {"?$AAA@", "AAA<>"},
};
- int i, num_test = ARRAY_SIZE(test);
+ int i;
char* name;
- for (i = 0; i < num_test; i++)
+ for (i = 0; i < ARRAY_SIZE(test); i++)
{
- name = p__unDName(0, test[i].in, 0, pmalloc, pfree, test[i].flags);
+ name = p__unDName(0, test[i].in, 0, malloc, free, test[i].flags);
ok(name != NULL, "%u: unDName failed\n", i);
if (!name) continue;
- ok( !strcmp_space(test[i].out, name) ||
- broken(test[i].broken && !strcmp_space(test[i].broken, name)),
+ ok( !strcmp(test[i].out, name) ||
+ broken(test[i].broken && !strcmp(test[i].broken, name)),
"%u: Got name \"%s\"\n", i, name );
- ok( !strcmp_space(test[i].out, name) ||
- broken(test[i].broken && !strcmp_space(test[i].broken, name)),
+ ok( !strcmp(test[i].out, name) ||
+ broken(test[i].broken && !strcmp(test[i].broken, name)),
"%u: Expected \"%s\"\n", i, test[i].out );
- pfree(name);
+ free(name);
}
}
diff --git a/modules/rostests/winetests/msvcrt/data.c
b/modules/rostests/winetests/msvcrt/data.c
index b0acc60b20b..b78bc4f7029 100644
--- a/modules/rostests/winetests/msvcrt/data.c
+++ b/modules/rostests/winetests/msvcrt/data.c
@@ -32,7 +32,11 @@
#include <errno.h>
#include <direct.h>
-void __cdecl __getmainargs(int *, char ***, char ***, int, int *);
+#ifdef __REACTOS__
+_CRTIMP void __cdecl __getmainargs(int *, char ***, char ***, int, int *);
+_CRTIMP void __cdecl __wgetmainargs(int *, wchar_t ***, wchar_t ***, int, int *);
+#endif
+
static int* (__cdecl *p___p___argc)(void);
static char*** (__cdecl *p___p___argv)(void);
@@ -92,12 +96,12 @@ static void test_initvar( HMODULE hmsvcrt )
winminor = *pp_winminor;
winmajor = *pp_winmajor;
GetVersionExA( &osvi);
- ok( winminor == osvi.dwMinorVersion, "Wrong value for _winminor %02x expected
%02x\n",
+ ok( winminor == osvi.dwMinorVersion, "Wrong value for _winminor %02x expected
%02lx\n",
winminor, osvi.dwMinorVersion);
- ok( winmajor == osvi.dwMajorVersion, "Wrong value for _winmajor %02x expected
%02x\n",
+ ok( winmajor == osvi.dwMajorVersion, "Wrong value for _winmajor %02x expected
%02lx\n",
winmajor, osvi.dwMajorVersion);
ok( winver == ((osvi.dwMajorVersion << 8) | osvi.dwMinorVersion),
- "Wrong value for _winver %02x expected %02x\n",
+ "Wrong value for _winver %02x expected %02lx\n",
winver, ((osvi.dwMajorVersion << 8) | osvi.dwMinorVersion));
if( !pp_osver || !pp_osplatform ) {
win_skip("_osver variables are not available\n");
@@ -108,10 +112,10 @@ static void test_initvar( HMODULE hmsvcrt )
ok( osver == (osvi.dwBuildNumber & 0xffff) ||
((osvi.dwBuildNumber >> 24) == osvi.dwMajorVersion &&
((osvi.dwBuildNumber >> 16) & 0xff) == osvi.dwMinorVersion),
/* 95/98/ME */
- "Wrong value for _osver %04x expected %04x\n",
+ "Wrong value for _osver %04x expected %04lx\n",
osver, osvi.dwBuildNumber);
ok(osplatform == osvi.dwPlatformId,
- "Wrong value for _osplatform %x expected %x\n",
+ "Wrong value for _osplatform %x expected %lx\n",
osplatform, osvi.dwPlatformId);
}
@@ -133,7 +137,7 @@ static void test___getmainargs(void)
{
int argc, new_argc, mode;
char **argv, **new_argv, **envp;
- char tmppath[MAX_PATH], filepath[MAX_PATH];
+ char tmppath[MAX_PATH], filepath[MAX_PATH + 14];
FILE *f;
ok(GetTempPathA(MAX_PATH, tmppath) != 0, "GetTempPath failed\n");
@@ -194,7 +198,7 @@ static void test___getmainargs(void)
static void test___getmainargs_parent(char *name)
{
char cmdline[3*MAX_PATH];
- char tmppath[MAX_PATH], filepath[MAX_PATH];
+ char tmppath[MAX_PATH], filepath[MAX_PATH + 14];
STARTUPINFOA startup;
PROCESS_INFORMATION proc;
FILE *f;
@@ -218,7 +222,7 @@ static void test___getmainargs_parent(char *name)
memset(&startup, 0, sizeof(startup));
startup.cb = sizeof(startup);
CreateProcessA(NULL, cmdline, NULL, NULL, TRUE,
CREATE_DEFAULT_ERROR_MODE|NORMAL_PRIORITY_CLASS, NULL, NULL, &startup, &proc);
- winetest_wait_child_process(proc.hProcess);
+ wait_child_process(proc.hProcess);
_unlink(filepath);
sprintf(filepath, "%swine_test\\a", tmppath);
diff --git a/modules/rostests/winetests/msvcrt/dir.c
b/modules/rostests/winetests/msvcrt/dir.c
index 210cf3983cd..a2a704d85d3 100644
--- a/modules/rostests/winetests/msvcrt/dir.c
+++ b/modules/rostests/winetests/msvcrt/dir.c
@@ -138,36 +138,6 @@ static void test_makepath(void)
}
}
-static const WCHAR expected0[] =
{'\0','X','X','X','X','X','X','X','X','X','X','X','X'};
-static const WCHAR expected1[] =
{'\0','X','X','X','X','X','X','X','X','X','X','X','X'};
-static const WCHAR expected2[] =
{'\0',':','X','X','X','X','X','X','X','X','X','X','X'};
-static const WCHAR expected3[] =
{'\0',':','d','X','X','X','X','X','X','X','X','X','X'};
-static const WCHAR expected4[] =
{'\0',':','d','\\','X','X','X','X','X','X','X','X','X'};
-static const WCHAR expected5[] =
{'\0',':','d','\\','f','X','X','X','X','X','X','X','X'};
-static const WCHAR expected6[] =
{'\0',':','d','\\','f','i','X','X','X','X','X','X','X'};
-static const WCHAR expected7[] =
{'\0',':','d','\\','f','i','l','X','X','X','X','X','X'};
-static const WCHAR expected8[] =
{'\0',':','d','\\','f','i','l','e','X','X','X','X','X'};
-static const WCHAR expected9[] =
{'\0',':','d','\\','f','i','l','e','.','X','X','X','X'};
-static const WCHAR expected10[] =
{'\0',':','d','\\','f','i','l','e','.','e','X','X','X'};
-static const WCHAR expected11[] =
{'\0',':','d','\\','f','i','l','e','.','e','x','X','X'};
-
-static const WCHAR expected12[] =
{'\0',':','X','X','X','X','X','X','X','X'};
-static const WCHAR expected13[] =
{'\0',':','d','X','X','X','X','X','X','X'};
-static const WCHAR expected14[] =
{'\0',':','d','i','X','X','X','X','X','X'};
-static const WCHAR expected15[] =
{'\0',':','d','i','r','X','X','X','X','X'};
-static const WCHAR expected16[] =
{'\0',':','d','i','r','\\','X','X','X','X'};
-
-static const WCHAR expected17[] = {'\0','o','o'};
-static const WCHAR expected18[] =
{'\0','o','o','\0','X'};
-static const WCHAR expected19[] = {'\0','o','o','\0'};
-static const WCHAR expected20[] =
{'\0','o','o','\0','X','X','X','X','X'};
-static const WCHAR expected21[] =
{'\0','o','o','\\','f','i','l','X','X'};
-static const WCHAR expected22[] =
{'\0','o','o','\0','X','X','X','X','X','X','X','X','X'};
-static const WCHAR expected23[] =
{'\0','o','o','\\','f','i','l','X','X','X','X','X','X'};
-static const WCHAR expected24[] =
{'\0','o','o','\\','f','i','l','e','.','e','x','X','X'};
-static const WCHAR expected25[] =
{'\0','o','o','\0','X','X','X','X'};
-static const WCHAR expected26[] =
{'\0','o','o','.','e','x','X','X'};
-
typedef struct
{
const char* buffer;
@@ -184,35 +154,35 @@ typedef struct
static const makepath_s_case makepath_s_cases[] =
{
/* Behavior with directory parameter containing backslash. */
- {NULL, 1, "c:", "d\\", "file", "ext",
"\0XXXXXXXXXXXX", expected0, 13},
- {NULL, 2, "c:", "d\\", "file", "ext",
"\0XXXXXXXXXXXX", expected1, 13},
- {NULL, 3, "c:", "d\\", "file", "ext",
"\0:XXXXXXXXXXX", expected2, 13},
- {NULL, 4, "c:", "d\\", "file", "ext",
"\0:dXXXXXXXXXX", expected3, 13},
- {NULL, 5, "c:", "d\\", "file", "ext",
"\0:d\\XXXXXXXXX", expected4, 13},
- {NULL, 6, "c:", "d\\", "file", "ext",
"\0:d\\fXXXXXXXX", expected5, 13},
- {NULL, 7, "c:", "d\\", "file", "ext",
"\0:d\\fiXXXXXXX", expected6, 13},
- {NULL, 8, "c:", "d\\", "file", "ext",
"\0:d\\filXXXXXX", expected7, 13},
- {NULL, 9, "c:", "d\\", "file", "ext",
"\0:d\\fileXXXXX", expected8, 13},
- {NULL, 10, "c:", "d\\", "file", "ext",
"\0:d\\file.XXXX", expected9, 13},
- {NULL, 11, "c:", "d\\", "file", "ext",
"\0:d\\file.eXXX", expected10, 13},
- {NULL, 12, "c:", "d\\", "file", "ext",
"\0:d\\file.exXX", expected11, 13},
+ {NULL, 1, "c:", "d\\", "file", "ext",
"\0XXXXXXXXXXXX", L"\0XXXXXXXXXXXX", 13},
+ {NULL, 2, "c:", "d\\", "file", "ext",
"\0XXXXXXXXXXXX", L"\0XXXXXXXXXXXX", 13},
+ {NULL, 3, "c:", "d\\", "file", "ext",
"\0:XXXXXXXXXXX", L"\0:XXXXXXXXXXX", 13},
+ {NULL, 4, "c:", "d\\", "file", "ext",
"\0:dXXXXXXXXXX", L"\0:dXXXXXXXXXX", 13},
+ {NULL, 5, "c:", "d\\", "file", "ext",
"\0:d\\XXXXXXXXX", L"\0:d\\XXXXXXXXX", 13},
+ {NULL, 6, "c:", "d\\", "file", "ext",
"\0:d\\fXXXXXXXX", L"\0:d\\fXXXXXXXX", 13},
+ {NULL, 7, "c:", "d\\", "file", "ext",
"\0:d\\fiXXXXXXX", L"\0:d\\fiXXXXXXX", 13},
+ {NULL, 8, "c:", "d\\", "file", "ext",
"\0:d\\filXXXXXX", L"\0:d\\filXXXXXX", 13},
+ {NULL, 9, "c:", "d\\", "file", "ext",
"\0:d\\fileXXXXX", L"\0:d\\fileXXXXX", 13},
+ {NULL, 10, "c:", "d\\", "file", "ext",
"\0:d\\file.XXXX", L"\0:d\\file.XXXX", 13},
+ {NULL, 11, "c:", "d\\", "file", "ext",
"\0:d\\file.eXXX", L"\0:d\\file.eXXX", 13},
+ {NULL, 12, "c:", "d\\", "file", "ext",
"\0:d\\file.exXX", L"\0:d\\file.exXX", 13},
/* Behavior with directory parameter lacking backslash. */
- {NULL, 3, "c:", "dir", "f", "ext",
"\0:XXXXXXXX", expected12, 10},
- {NULL, 4, "c:", "dir", "f", "ext",
"\0:dXXXXXXX", expected13, 10},
- {NULL, 5, "c:", "dir", "f", "ext",
"\0:diXXXXXX", expected14, 10},
- {NULL, 6, "c:", "dir", "f", "ext",
"\0:dirXXXXX", expected15, 10},
- {NULL, 7, "c:", "dir", "f", "ext",
"\0:dir\\XXXX", expected16, 10},
+ {NULL, 3, "c:", "dir", "f", "ext",
"\0:XXXXXXXX", L"\0:XXXXXXXX", 10},
+ {NULL, 4, "c:", "dir", "f", "ext",
"\0:dXXXXXXX", L"\0:dXXXXXXX", 10},
+ {NULL, 5, "c:", "dir", "f", "ext",
"\0:diXXXXXX", L"\0:diXXXXXX", 10},
+ {NULL, 6, "c:", "dir", "f", "ext",
"\0:dirXXXXX", L"\0:dirXXXXX", 10},
+ {NULL, 7, "c:", "dir", "f", "ext",
"\0:dir\\XXXX", L"\0:dir\\XXXX", 10},
/* Behavior with overlapped buffer. */
- {"foo", 2, USE_BUFF, NULL, NULL, NULL, "\0oo", expected17, 3},
- {"foo", 4, NULL, USE_BUFF, NULL, NULL, "\0oo\0X", expected18,
5},
- {"foo", 3, NULL, NULL, USE_BUFF, NULL, "\0oo\0", expected19, 4},
- {"foo", 4, NULL, USE_BUFF, "file", NULL, "\0oo\0XXXXX",
expected20, 9},
- {"foo", 8, NULL, USE_BUFF, "file", NULL, "\0oo\\filXX",
expected21, 9},
- {"foo", 4, NULL, USE_BUFF, "file", "ext",
"\0oo\0XXXXXXXXX", expected22, 13},
- {"foo", 8, NULL, USE_BUFF, "file", "ext",
"\0oo\\filXXXXXX", expected23, 13},
- {"foo", 12, NULL, USE_BUFF, "file", "ext",
"\0oo\\file.exXX", expected24, 13},
- {"foo", 4, NULL, NULL, USE_BUFF, "ext", "\0oo\0XXXX",
expected25, 8},
- {"foo", 7, NULL, NULL, USE_BUFF, "ext", "\0oo.exXX",
expected26, 8},
+ {"foo", 2, USE_BUFF, NULL, NULL, NULL, "\0oo", L"\0oo",
3},
+ {"foo", 4, NULL, USE_BUFF, NULL, NULL, "\0oo\0X",
L"\0oo\0X", 5},
+ {"foo", 3, NULL, NULL, USE_BUFF, NULL, "\0oo\0",
L"\0oo", 4},
+ {"foo", 4, NULL, USE_BUFF, "file", NULL, "\0oo\0XXXXX",
L"\0oo\0XXXXX", 9},
+ {"foo", 8, NULL, USE_BUFF, "file", NULL, "\0oo\\filXX",
L"\0oo\\filXX", 9},
+ {"foo", 4, NULL, USE_BUFF, "file", "ext",
"\0oo\0XXXXXXXXX", L"\0oo\0XXXXXXXXX", 13},
+ {"foo", 8, NULL, USE_BUFF, "file", "ext",
"\0oo\\filXXXXXX", L"\0oo\\filXXXXXX", 13},
+ {"foo", 12, NULL, USE_BUFF, "file", "ext",
"\0oo\\file.exXX", L"\0oo\\file.exXX", 13},
+ {"foo", 4, NULL, NULL, USE_BUFF, "ext", "\0oo\0XXXX",
L"\0oo\0XXXX", 8},
+ {"foo", 7, NULL, NULL, USE_BUFF, "ext", "\0oo.exXX",
L"\0oo.exXX", 8},
};
static void test_makepath_s(void)
@@ -438,10 +408,6 @@ static void test_searchenv(void)
"\\search_env_test\\dir3longer\\3.dat"
};
- const WCHAR env_w[] =
{'T','E','S','T','_','P','A','T','H',0};
- const WCHAR dat1_w[] =
{'1','.','d','a','t',0};
- const WCHAR dat3_w[] =
{'3','.','d','a','t',0};
-
char env1[4*MAX_PATH], env2[4*MAX_PATH], tmppath[MAX_PATH], path[2*MAX_PATH];
char result[MAX_PATH], exp[2*MAX_PATH];
WCHAR result_w[MAX_PATH];
@@ -510,13 +476,13 @@ static void test_searchenv(void)
}
memset(result_w, 'x', sizeof(result_w));
- _wsearchenv(dat1_w, env_w, result_w);
+ _wsearchenv(L"1.dat", L"TEST_PATH", result_w);
WideCharToMultiByte(CP_ACP, 0, result_w, -1, result, MAX_PATH, NULL, NULL);
ok(!strcmp(result, exp), "got %s, expected '%s'\n", result, exp);
if (p_wsearchenv_s) {
memset(result_w, 'x', sizeof(result_w));
- i = p_wsearchenv_s(dat1_w, env_w, result_w, MAX_PATH);
+ i = p_wsearchenv_s(L"1.dat", L"TEST_PATH", result_w,
MAX_PATH);
ok(!i, "wsearchenv_s returned %d\n", i);
ok(!strcmp(result, exp), "got %s, expected '%s'\n", result,
exp);
}
@@ -535,13 +501,13 @@ static void test_searchenv(void)
}
memset(result_w, 'x', sizeof(result_w));
- _wsearchenv(dat3_w, env_w, result_w);
+ _wsearchenv(L"3.dat", L"TEST_PATH", result_w);
WideCharToMultiByte(CP_ACP, 0, result_w, -1, result, MAX_PATH, NULL, NULL);
ok(!strcmp(result, exp), "got %s, expected '%s'\n", result, exp);
if (p_wsearchenv_s) {
memset(result_w, 'x', sizeof(result_w));
- i = p_wsearchenv_s(dat3_w, env_w, result_w, MAX_PATH);
+ i = p_wsearchenv_s(L"3.dat", L"TEST_PATH", result_w,
MAX_PATH);
ok(!i, "wsearchenv_s returned %d\n", i);
ok(!strcmp(result, exp), "got %s, expected '%s'\n", result,
exp);
}
@@ -561,13 +527,13 @@ static void test_searchenv(void)
}
memset(result_w, 'x', sizeof(result_w));
- _wsearchenv(dat1_w, env_w, result_w);
+ _wsearchenv(L"1.dat", L"TEST_PATH", result_w);
WideCharToMultiByte(CP_ACP, 0, result_w, -1, result, MAX_PATH, NULL, NULL);
ok(!strcmp(result, exp), "got %s, expected '%s'\n", result, exp);
if (p_wsearchenv_s) {
memset(result_w, 'x', sizeof(result_w));
- i = p_wsearchenv_s(dat1_w, env_w, result_w, MAX_PATH);
+ i = p_wsearchenv_s(L"1.dat", L"TEST_PATH", result_w,
MAX_PATH);
ok(!i, "wsearchenv_s returned %d\n", i);
ok(!strcmp(result, exp), "got %s, expected '%s'\n", result,
exp);
}
@@ -586,17 +552,31 @@ static void test_searchenv(void)
}
memset(result_w, 'x', sizeof(result_w));
- _wsearchenv(dat3_w, env_w, result_w);
+ _wsearchenv(L"3.dat", L"TEST_PATH", result_w);
WideCharToMultiByte(CP_ACP, 0, result_w, -1, result, MAX_PATH, NULL, NULL);
ok(!strcmp(result, exp), "got %s, expected '%s'\n", result, exp);
if (p_wsearchenv_s) {
memset(result_w, 'x', sizeof(result_w));
- i = p_wsearchenv_s(dat3_w, env_w, result_w, MAX_PATH);
+ i = p_wsearchenv_s(L"3.dat", L"TEST_PATH", result_w,
MAX_PATH);
ok(!i, "wsearchenv_s returned %d\n", i);
ok(!strcmp(result, exp), "got %s, expected '%s'\n", result,
exp);
}
+ strcpy(env1, "TEST_PATH=");
+ strcat(env1, tmppath);
+ strcat(env1,
"\"\\search_env_test\\\"d\"i\"r\"1");
+ putenv(env1);
+ strcpy(exp, tmppath);
+ strcat(exp, files[0]);
+ _searchenv("1.dat", "TEST_PATH", result);
+ ok(!strcmp(result, exp), "got %s, expected '%s'\n", result, exp);
+
+ strcat(env1, ";");
+ putenv(env1);
+ _searchenv("1.dat", "TEST_PATH", result);
+ ok(!result[0], "got %s, expected ''\n", result);
+
putenv("TEST_PATH=");
for (i=ARRAY_SIZE(files)-1; i>=0; i--) {
diff --git a/modules/rostests/winetests/msvcrt/environ.c
b/modules/rostests/winetests/msvcrt/environ.c
index b8e0ae6251a..9951c5b1308 100644
--- a/modules/rostests/winetests/msvcrt/environ.c
+++ b/modules/rostests/winetests/msvcrt/environ.c
@@ -19,7 +19,15 @@
*/
#include "wine/test.h"
+#include <errno.h>
#include <stdlib.h>
+#include <process.h>
+#include <winnls.h>
+
+#ifdef __REACTOS__
+_CRTIMP void __cdecl __getmainargs(int *, char ***, char ***, int, int *);
+_CRTIMP void __cdecl __wgetmainargs(int *, wchar_t ***, wchar_t ***, int, int *);
+#endif
static const char *a_very_long_env_string =
"LIBRARY_PATH="
@@ -42,13 +50,15 @@ static const char *a_very_long_env_string =
"/usr/lib/mingw32/3.4.2/;"
"/usr/lib/";
-void __cdecl __getmainargs(int *, char ***, char ***, int, int *);
-void __cdecl __wgetmainargs(int *, wchar_t ***, wchar_t ***, int, int *);
-
static char ***(__cdecl *p__p__environ)(void);
static WCHAR ***(__cdecl *p__p__wenviron)(void);
-static void (*p_get_environ)(char ***);
-static void (*p_get_wenviron)(WCHAR ***);
+static char ***(__cdecl *p__p___initenv)(void);
+static wchar_t ***(__cdecl *p__p___winitenv)(void);
+static void (__cdecl *p_get_environ)(char ***);
+static void (__cdecl *p_get_wenviron)(WCHAR ***);
+static errno_t (__cdecl *p_putenv_s)(const char*, const char*);
+static errno_t (__cdecl *p_wputenv_s)(const wchar_t*, const wchar_t*);
+static errno_t (__cdecl *p_getenv_s)(size_t*, char*, size_t, const char*);
static char ***p_environ;
static WCHAR ***p_wenviron;
@@ -59,10 +69,15 @@ static void init(void)
p__p__environ = (void *)GetProcAddress(hmod, "__p__environ");
p__p__wenviron = (void *)GetProcAddress(hmod, "__p__wenviron");
+ p__p___initenv = (void *)GetProcAddress(hmod, "__p___initenv");
+ p__p___winitenv = (void *)GetProcAddress(hmod, "__p___winitenv");
p_environ = (void *)GetProcAddress(hmod, "_environ");
p_wenviron = (void *)GetProcAddress(hmod, "_wenviron");
p_get_environ = (void *)GetProcAddress(hmod, "_get_environ");
p_get_wenviron = (void *)GetProcAddress(hmod, "_get_wenviron");
+ p_putenv_s = (void *)GetProcAddress(hmod, "_putenv_s");
+ p_wputenv_s = (void *)GetProcAddress(hmod, "_wputenv_s");
+ p_getenv_s = (void *)GetProcAddress(hmod, "getenv_s");
}
static void test_system(void)
@@ -74,30 +89,46 @@ static void test_system(void)
ok(ret == 0, "Expected system to return 0, got %d\n", ret);
}
-static void test__environ(void)
+static unsigned env_get_entry_countA( char **env )
{
- int argc;
- char **argv, **envp = NULL;
- int i, mode = 0;
+ unsigned count;
- ok( p_environ != NULL, "Expected the pointer to _environ to be non-NULL\n"
);
- if (p_environ)
- ok( *p_environ != NULL, "Expected _environ to be initialized on
startup\n" );
+ if (!env) return 0;
+ for (count = 0; env[count] != NULL; count++) {}
+ return count;
+}
- if (!p_environ || !*p_environ)
- {
- skip( "_environ pointers are not valid\n" );
- return;
- }
+static wchar_t *env_get_valueW( wchar_t **envp, const wchar_t *var )
+{
+ unsigned i;
+ size_t len = wcslen( var );
- /* Examine the returned pointer from __p__environ(), if available. */
- if (p__p__environ)
+ if (!envp) return NULL;
+ for (i = 0; envp[i] != NULL; i++)
{
- ok( *p__p__environ() == *p_environ,
- "Expected _environ pointers to be identical\n" );
+ wchar_t *ptr;
+
+ if (!(ptr = wcschr( envp[i], L'=' ))) continue;
+
+ if (ptr - envp[i] == len && !memcmp( envp[i], var, len * sizeof(wchar_t)
))
+ return ptr + 1;
}
+ return NULL;
+}
+
+static void test__environ(void)
+{
+ int argc;
+ char **argv, **envp = NULL, **initenv = NULL;
+ int mode = 0;
+
+ ok( p_environ != NULL, "Expected the pointer to _environ to be non-NULL\n"
);
+ ok( *p_environ != NULL, "Expected _environ to be initialized on startup\n"
);
+
+ if (sizeof(void*) != sizeof(int))
+ ok( !p__p__environ, "__p__environ() should be 32-bit only\n");
else
- skip( "__p__environ() is not available\n" );
+ ok( *p__p__environ() == *p_environ, "Expected _environ pointers to be
identical\n" );
if (p_get_environ)
{
@@ -109,76 +140,74 @@ static void test__environ(void)
else
win_skip( "_get_environ() is not available\n" );
+ if (p__p___initenv)
+ {
+ initenv = *p__p___initenv();
+
+ ok( initenv == *p_environ,
+ "Expected _environ to be equal to initial env\n" );
+ }
+ else
+ skip( "__p___initenv() is not available\n" );
+
/* Note that msvcrt from Windows versions older than Vista
* expects the mode pointer parameter to be valid.*/
__getmainargs(&argc, &argv, &envp, 0, &mode);
- ok( envp != NULL, "Expected initial environment block pointer to be
non-NULL\n" );
- if (!envp)
- {
- skip( "Initial environment block pointer is not valid\n" );
- return;
- }
+ ok( envp != NULL,
+ "Expected initial environment block pointer to be non-NULL\n" );
+ ok( envp == *p_environ,
+ "Expected initial environment to be equal to _environ\n" );
- for (i = 0; ; i++)
+ ok( _putenv("cat=dog") == 0, "failed setting cat=dog\n" );
+ if (p__p___initenv)
{
- if ((*p_environ)[i])
- {
- ok( envp[i] != NULL, "Expected environment block pointer element to be
non-NULL\n" );
- ok( !strcmp((*p_environ)[i], envp[i]),
- "Expected _environ and environment block pointer strings (%s vs. %s)
to match\n",
- (*p_environ)[i], envp[i] );
- }
- else
- {
- ok( !envp[i], "Expected environment block pointer element to be NULL,
got %p\n", envp[i] );
- break;
- }
+ char **retptr = *p__p___initenv();
+
+ ok( retptr != *p_environ,
+ "Expected _environ[] not to be equal to initial env\n" );
+ ok( retptr == initenv,
+ "Unexpected modification of initial env\n" );
}
+ ok( _putenv("cat=") == 0, "failed setting cat=\n" );
}
static void test__wenviron(void)
{
- static const WCHAR cat_eq_dogW[] =
{'c','a','t','=','d','o','g',0};
- static const WCHAR cat_eqW[] = {'c','a','t','=',0};
-
int argc;
char **argv, **envp = NULL;
WCHAR **wargv, **wenvp = NULL;
- int i, mode = 0;
+ int mode = 0;
ok( p_wenviron != NULL, "Expected the pointer to _wenviron to be
non-NULL\n" );
- if (p_wenviron)
- ok( *p_wenviron == NULL, "Expected _wenviron to be NULL, got %p\n",
*p_wenviron );
- else
- {
- win_skip( "Pointer to _wenviron is not valid\n" );
- return;
- }
+ ok( !*p_wenviron, "Expected _wenviron[] to be NULL, got %p\n", *p_wenviron
);
- /* Examine the returned pointer from __p__wenviron(), if available. */
- if (p__p__wenviron)
- {
- ok( *p__p__wenviron() == NULL,
- "Expected _wenviron pointers to be NULL\n" );
- }
+ if (sizeof(void*) != sizeof(int))
+ ok( !p__p__wenviron, "__p__wenviron() should be 32-bit only\n");
else
- skip( "__p__wenviron() is not available\n" );
+ ok( !*p__p__wenviron(), "Expected _wenviron to be NULL, got %p\n",
*p_wenviron );
if (p_get_wenviron)
{
WCHAR **retptr;
p_get_wenviron(&retptr);
- ok( retptr == NULL,
- "Expected _wenviron pointers to be NULL\n" );
+ ok( retptr == *p_wenviron, "Expected _wenviron pointers to be NULL\n"
);
}
else
win_skip( "_get_wenviron() is not available\n" );
+ if (p__p___winitenv)
+ {
+ wchar_t ***retptr = p__p___winitenv();
+ ok( !*retptr, "Expected initial env to be NULL\n" );
+ }
+ else
+ skip( "__p___winitenv() is not available\n" );
+
/* __getmainargs doesn't initialize _wenviron. */
__getmainargs(&argc, &argv, &envp, 0, &mode);
- ok( *p_wenviron == NULL, "Expected _wenviron to be NULL, got %p\n",
*p_wenviron);
+ ok( !*p_wenviron, "Expected _wenviron to be NULL\n");
ok( envp != NULL, "Expected initial environment block pointer to be
non-NULL\n" );
if (!envp)
{
@@ -188,24 +217,31 @@ static void test__wenviron(void)
/* Neither does calling the non-Unicode environment manipulation functions. */
ok( _putenv("cat=dog") == 0, "failed setting cat=dog\n" );
- ok( *p_wenviron == NULL, "Expected _wenviron to be NULL, got %p\n",
*p_wenviron);
- ok( _putenv("cat=") == 0, "failed deleting cat\n" );
+ ok( !*p_wenviron, "Expected _wenviron to be NULL\n" );
/* _wenviron isn't initialized until __wgetmainargs is called or
* one of the Unicode environment manipulation functions is called. */
- ok( _wputenv(cat_eq_dogW) == 0, "failed setting cat=dog\n" );
+ ok( _wputenv(L"cat=dog2") == 0, "failed setting cat=dog2\n" );
ok( *p_wenviron != NULL, "Expected _wenviron to be non-NULL\n" );
- ok( _wputenv(cat_eqW) == 0, "failed deleting cat\n" );
__wgetmainargs(&argc, &wargv, &wenvp, 0, &mode);
-
- ok( *p_wenviron != NULL, "Expected _wenviron to be non-NULL\n" );
ok( wenvp != NULL, "Expected initial environment block pointer to be
non-NULL\n" );
- if (!wenvp)
+ ok( wenvp == *p_wenviron, "Expected initial environment to be
_wenviron[]\n" );
+
+ if (p__p___winitenv)
{
- skip( "Initial environment block pointer is not valid\n" );
- return;
+ wchar_t ***retptr = p__p___winitenv();
+ wchar_t *value;
+
+ ok( *retptr != NULL, "Expected *__p___winitenv() to be NULL\n" );
+ ok( *retptr != *p_wenviron,
+ "Expected _wenviron to be different from __p___winitenv() %p %p\n",
*retptr, *p_wenviron );
+ /* test that w-initial env is derived from current _environ[] and not from ansi
initial env */
+ value = env_get_valueW( *retptr, L"cat" );
+ ok( value && !wcscmp( value, L"dog" ),
+ "Expecting initial env to be derived from current env (got
%ls)\n", value );
}
+ _putenv("cat=");
/* Examine the returned pointer from __p__wenviron(),
* if available, after _wenviron is initialized. */
@@ -222,29 +258,27 @@ static void test__wenviron(void)
ok( retptr == *p_wenviron,
"Expected _wenviron pointers to be identical\n" );
}
-
- for (i = 0; ; i++)
- {
- if ((*p_wenviron)[i])
- {
- ok( wenvp[i] != NULL, "Expected environment block pointer element to be
non-NULL\n" );
- ok( !winetest_strcmpW((*p_wenviron)[i], wenvp[i]),
- "Expected _wenviron and environment block pointer strings (%s vs.
%s) to match\n",
- wine_dbgstr_w((*p_wenviron)[i]), wine_dbgstr_w(wenvp[i]) );
- }
- else
- {
- ok( !wenvp[i], "Expected environment block pointer element to be NULL,
got %p\n", wenvp[i] );
- break;
- }
- }
}
static void test_environment_manipulation(void)
{
+ char buf[256];
+ errno_t ret;
+ size_t len;
+ unsigned count;
+ char* first;
+ char* second;
+
ok( _putenv("cat=") == 0, "_putenv failed on deletion of nonexistent
environment variable\n" );
ok( _putenv("cat=dog") == 0, "failed setting cat=dog\n" );
ok( strcmp(getenv("cat"), "dog") == 0, "getenv did not
return 'dog'\n" );
+ if (p_getenv_s)
+ {
+ ret = p_getenv_s(&len, buf, sizeof(buf), "cat");
+ ok( !ret, "getenv_s returned %d\n", ret );
+ ok( len == 4, "getenv_s returned length is %Id\n", len);
+ ok( !strcmp(buf, "dog"), "getenv_s did not return
'dog'\n");
+ }
ok( _putenv("cat=") == 0, "failed deleting cat\n" );
ok( _putenv("=") == -1, "should not accept '=' as
input\n" );
@@ -252,16 +286,190 @@ static void test_environment_manipulation(void)
ok( _putenv(a_very_long_env_string) == 0, "_putenv failed for long environment
string\n");
ok( getenv("nonexistent") == NULL, "getenv should fail with
nonexistent var name\n" );
+
+ if (p_putenv_s)
+ {
+ ret = p_putenv_s(NULL, "dog");
+ ok( ret == EINVAL, "_putenv_s returned %d\n", ret);
+ ret = p_putenv_s("cat", NULL);
+ ok( ret == EINVAL, "_putenv_s returned %d\n", ret);
+ ret = p_putenv_s("a=b", NULL);
+ ok( ret == EINVAL, "_putenv_s returned %d\n", ret);
+ ret = p_putenv_s("cat", "a=b");
+ ok( !ret, "_putenv_s returned %d\n", ret);
+ ret = p_putenv_s("cat", "");
+ ok( !ret, "_putenv_s returned %d\n", ret);
+ }
+
+ if (p_wputenv_s)
+ {
+ ret = p_wputenv_s(NULL, L"dog");
+ ok( ret == EINVAL, "_wputenv_s returned %d\n", ret);
+ ret = p_wputenv_s(L"cat", NULL);
+ ok( ret == EINVAL, "_wputenv_s returned %d\n", ret);
+ ret = p_wputenv_s(L"a=b", NULL);
+ ok( ret == EINVAL, "_wputenv_s returned %d\n", ret);
+ ret = p_wputenv_s(L"cat", L"a=b");
+ ok( !ret, "_wputenv_s returned %d\n", ret);
+ ret = p_wputenv_s(L"cat", L"");
+ ok( !ret, "_wputenv_s returned %d\n", ret);
+ }
+
+ if (p_getenv_s)
+ {
+ buf[0] = 'x';
+ len = 1;
+ errno = 0xdeadbeef;
+ ret = p_getenv_s(&len, buf, sizeof(buf), "nonexistent");
+ ok( !ret, "_getenv_s returned %d\n", ret);
+ ok( !len, "getenv_s returned length is %Id\n", len);
+ ok( !buf[0], "buf = %s\n", buf);
+ ok( errno == 0xdeadbeef, "errno = %d\n", errno);
+
+ buf[0] = 'x';
+ len = 1;
+ errno = 0xdeadbeef;
+ ret = p_getenv_s(&len, buf, sizeof(buf), NULL);
+ ok( !ret, "_getenv_s returned %d\n", ret);
+ ok( !len, "getenv_s returned length is %Id\n", len);
+ ok( !buf[0], "buf = %s\n", buf);
+ ok( errno == 0xdeadbeef, "errno = %d\n", errno);
+ }
+
+ /* test stability of _environ[] pointers */
+ ok( _putenv( "__winetest_cat=" ) == 0, "Couldn't reset env
var\n" );
+ ok( _putenv( "__winetest_dog=" ) == 0, "Couldn't reset env
var\n" );
+ count = env_get_entry_countA( *p_environ );
+ ok( _putenv( "__winetest_cat=mew") == 0, "Couldn't set env
var\n" );
+ ok( !strcmp( (*p_environ)[count], "__winetest_cat=mew"), "Unexpected
env var value\n" );
+ first = (*p_environ)[count];
+ ok( getenv("__winetest_cat") == strchr( (*p_environ)[count], '=') +
1, "Expected getenv() to return pointer inside _environ[] entry\n" );
+ ok( _putenv( "__winetest_dog=bark" ) == 0, "Couldn't set env
var\n" );
+ ok( !strcmp( (*p_environ)[count + 1], "__winetest_dog=bark" ),
"Unexpected env var value\n" );
+ ok( getenv( "__winetest_dog" ) == strchr( (*p_environ)[count + 1],
'=' ) + 1, "Expected getenv() to return pointer inside _environ[]
entry\n" );
+ ok( first == (*p_environ)[count], "Expected stability of _environ[count]
pointer\n" );
+ second = (*p_environ)[count + 1];
+ ok( count + 2 == env_get_entry_countA( *p_environ ), "Unexpected count\n"
);
+
+ ok( _putenv( "__winetest_cat=purr" ) == 0, "Couldn't set env
var\n" );
+ ok( !strcmp( (*p_environ)[count], "__winetest_cat=purr" ), "Unexpected
env var value\n" );
+ ok( getenv( "__winetest_cat" ) == strchr( (*p_environ)[count], '='
) + 1, "Expected getenv() to return pointer inside _environ[] entry\n" );
+ ok( second == (*p_environ)[count + 1], "Expected stability of _environ[count]
pointer\n" );
+ ok( !strcmp( (*p_environ)[count + 1], "__winetest_dog=bark" ),
"Couldn't get env var value\n" );
+ ok( getenv( "__winetest_dog" ) == strchr( (*p_environ)[count + 1],
'=' ) + 1, "Expected getenv() to return pointer inside _environ[]
entry\n" );
+ ok( count + 2 == env_get_entry_countA( *p_environ ), "Unexpected count\n"
);
+ ok( _putenv( "__winetest_cat=" ) == 0, "Couldn't reset env
vat\n" );
+ ok( second == (*p_environ)[count], "Expected _environ[count] to be
second\n" );
+ ok( !strcmp( (*p_environ)[count], "__winetest_dog=bark" ), "Unexpected
env var value\n" );
+ ok( count + 1 == env_get_entry_countA( *p_environ ), "Unexpected count\n"
);
+ ok( _putenv( "__winetest_dog=" ) == 0, "Couldn't reset env
var\n" );
+ ok( count == env_get_entry_countA( *p_environ ), "Unexpected count\n" );
+
+ /* in putenv, only changed variable is updated (no other reload of kernel info is
done) */
+ ret = SetEnvironmentVariableA( "__winetest_cat", "meow" );
+ ok( ret, "SetEnvironmentVariableA failed: %lu\n", GetLastError() );
+ ok( _putenv( "__winetest_dog=bark" ) == 0, "Couldn't set env
var\n" );
+ ok( getenv( "__winetest_cat" ) == NULL, "msvcrt env cache
shouldn't have been updated\n" );
+ ok( _putenv( "__winetest_cat=" ) == 0, "Couldn't reset env
var\n" );
+ ok( _putenv( "__winetest_dog=" ) == 0, "Couldn't reset env
var\n" );
+
+ /* test setting unicode bits */
+ count = env_get_entry_countA( *p_environ );
+ ret = WideCharToMultiByte( CP_ACP, 0, L"\u263a", -1, buf, ARRAY_SIZE(buf),
0, 0 );
+ ok( ret, "WideCharToMultiByte failed: %lu\n", GetLastError() );
+ ok( _wputenv( L"__winetest_cat=\u263a" ) == 0, "Couldn't set env
var\n" );
+ ok( _wgetenv( L"__winetest_cat" ) && !wcscmp( _wgetenv(
L"__winetest_cat" ), L"\u263a" ), "Couldn't retrieve env
var\n" );
+ ok( getenv( "__winetest_cat" ) && !strcmp( getenv(
"__winetest_cat" ), buf ), "Couldn't retrieve env var\n" );
+ ok( _wputenv( L"__winetest_cat=" ) == 0, "Couldn't reset env
var\n" );
+
+ ret = WideCharToMultiByte( CP_ACP, 0, L"__winetest_\u263a", -1, buf,
ARRAY_SIZE(buf), 0, 0 );
+ ok( ret, "WideCharToMultiByte failed: %lu\n", GetLastError() );
+ ok( _wputenv( L"__winetest_\u263a=bark" ) == 0, "Couldn't set env
var\n" );
+ ok( _wgetenv( L"__winetest_\u263a" ) && !wcscmp( _wgetenv(
L"__winetest_\u263a" ), L"bark"), "Couldn't retrieve env
var\n" );
+ ok( getenv( buf ) && !strcmp( getenv( buf ), "bark"),
"Couldn't retrieve env var %s\n", wine_dbgstr_a(buf) );
+ ok( _wputenv( L"__winetest_\u263a=" ) == 0, "Couldn't reset env
var\n" );
+ ok( count == env_get_entry_countA( *p_environ ), "Unexpected modification of
_environ[]\n" );
+}
+
+static void test_child_env(char** argv)
+{
+ STARTUPINFOA si = {sizeof(si)};
+ WCHAR *cur_env, *env, *p, *q;
+ PROCESS_INFORMATION pi;
+ char tmp[1024];
+ BOOL ret;
+ int len;
+
+ cur_env = GetEnvironmentStringsW();
+ ok( cur_env != NULL, "GetEnvironemntStrings failed\n" );
+
+ p = cur_env;
+ while (*p) p += wcslen( p ) + 1;
+ len = p - cur_env;
+ env = malloc( (len + 1024) * sizeof(*env) );
+ memcpy(env, cur_env, len * sizeof(*env) );
+ q = env + len;
+ FreeEnvironmentStringsW( cur_env );
+
+ wcscpy( q, L"__winetest_dog=bark" );
+ q += wcslen( L"__winetest_dog=bark" ) + 1;
+ wcscpy( q, L"__winetest_\u263a=\u03b2" );
+ q += wcslen( L"__winetest_\u263a=\u03b2" ) + 1;
+ *q = 0;
+
+ snprintf( tmp, sizeof(tmp), "%s %s create", argv[0], argv[1] );
+ ret = CreateProcessA( NULL, tmp, NULL, NULL, FALSE, CREATE_UNICODE_ENVIRONMENT, env,
NULL, &si, &pi );
+ ok( ret, "Couldn't create child process %s\n", tmp );
+ winetest_wait_child_process( pi.hProcess );
+ CloseHandle( pi.hProcess );
+ CloseHandle( pi.hThread );
+ free( env );
+}
+
+static void test_case_insensitive(void)
+{
+ const char *uppercase_env = getenv("APPDATA");
+ const char *lowercase_env = getenv("appdata");
+ const wchar_t *uppercase_wenv = _wgetenv(L"APPDATA");
+ const wchar_t *lowercase_wenv = _wgetenv(L"appdata");
+
+ ok( uppercase_env == lowercase_env, "getenv() must be case insensitive, %p
should be %p\n",
+ lowercase_env, uppercase_env );
+ ok( uppercase_wenv == lowercase_wenv, "_wgetenv() must be case insensitive, %p
should be %p\n",
+ lowercase_wenv, uppercase_wenv );
+
+ ok( !_putenv("cAt=bar"), "Failed to set CAT=bar\n" );
+ ok( !_putenv("CAT=BAR"), "Failed to set CAT=BAR\n" );
+ ok( !strcmp(getenv("cAt"), "BAR"), "_putenv() must be case
insensitive\n" );
+
+ ok( !_wputenv(L"cAt=bar"), "Failed to set CAT=bar\n" );
+ ok( !_wputenv(L"CAT=BAR"), "Failed to set CAT=BAR\n" );
+ ok( !wcscmp(_wgetenv(L"cAt"), L"BAR"), "_wputenv() must be
case insensitive\n" );
+
+ _putenv("cat=");
}
START_TEST(environ)
{
+ char **argv;
+ int argc;
+
init();
- /* The environ tests should always be run first, as they assume
- * that the process has not manipulated the environment. */
+ argc = winetest_get_mainargs( &argv );
+ if (argc == 3 && !strcmp( argv[2], "create" ))
+ {
+ ok( getenv( "__winetest_dog" ) && !strcmp( getenv(
"__winetest_dog" ), "bark" ),
+ "Couldn't find env var\n" );
+ ok( _wgetenv( L"__winetest_\u263a" ) && !wcscmp( _wgetenv(
L"__winetest_\u263a" ), L"\u03b2" ),
+ "Couldn't find unicode env var\n" );
+ return;
+ }
+
test__environ();
test__wenviron();
test_environment_manipulation();
+ test_child_env(argv);
test_system();
+ test_case_insensitive();
}
diff --git a/modules/rostests/winetests/msvcrt/file.c
b/modules/rostests/winetests/msvcrt/file.c
index fe62d5c385e..d082bb269c6 100644
--- a/modules/rostests/winetests/msvcrt/file.c
+++ b/modules/rostests/winetests/msvcrt/file.c
@@ -35,6 +35,25 @@
#include <process.h>
#include <errno.h>
#include <locale.h>
+#ifdef __REACTOS__
+#include <ntndk.h>
+#else
+#include <winternl.h>
+#endif
+
+#define WX_OPEN 0x01
+#define WX_ATEOF 0x02
+#define WX_READNL 0x04
+#define WX_PIPE 0x08
+#define WX_DONTINHERIT 0x10
+#define WX_APPEND 0x20
+#define WX_TTY 0x40
+#define WX_TEXT 0x80
+
+#define EF_UTF8 0x01
+#define EF_UTF16 0x02
+#define EF_CRIT_INIT 0x04
+#define EF_UNK_UNICODE 0x08
#define MSVCRT_FD_BLOCK_SIZE 32
typedef struct {
@@ -52,6 +71,7 @@ static int (__cdecl *p_fopen_s)(FILE**, const char*, const char*);
static int (__cdecl *p__wfopen_s)(FILE**, const wchar_t*, const wchar_t*);
static errno_t (__cdecl *p__get_fmode)(int*);
static errno_t (__cdecl *p__set_fmode)(int);
+static int (__cdecl *p__setmaxstdio)(int);
static const char* get_base_name(const char *path)
{
@@ -76,6 +96,7 @@ static void init(void)
__pioinfo = (void*)GetProcAddress(hmod, "__pioinfo");
p__get_fmode = (void*)GetProcAddress(hmod, "_get_fmode");
p__set_fmode = (void*)GetProcAddress(hmod, "_set_fmode");
+ p__setmaxstdio = (void*)GetProcAddress(hmod, "_setmaxstdio");
}
static void test_filbuf( void )
@@ -211,7 +232,50 @@ static void test_fileops( void )
ok(fread(buffer, sizeof(buffer), 1, file) == 0, "fread test failed\n");
/* feof should be set now */
ok(feof(file), "feof after fread failed\n");
- fclose (file);
+ clearerr(file);
+ ok(!feof(file), "feof after clearerr failed\n");
+ fclose(file);
+
+ file = fopen("fdopen.tst", "rb");
+ ok( file != NULL, "fopen failed\n");
+ /* sizeof(buffer) > content of file */
+ ok(fread(buffer, sizeof(buffer), 1, file) == 0, "fread test failed\n");
+ /* feof should be set now */
+ ok(feof(file), "feof after fread failed\n");
+ rewind(file);
+ ok(!feof(file), "feof after rewind failed\n");
+ fclose(file);
+
+ file = fopen("fdopen.tst", "rb");
+ ok( file != NULL, "fopen failed\n");
+ /* sizeof(buffer) > content of file */
+ ok(fread(buffer, sizeof(buffer), 1, file) == 0, "fread test failed\n");
+ /* feof should be set now */
+ ok(feof(file), "feof after fread failed\n");
+ fseek(file, 0, SEEK_SET);
+ ok(!feof(file), "feof after fseek failed\n");
+ fclose(file);
+
+ file = fopen("fdopen.tst", "rb");
+ ok( file != NULL, "fopen failed\n");
+ /* sizeof(buffer) > content of file */
+ ok(fread(buffer, sizeof(buffer), 1, file) == 0, "fread test failed\n");
+ /* feof should be set now */
+ ok(feof(file), "feof after fread failed\n");
+ fgetpos(file, &pos);
+ fsetpos(file, &pos);
+ ok(!feof(file), "feof after fsetpos failed\n");
+ fclose(file);
+
+ file = fopen("fdopen.tst", "rb");
+ ok( file != NULL, "fopen failed\n");
+ /* sizeof(buffer) > content of file */
+ ok(fread(buffer, sizeof(buffer), 1, file) == 0, "fread test failed\n");
+ /* feof should be set now */
+ ok(feof(file), "feof after fread failed\n");
+ fsetpos(file, &pos);
+ ok(!feof(file), "feof after fsetpos failed\n");
+ fclose(file);
unlink ("fdopen.tst");
}
@@ -233,7 +297,7 @@ static void test_readmode( BOOL ascii_mode )
fd = open ("fdopen.tst", O_WRONLY | O_CREAT | O_BINARY, _S_IREAD
|_S_IWRITE);
/* an internal buffer of BUFSIZ is maintained, so make a file big
- * enough to test operations that cross the buffer boundary
+ * enough to test operations that cross the buffer boundary
*/
j = (2*BUFSIZ-4)/strlen(padbuffer);
for (i=0; i<j; i++)
@@ -243,8 +307,21 @@ static void test_readmode( BOOL ascii_mode )
write (fd, &padbuffer[i], 1);
write (fd, nlbuffer, strlen(nlbuffer));
write (fd, outbuffer, sizeof (outbuffer));
+
+ errno = 0xdeadbeef;
+ _doserrno = 0xdeadbeef;
+ ok(read(fd, buffer, 1) == -1, "read succeeded on write-only file\n");
+ ok(errno == EBADF, "errno = %d\n", errno);
+ ok(_doserrno == ERROR_ACCESS_DENIED, "doserrno = %ld\n", _doserrno);
+
close (fd);
-
+
+ fd = open ("fdopen.tst", O_RDONLY, _S_IREAD |_S_IWRITE);
+ errno = 0xdeadbeef;
+ ok(dup2(fd, -1) == -1, "dup2(fd, -1) succeeded\n");
+ ok(errno == EBADF, "errno = %d\n", errno);
+ close (fd);
+
if (ascii_mode) {
/* Open file in ascii mode */
fd = open ("fdopen.tst", O_RDONLY);
@@ -256,13 +333,13 @@ static void test_readmode( BOOL ascii_mode )
file = fdopen (fd, "rb");
ao = 0;
}
-
+
/* first is a test of fgets, ftell, fseek */
ok(ftell(file) == 0,"Did not start at beginning of file in %s\n", IOMODE);
ok(fgets(buffer,2*BUFSIZ+256,file) !=0,"padding line fgets failed unexpected in
%s\n", IOMODE);
l = ftell(file);
pl = 2*BUFSIZ-2;
- ok(l == pl,"padding line ftell got %d should be %d in %s\n", l, pl,
IOMODE);
+ ok(l == pl,"padding line ftell got %ld should be %d in %s\n", l, pl,
IOMODE);
ok(lstrlenA(buffer) == pl+ao,"padding line fgets got size %d should be %d in
%s\n",
lstrlenA(buffer), pl+ao, IOMODE);
for (fp=0; fp<strlen(outbuffer); fp++)
@@ -270,26 +347,32 @@ static void test_readmode( BOOL ascii_mode )
fp++;
ok(fgets(buffer,256,file) !=0,"line 1 fgets failed unexpected in %s\n",
IOMODE);
l = ftell(file);
- ok(l == pl+fp,"line 1 ftell got %d should be %d in %s\n", l, pl+fp,
IOMODE);
+ ok(l == pl+fp,"line 1 ftell got %ld should be %d in %s\n", l, pl+fp,
IOMODE);
ok(lstrlenA(buffer) == fp+ao,"line 1 fgets got size %d should be %d in
%s\n",
lstrlenA(buffer), fp+ao, IOMODE);
/* test a seek back across the buffer boundary */
l = pl;
ok(fseek(file,l,SEEK_SET)==0,"seek failure in %s\n", IOMODE);
l = ftell(file);
- ok(l == pl,"ftell after seek got %d should be %d in %s\n", l, pl, IOMODE);
+ ok(l == pl,"ftell after seek got %ld should be %d in %s\n", l, pl,
IOMODE);
ok(fgets(buffer,256,file) !=0,"second read of line 1 fgets failed unexpected in
%s\n", IOMODE);
l = ftell(file);
- ok(l == pl+fp,"second read of line 1 ftell got %d should be %d in %s\n", l,
pl+fp, IOMODE);
+ ok(l == pl+fp,"second read of line 1 ftell got %ld should be %d in %s\n",
l, pl+fp, IOMODE);
ok(lstrlenA(buffer) == fp+ao,"second read of line 1 fgets got size %d should be
%d in %s\n",
lstrlenA(buffer), fp+ao, IOMODE);
ok(fgets(buffer,256,file) !=0,"line 2 fgets failed unexpected in %s\n",
IOMODE);
fp += 2;
l = ftell(file);
- ok(l == pl+fp,"line 2 ftell got %d should be %d in %s\n", l, pl+fp,
IOMODE);
+ ok(l == pl+fp,"line 2 ftell got %ld should be %d in %s\n", l, pl+fp,
IOMODE);
ok(lstrlenA(buffer) == 2+ao,"line 2 fgets got size %d should be %d in
%s\n",
lstrlenA(buffer), 2+ao, IOMODE);
-
+
+ errno = 0xdeadbeef;
+ _doserrno = 0xdeadbeef;
+ ok(write(fd, buffer, 1) == -1, "read succeeded on write-only file\n");
+ ok(errno == EBADF, "errno = %d\n", errno);
+ ok(_doserrno == ERROR_ACCESS_DENIED, "doserrno = %ld\n", _doserrno);
+
/* test fread across buffer boundary */
rewind(file);
ok(ftell(file) == 0,"Did not start at beginning of file in %s\n", IOMODE);
@@ -298,7 +381,7 @@ static void test_readmode( BOOL ascii_mode )
i=fread(buffer,1,BUFSIZ+strlen(outbuffer),file);
ok(i==BUFSIZ+j,"fread failed, expected %d got %d in %s\n", BUFSIZ+j, i,
IOMODE);
l = ftell(file);
- ok(l == pl+j-(ao*4)-5,"ftell after fread got %d should be %d in %s\n", l,
pl+j-(ao*4)-5, IOMODE);
+ ok(l == pl+j-(ao*4)-5,"ftell after fread got %ld should be %d in %s\n", l,
pl+j-(ao*4)-5, IOMODE);
for (m=0; m<3; m++)
ok(buffer[m]==padbuffer[m+(BUFSIZ-4)%strlen(padbuffer)],"expected %c got
%c\n", padbuffer[m], buffer[m]);
m+=BUFSIZ+2+ao;
@@ -687,7 +770,7 @@ static void test_fflush( void )
char buf1[16], buf2[24];
char *tempf;
FILE *tempfh;
- int ret;
+ int ret, fd;
tempf=_tempnam(".","wne");
@@ -728,7 +811,23 @@ static void test_fflush( void )
ok(memcmp(buf1, buf2, sizeof(buf1)) == 0, "Got unexpected data (%c)\n",
buf2[0]);
fclose(tempfh);
+ unlink(tempf);
+
+ /* test flush failure */
+ tempfh = fopen(tempf,"wb");
+ ok(tempfh != NULL, "Can't open test file.\n");
+ fwrite(obuf, 1, sizeof(obuf), tempfh);
+ fd = tempfh->_file;
+ tempfh->_file = -1;
+ ok(tempfh->_ptr - tempfh->_base, "buffer is empty\n");
+ ret = fflush(tempfh);
+ ok(ret == EOF, "expected EOF, got %d\n", ret);
+ ok(!(tempfh->_ptr - tempfh->_base), "buffer should be empty\n");
+ ok(!tempfh->_cnt, "tempfh->_cnt = %d\n", tempfh->_cnt);
+
+ tempfh->_file = fd;
+ fclose(tempfh);
unlink(tempf);
free(tempf);
}
@@ -764,10 +863,10 @@ static void test_fgetwc( void )
tempfh = fopen(tempf,"rt"); /* open in TEXT mode */
fgetws(wtextW,LLEN,tempfh);
l=ftell(tempfh);
- ok(l==BUFSIZ-2, "ftell expected %d got %d\n", BUFSIZ-2, l);
+ ok(l==BUFSIZ-2, "ftell expected %d got %ld\n", BUFSIZ-2, l);
fgetws(wtextW,LLEN,tempfh);
l=ftell(tempfh);
- ok(l==BUFSIZ-2+strlen(mytext), "ftell expected %d got %d\n",
BUFSIZ-2+lstrlenA(mytext), l);
+ ok(l==BUFSIZ-2+strlen(mytext), "ftell expected %d got %ld\n",
BUFSIZ-2+lstrlenA(mytext), l);
mytextW = AtoW (mytext);
aptr = mytextW;
wptr = wtextW;
@@ -779,7 +878,7 @@ static void test_fgetwc( void )
ok(*wptr == '\n', "Carriage return was not skipped\n");
fclose(tempfh);
unlink(tempf);
-
+
tempfh = fopen(tempf,"wb");
j = 'a';
/* pad to almost the length of the internal buffer. Use an odd number of bytes
@@ -800,25 +899,25 @@ static void test_fgetwc( void )
fgetws(wtextW,j,tempfh);
l=ftell(tempfh);
j=(j-1)*sizeof(WCHAR);
- ok(l==j, "ftell expected %d got %d\n", j, l);
+ ok(l==j, "ftell expected %d got %ld\n", j, l);
i=fgetc(tempfh);
ok(i=='a', "fgetc expected %d got %d\n", 0x61, i);
l=ftell(tempfh);
j++;
- ok(l==j, "ftell expected %d got %d\n", j, l);
+ ok(l==j, "ftell expected %d got %ld\n", j, l);
fgetws(wtextW,3,tempfh);
ok(wtextW[0]=='\r',"expected carriage return got %04hx\n",
wtextW[0]);
ok(wtextW[1]=='\n',"expected newline got %04hx\n", wtextW[1]);
l=ftell(tempfh);
j += 4;
- ok(l==j, "ftell expected %d got %d\n", j, l);
+ ok(l==j, "ftell expected %d got %ld\n", j, l);
for(i=0; i<strlen(mytext); i++)
wtextW[i] = 0;
/* the first time we get the string, it should be entirely within the local buffer */
fgetws(wtextW,LLEN,tempfh);
l=ftell(tempfh);
j += (strlen(mytext)-1)*sizeof(WCHAR);
- ok(l==j, "ftell expected %d got %d\n", j, l);
+ ok(l==j, "ftell expected %d got %ld\n", j, l);
diff_found = FALSE;
aptr = mytextW;
wptr = wtextW;
@@ -955,6 +1054,38 @@ static void test_fgetwc_unicode(void)
ok(ch == WEOF, "got %04hx, expected WEOF (unicode)\n", ch);
fclose(tempfh);
+ tempfh = fopen(tempfile, "r,ccs=utf-8");
+ ok(tempfh != NULL, "can't open tempfile\n");
+ for (i = 1; i < ARRAY_SIZE(wchar_text); i++)
+ {
+ ch = fgetwc(tempfh);
+ ok(ch == wchar_text[i],
+ "got %04hx, expected %04x (unicode[%d])\n", ch, wchar_text[i],
i-1);
+ }
+ ch = fgetwc(tempfh);
+ ok(ch == WEOF, "got %04hx, expected WEOF (unicode)\n", ch);
+ fclose(tempfh);
+
+ tempfh = fopen(tempfile, "a,ccs=utf-16le");
+ ok(tempfh != NULL, "can't open tempfile\n");
+ ch = fputwc('a', tempfh);
+ ok(ch == 'a', "fputwc returned %x\n", ch);
+ fclose(tempfh);
+
+ tempfh = fopen(tempfile, "a+,ccs=utf-8");
+ ok(tempfh != NULL, "can't open tempfile\n");
+ for (i = 1; i < ARRAY_SIZE(wchar_text); i++)
+ {
+ ch = fgetwc(tempfh);
+ ok(ch == wchar_text[i],
+ "got %04hx, expected %04x (unicode[%d])\n", ch, wchar_text[i],
i-1);
+ }
+ ch = fgetwc(tempfh);
+ ok(ch == 'a', "got %04x, expected 'a'\n", ch);
+ ch = fgetwc(tempfh);
+ ok(ch == WEOF, "got %04hx, expected WEOF (unicode)\n", ch);
+ fclose(tempfh);
+
tempfh = fopen(tempfile, "wb");
ok(tempfh != NULL, "can't open tempfile\n");
ret = WideCharToMultiByte(CP_UTF8, 0, wchar_text, ARRAY_SIZE(wchar_text),
@@ -974,6 +1105,57 @@ static void test_fgetwc_unicode(void)
ch = fgetwc(tempfh);
ok(ch == WEOF, "got %04hx, expected WEOF (utf8)\n", ch);
fclose(tempfh);
+
+ tempfh = fopen(tempfile, "wb");
+ ok(tempfh != NULL, "can't open tempfile\n");
+ fwrite(wchar_text+1, 1, sizeof(wchar_text)-1, tempfh);
+ fclose(tempfh);
+
+ tempfh = fopen(tempfile, "rt,ccs=utf-16le");
+ ok(tempfh != NULL, "can't open tempfile\n");
+ for (i = 1; i < ARRAY_SIZE(wchar_text); i++)
+ {
+ ch = fgetwc(tempfh);
+ ok(ch == wchar_text[i],
+ "got %04hx, expected %04x (unicode[%d])\n", ch, wchar_text[i],
i-1);
+ }
+ ch = fgetwc(tempfh);
+ ok(ch == WEOF, "got %04hx, expected WEOF (unicode)\n", ch);
+ fclose(tempfh);
+
+ tempfh = fopen(tempfile, "wb");
+ ok(tempfh != NULL, "can't open tempfile\n");
+ ret = WideCharToMultiByte(CP_UTF8, 0, wchar_text + 1, ARRAY_SIZE(wchar_text) - 1,
+ utf8_text, sizeof(utf8_text), NULL, NULL);
+ ok(ret > 0, "utf-8 conversion failed\n");
+ utf8_text[ret] = 0;
+ fwrite(utf8_text, sizeof(char), ret, tempfh);
+ fclose(tempfh);
+
+ tempfh = fopen(tempfile, "rt, ccs=UTF-8");
+ ok(tempfh != NULL, "can't open tempfile\n");
+ for (i = 1; i < ARRAY_SIZE(wchar_text); i++)
+ {
+ ch = fgetwc(tempfh);
+ ok(ch == wchar_text[i],
+ "got %04hx, expected %04x (utf8[%d])\n", ch, wchar_text[i], i-1);
+ }
+ ch = fgetwc(tempfh);
+ ok(ch == WEOF, "got %04hx, expected WEOF (utf8)\n", ch);
+ fclose(tempfh);
+
+ tempfh = fopen(tempfile, "rt, ccs=unicode");
+ ok(tempfh != NULL, "can't open tempfile\n");
+ for (i = 0; utf8_text[i]; i++)
+ {
+ ch = fgetwc(tempfh);
+ ok(ch == (unsigned char) utf8_text[i],
+ "got %04hx, expected %04x (unicode[%d])\n", ch, (unsigned
char)utf8_text[i], i);
+ }
+ ch = fgetwc(tempfh);
+ ok(ch == WEOF, "got %04hx, expected WEOF (unicode)\n", ch);
+ fclose(tempfh);
+
unlink(temppath);
}
@@ -1034,6 +1216,98 @@ static void test_fputwc(void)
_unlink(tempfile);
}
+static void test_freopen( void )
+{
+ char filename1[8] = "AXXXXXX";
+ char filename2[8] = "BXXXXXX";
+ FILE *file;
+ FILE *new;
+ int ret;
+ int fd;
+ char ch;
+ long pos;
+
+ mktemp(filename1);
+ mktemp(filename2);
+
+ file = fopen(filename1, "wt");
+ ok(file != NULL, "fopen(filename1) returned NULL\n");
+ ret = fwrite("1", 1, 1, file);
+ ok(ret == 1, "fwrite() returned %d (%d)\n", ret, errno);
+ ret = fclose(file);
+ ok(ret == 0, "fclose() returned %d\n", ret);
+
+ file = fopen(filename2, "wt");
+ ok(file != NULL, "fopen(filename1) returned NULL\n");
+ ret = fwrite("2", 1, 1, file);
+ ok(ret == 1, "fwrite() returned %d (%d)\n", ret, errno);
+ ret = fclose(file);
+ ok(ret == 0, "fclose() returned %d\n", ret);
+
+ file = fopen(filename1, "rt");
+ ok(file != NULL, "fopen(filename1) returned NULL\n");
+ file = freopen(filename2, "rt", file);
+ ok(file != NULL, "fopen(filename2) returned NULL\n");
+ ch = '#';
+ ret = fread(&ch, 1, 1, file);
+ ok(ret == 1, "fread() returned %d\n", ret);
+ ok(ch == '2', "fread() read %c\n", ch);
+ ret = fclose(file);
+ ok(ret == 0, "fclose() returned %d\n", ret);
+
+ file = fopen(filename1, "at");
+ ok(file != NULL, "fopen(filename1) returned NULL\n");
+ file = freopen(filename1, "rt", file);
+ ok(file != NULL, "fopen(filename1) returned NULL\n");
+ pos = ftell(file);
+ ok(pos == 0, "ftell() returned %ld\n", pos);
+ ch = '#';
+ ret = fread(&ch, 1, 1, file);
+ ok(ret == 1, "fread() returned %d\n", ret);
+ ok(ch == '1', "fread() read %c\n", ch);
+ ret = fclose(file);
+ ok(ret == 0, "fclose() returned %d\n", ret);
+
+ file = fopen(filename1, "rt");
+ ok(file != NULL, "fopen(filename1) returned NULL\n");
+ fd = fileno(file);
+ ok(fd > 0, "fileno() returned %d\n", fd);
+ /* invalid filename */
+ new = freopen("_:", "rt", file);
+ ok(new == NULL, "fopen(_:) returned non NULL\n");
+ errno = 0xdeadbeef;
+ ch = '#';
+ ret = read(fd, &ch, 1);
+ ok(ret == -1, "read() returned %d\n", ret);
+ ok(errno == EBADF, "errno is %d\n", errno);
+ errno = 0xdeadbeef;
+ ret = fclose(file);
+ ok(ret == EOF, "fclose(file) succeeded\n");
+ ok(errno == 0xdeadbeef, "errno is %d\n", errno);
+
+ file = fopen(filename1, "rb");
+ ok(file != NULL, "couldn't open %s\n", filename1);
+ close(file->_file);
+ file->_file = -1;
+
+ new = freopen(filename2, "rb", file);
+ ok(new == file, "freopen() didn't return same FILE*\n");
+
+ fd = fileno(file);
+ ok(fd > 0, "fileno() returned %d\n", fd);
+
+ ch = '#';
+ ret = fread(&ch, 1, 1, file);
+ ok(ret == 1, "fread() returned %d\n", ret);
+ ok(ch == '2', "Unexpected char\n");
+
+ ret = fclose(file);
+ ok(ret == 0, "fclose(file) returned %d\n", ret);
+
+ unlink(filename1);
+ unlink(filename2);
+}
+
static void test_ctrlz( void )
{
char* tempf;
@@ -1062,17 +1336,17 @@ static void test_ctrlz( void )
ok(i==j, "returned string length expected %d got %d\n", j, i);
j+=4; /* ftell should indicate the true end of file */
l=ftell(tempfh);
- ok(l==j, "ftell expected %d got %d\n", j, l);
+ ok(l==j, "ftell expected %d got %ld\n", j, l);
ok(feof(tempfh), "did not get EOF\n");
fclose(tempfh);
-
+
tempfh = fopen(tempf,"rb"); /* open in BINARY mode */
ok(fgets(buffer,256,tempfh) != 0,"fgets failed unexpected\n");
i=strlen(buffer);
j=strlen(mytext)+3; /* should get through newline */
ok(i==j, "returned string length expected %d got %d\n", j, i);
l=ftell(tempfh);
- ok(l==j, "ftell expected %d got %d\n", j, l);
+ ok(l==j, "ftell expected %d got %ld\n", j, l);
ok(fgets(buffer,256,tempfh) != 0,"fgets failed unexpected\n");
i=strlen(buffer);
ok(i==1, "returned string length expected %d got %d\n", 1, i);
@@ -1185,7 +1459,7 @@ static void test_file_write_read( void )
memset(btext, 0, LLEN);
tempfd = _open(tempf,_O_APPEND|_O_RDWR); /* open for APPEND in default mode */
- ok(tell(tempfd) == 0, "bad position %u expecting 0\n", tell(tempfd));
+ ok(tell(tempfd) == 0, "bad position %lu expecting 0\n", tell(tempfd));
ok(_read(tempfd,btext,LLEN) == lstrlenA(mytext), "_read _O_APPEND got bad
length\n");
ok( memcmp(mytext,btext,strlen(mytext)) == 0, "problems with _O_APPEND
_read\n");
_close(tempfd);
@@ -1206,15 +1480,15 @@ static void test_file_write_read( void )
_lseek(tempfd, -3, FILE_END);
ret = _read(tempfd,btext,1);
ok(ret == 1 && *btext == 'e', "_read expected 'e' got
\"%.*s\" bad length: %d\n", ret, btext, ret);
- ok(tell(tempfd) == 41, "bad position %u expecting 41\n", tell(tempfd));
+ ok(tell(tempfd) == 41, "bad position %lu expecting 41\n", tell(tempfd));
_lseek(tempfd, -3, FILE_END);
ret = _read(tempfd,btext,2);
ok(ret == 1 && *btext == 'e', "_read expected 'e' got
\"%.*s\" bad length: %d\n", ret, btext, ret);
- ok(tell(tempfd) == 42, "bad position %u expecting 42\n", tell(tempfd));
+ ok(tell(tempfd) == 42, "bad position %lu expecting 42\n", tell(tempfd));
_lseek(tempfd, -3, FILE_END);
ret = _read(tempfd,btext,3);
ok(ret == 2 && *btext == 'e', "_read expected 'e' got
\"%.*s\" bad length: %d\n", ret, btext, ret);
- ok(tell(tempfd) == 43, "bad position %u expecting 43\n", tell(tempfd));
+ ok(tell(tempfd) == 43, "bad position %lu expecting 43\n", tell(tempfd));
_close(tempfd);
ret = unlink(tempf);
@@ -1336,9 +1610,9 @@ static void test_file_write_read( void )
/* test invalid utf8 sequence */
lseek(tempfd, 5, SEEK_SET);
ret = _read(tempfd, btext, sizeof(btext));
- todo_wine ok(ret == 10, "_read returned %d, expected 10\n", ret);
+ ok(ret == 10, "_read returned %d, expected 10\n", ret);
/* invalid char should be replaced by U+FFFD in MultiByteToWideChar */
- todo_wine ok(!memcmp(btext, "\xfd\xff", 2), "invalid UTF8 character
was not replaced by U+FFFD\n");
+ ok(!memcmp(btext, "\xfd\xff", 2), "invalid UTF8 character was not
replaced by U+FFFD\n");
ok(!memcmp(btext+ret-8, "\x62\x00\x7c\x01\x0d\x00\x0a\x00", 8),
"btext is incorrect\n");
_close(tempfd);
}
@@ -1355,13 +1629,27 @@ static void test_file_write_read( void )
free(tempf);
}
-static void test_file_inherit_child(const char* fd_s)
+static void test_file_inherit_child(const char* fd_s, const char *handle_str)
{
+ HANDLE handle_value;
int fd = atoi(fd_s);
+ HANDLE *handle_ptr;
+ unsigned int count;
char buffer[32];
+ STARTUPINFOA si;
int ret;
- ret =write(fd, "Success", 8);
+ GetStartupInfoA(&si);
+ count = *(unsigned *)si.lpReserved2;
+ if (handle_str)
+ {
+ ok(count == 3, "Got unexpected count %u.\n", count);
+ sscanf(handle_str, "%p", &handle_value);
+ handle_ptr = (HANDLE *)(si.lpReserved2 + sizeof(unsigned) + count);
+ ok(handle_value == handle_ptr[1], "Got unexpected handle %p.\n",
handle_ptr[1]);
+ }
+
+ ret = write(fd, "Success", 8);
ok( ret == 8, "Couldn't write in child process on %d (%s)\n", fd,
strerror(errno));
lseek(fd, 0, SEEK_SET);
ok(read(fd, buffer, sizeof (buffer)) == 8, "Couldn't read back the
data\n");
@@ -1374,7 +1662,7 @@ static void test_file_inherit_child_no(const char* fd_s)
int ret;
ret = write(fd, "Success", 8);
- ok( ret == -1 && errno == EBADF,
+ ok( ret == -1 && errno == EBADF,
"Wrong write result in child process on %d (%s)\n", fd,
strerror(errno));
}
@@ -1430,7 +1718,7 @@ static void test_stdout_handle( STARTUPINFOA *startup, char
*cmdline, HANDLE hst
CreateProcessA( NULL, cmdline, NULL, NULL, TRUE,
CREATE_DEFAULT_ERROR_MODE | NORMAL_PRIORITY_CLASS, NULL, NULL,
startup, &proc );
- winetest_wait_child_process( proc.hProcess );
+ wait_child_process( proc.hProcess );
data = read_file( hErrorFile );
if (expect_stdout)
@@ -1451,6 +1739,18 @@ static void test_stdout_handle( STARTUPINFOA *startup, char
*cmdline, HANDLE hst
DeleteFileA( "fdopen.err" );
}
+static unsigned WINAPI read_pipe_thread(void *argument)
+{
+ unsigned char buffer[2];
+ int ret;
+ int *pipefds = argument;
+
+ ret = _read(pipefds[0], buffer, sizeof(buffer));
+ ok(ret == 1, "ret = %d\n", ret);
+ ok(buffer[0] == 'a', "%x\n", buffer[0]);
+ return 0;
+}
+
static void test_file_inherit( const char* selfname )
{
int fd;
@@ -1460,33 +1760,62 @@ static void test_file_inherit( const char* selfname )
STARTUPINFOA startup;
SECURITY_ATTRIBUTES sa;
HANDLE handles[3];
+ HANDLE thread_handle;
+ int pipefds[2];
+ intptr_t ret;
fd = open ("fdopen.tst", O_CREAT | O_RDWR | O_BINARY, _S_IREAD
|_S_IWRITE);
ok(fd != -1, "Couldn't create test file\n");
arg_v[0] = get_base_name(selfname);
- arg_v[1] = "tests/file.c";
+ arg_v[1] = "file";
arg_v[2] = "inherit";
arg_v[3] = buffer; sprintf(buffer, "%d", fd);
arg_v[4] = 0;
- _spawnvp(_P_WAIT, selfname, arg_v);
- ok(tell(fd) == 8, "bad position %u expecting 8\n", tell(fd));
+ ret = _spawnvp(_P_WAIT, selfname, arg_v);
+ ok(ret == 0, "_spawnvp returned %Id, errno %d\n", ret, errno);
+ ok(tell(fd) == 8, "bad position %lu expecting 8\n", tell(fd));
lseek(fd, 0, SEEK_SET);
ok(read(fd, buffer, sizeof (buffer)) == 8 && memcmp(buffer,
"Success", 8) == 0, "Couldn't read back the data\n");
close (fd);
ok(unlink("fdopen.tst") == 0, "Couldn't unlink\n");
-
+
fd = open ("fdopen.tst", O_CREAT | O_RDWR | O_BINARY | O_NOINHERIT,
_S_IREAD |_S_IWRITE);
ok(fd != -1, "Couldn't create test file\n");
- arg_v[1] = "tests/file.c";
+ arg_v[1] = "file";
arg_v[2] = "inherit_no";
arg_v[3] = buffer; sprintf(buffer, "%d", fd);
arg_v[4] = 0;
- _spawnvp(_P_WAIT, selfname, arg_v);
- ok(tell(fd) == 0, "bad position %u expecting 0\n", tell(fd));
+ ret = _spawnvp(_P_WAIT, selfname, arg_v);
+ ok(ret == 0, "_spawnvp returned %Id, errno %d\n", ret, errno);
+ ok(tell(fd) == 0, "bad position %lu expecting 0\n", tell(fd));
ok(read(fd, buffer, sizeof (buffer)) == 0, "Found unexpected data (%s)\n",
buffer);
close (fd);
ok(unlink("fdopen.tst") == 0, "Couldn't unlink\n");
+ /* Show that spawn works while a read is active */
+ ok(_pipe(pipefds, 1, O_BINARY) == 0, "_pipe() failed\n");
+ thread_handle = (HANDLE)_beginthreadex(NULL, 0, read_pipe_thread, pipefds, 0, NULL);
+ Sleep(100); /* try to make sure the thread is reading */
+ fd = open ("fdopen.tst", O_CREAT | O_RDWR | O_BINARY, _S_IREAD
|_S_IWRITE);
+ ok(fd != -1, "Couldn't create test file\n");
+ arg_v[1] = "tests/file.c";
+ arg_v[2] = "inherit";
+ arg_v[3] = buffer; sprintf(buffer, "%d", fd);
+ arg_v[4] = 0;
+ ret = _spawnvp(_P_WAIT, selfname, arg_v);
+ ok(ret == 0, "_spawnvp returned %Id, errno %d\n", ret, errno);
+ ret = tell(fd);
+ ok(ret == 8, "bad position %Iu expecting 8\n", ret);
+ lseek(fd, 0, SEEK_SET);
+ ok(read(fd, buffer, sizeof (buffer)) == 8 && memcmp(buffer,
"Success", 8) == 0, "Couldn't read back the data\n");
+ close (fd);
+ ok(unlink("fdopen.tst") == 0, "Couldn't unlink\n");
+ _write(pipefds[1], "a", 1);
+ WaitForSingleObject(thread_handle, INFINITE);
+ CloseHandle(thread_handle);
+ close(pipefds[0]);
+ close(pipefds[1]);
+
/* make file handle inheritable */
sa.nLength = sizeof(sa);
sa.lpSecurityDescriptor = NULL;
@@ -1544,6 +1873,22 @@ static void test_file_inherit( const char* selfname )
test_stdout_handle( &startup, cmdline, handles[1], TRUE, "large size
block" );
CloseHandle( handles[1] );
DeleteFileA("fdopen.tst");
+
+ /* test inherit block with invalid handle */
+ handles[1] = INVALID_HANDLE_VALUE;
+ create_io_inherit_block( &startup, 3, handles );
+ sprintf(cmdline, "%s file inherit 1 %p", selfname, handles[1]);
+ test_stdout_handle( &startup, cmdline, NULL, FALSE, "INVALID_HANDLE_VALUE
stdout handle" );
+
+ handles[1] = NULL;
+ create_io_inherit_block( &startup, 3, handles );
+ sprintf(cmdline, "%s file inherit 1 %p", selfname, handles[1]);
+ test_stdout_handle( &startup, cmdline, NULL, FALSE, "NULL stdout
handle" );
+
+ handles[1] = (void *)0xdeadbeef;
+ create_io_inherit_block( &startup, 3, handles );
+ sprintf(cmdline, "%s file inherit 1 %p", selfname, handles[1]);
+ test_stdout_handle( &startup, cmdline, NULL, FALSE, "invalid stdout
handle" );
}
static void test_invalid_stdin_child( void )
@@ -1557,6 +1902,8 @@ static void test_invalid_stdin_child( void )
handle = (HANDLE)_get_osfhandle(STDIN_FILENO);
ok(handle == (HANDLE)-2, "handle = %p\n", handle);
ok(errno == 0xdeadbeef, "errno = %d\n", errno);
+ handle = GetStdHandle(STD_INPUT_HANDLE);
+ ok((LONG_PTR)handle > 0, "Expecting passed handle to be untouched\n");
info =
&__pioinfo[STDIN_FILENO/MSVCRT_FD_BLOCK_SIZE][STDIN_FILENO%MSVCRT_FD_BLOCK_SIZE];
ok(info->handle == (HANDLE)-2, "info->handle = %p\n",
info->handle);
@@ -1631,7 +1978,11 @@ static void test_invalid_stdin( const char* selfname )
}
ret = RegOpenCurrentUser(KEY_READ, &key);
- ok(!ret, "RegOpenCurrentUser failed: %x\n", ret);
+ ok(!ret, "RegOpenCurrentUser failed: %lx\n", ret);
+
+ ret = DuplicateHandle(GetCurrentProcess(), key, GetCurrentProcess(),
+ (HANDLE *)&key, GENERIC_READ, TRUE, DUPLICATE_CLOSE_SOURCE);
+ ok(ret, "DuplicateHandle failed: %lx\n", GetLastError());
sa.nLength = sizeof(sa);
sa.lpSecurityDescriptor = NULL;
@@ -1647,10 +1998,10 @@ static void test_invalid_stdin( const char* selfname )
sprintf(cmdline, "%s file stdin", selfname);
CreateProcessA(NULL, cmdline, NULL, NULL, TRUE,
CREATE_DEFAULT_ERROR_MODE|NORMAL_PRIORITY_CLASS, NULL, NULL, &startup,
&proc);
- winetest_wait_child_process(proc.hProcess);
+ wait_child_process(proc.hProcess);
ret = RegCloseKey(key);
- ok(!ret, "RegCloseKey failed: %x\n", ret);
+ ok(!ret, "RegCloseKey failed: %lx\n", ret);
}
static void test_tmpnam( void )
@@ -1678,8 +2029,8 @@ static void test_chsize( void )
LONG cur, pos, count;
char temptext[] = "012345678";
char *tempfile = _tempnam( ".", "tst" );
-
- ok( tempfile != NULL, "Couldn't create test file: %s\n", tempfile );
+
+ ok( tempfile != NULL, "Couldn't create test file\n" );
fd = _open( tempfile, _O_CREAT|_O_TRUNC|_O_RDWR, _S_IREAD|_S_IWRITE );
ok( fd > 0, "Couldn't open test file\n" );
@@ -1694,14 +2045,14 @@ static void test_chsize( void )
ok( _chsize( fd, sizeof(temptext) / 2 ) == 0, "_chsize() failed\n" );
pos = _lseek( fd, 0, SEEK_CUR );
- ok( cur == pos, "File pointer changed from: %d to: %d\n", cur, pos );
+ ok( cur == pos, "File pointer changed from: %ld to: %ld\n", cur, pos );
ok( _filelength( fd ) == sizeof(temptext) / 2, "Wrong file size\n" );
/* enlarge the file */
- ok( _chsize( fd, sizeof(temptext) * 2 ) == 0, "_chsize() failed\n" );
+ ok( _chsize( fd, sizeof(temptext) * 2 ) == 0, "_chsize() failed\n" );
pos = _lseek( fd, 0, SEEK_CUR );
- ok( cur == pos, "File pointer changed from: %d to: %d\n", cur, pos );
+ ok( cur == pos, "File pointer changed from: %ld to: %ld\n", cur, pos );
ok( _filelength( fd ) == sizeof(temptext) * 2, "Wrong file size\n" );
_close( fd );
@@ -1733,7 +2084,7 @@ static void test_fopen_fclose_fcloseall( void )
"filename is empty, errno = %d (expected 2 or 22)\n", errno);
errno = 0xfaceabad;
stream4 = fopen(NULL, "w+");
- ok(stream4 == NULL && (errno == EINVAL || errno == ENOENT),
+ ok(stream4 == NULL && (errno == EINVAL || errno == ENOENT),
"filename is NULL, errno = %d (expected 2 or 22)\n", errno);
/* testing fclose() */
@@ -1748,6 +2099,9 @@ static void test_fopen_fclose_fcloseall( void )
ret = fclose(stream3);
ok(ret == EOF, "Closing file '%s' returned %d\n", fname3, ret);
ok(errno == 0xdeadbeef, "errno = %d\n", errno);
+ ret = fclose(NULL);
+ ok(ret == EOF, "Closing NULL file returned %d\n", ret);
+ ok(errno == EINVAL, "errno = %d\n", errno);
/* testing fcloseall() */
numclosed = _fcloseall();
@@ -1879,12 +2233,6 @@ static void test_fopen_s( void )
static void test__wfopen_s( void )
{
const char name[] = "empty1";
- const WCHAR wname[] = {
- 'e','m','p','t','y','1',0
- };
- const WCHAR wmode[] = {
- 'w',0
- };
char buff[16];
FILE *file;
int ret;
@@ -1896,7 +2244,7 @@ static void test__wfopen_s( void )
return;
}
/* testing _wfopen_s */
- ret = p__wfopen_s(&file, wname, wmode);
+ ret = p__wfopen_s(&file, L"empty1", L"w");
ok(ret == 0, "_wfopen_s failed with %d\n", ret);
ok(file != 0, "_wfopen_s failed to return value\n");
fwrite(name, sizeof(name), 1, file);
@@ -2007,8 +2355,12 @@ static void test_get_osfhandle(void)
static void test_setmaxstdio(void)
{
- ok(2048 == _setmaxstdio(2048),"_setmaxstdio returned %d instead of
2048\n",_setmaxstdio(2048));
- ok(-1 == _setmaxstdio(2049),"_setmaxstdio returned %d instead of
-1\n",_setmaxstdio(2049));
+ if (p__setmaxstdio)
+ {
+ ok(2048 == p__setmaxstdio(2048),"_setmaxstdio returned %d instead of
2048\n",p__setmaxstdio(2048));
+ ok(-1 == p__setmaxstdio(2049),"_setmaxstdio returned %d instead of
-1\n",p__setmaxstdio(2049));
+ }
+ else win_skip( "_setmaxstdio not supported\n" );
}
static void test_stat(void)
@@ -2168,7 +2520,7 @@ static void test_pipes(const char* selfname)
}
arg_v[0] = get_base_name(selfname);
- arg_v[1] = "tests/file.c";
+ arg_v[1] = "file";
arg_v[2] = "pipes";
arg_v[3] = str_fdr; sprintf(str_fdr, "%d", pipes[0]);
arg_v[4] = str_fdw; sprintf(str_fdw, "%d", pipes[1]);
@@ -2197,7 +2549,7 @@ static void test_pipes(const char* selfname)
return;
}
- arg_v[1] = "tests/file.c";
+ arg_v[1] = "file";
arg_v[2] = "pipes";
arg_v[3] = str_fdr; sprintf(str_fdr, "%d", pipes[0]);
arg_v[4] = str_fdw; sprintf(str_fdw, "%d", pipes[1]);
@@ -2313,7 +2665,7 @@ static void test_stdin(void)
"GetStdHandle(STD_INPUT_HANDLE) !=
_get_osfhandle(STDIN_FILENO)\n");
r = SetStdHandle(STD_INPUT_HANDLE, INVALID_HANDLE_VALUE);
- ok(r == TRUE, "SetStdHandle returned %x, expected TRUE\n", r);
+ ok(r == TRUE, "SetStdHandle returned %lx, expected TRUE\n", r);
h = GetStdHandle(STD_INPUT_HANDLE);
ok(h == INVALID_HANDLE_VALUE, "h = %p\n", h);
@@ -2548,7 +2900,7 @@ static void test__creat(void)
pos = _tell(fd);
ok(pos == 6, "expected pos 6 (text mode), got %d\n", pos);
}
- ok(_lseek(fd, SEEK_SET, 0) == 0, "_lseek failed\n");
+ ok(_lseek(fd, 0, SEEK_SET) == 0, "_lseek failed\n");
count = _read(fd, buf, 6);
ok(count == 4, "_read returned %d, expected 4\n", count);
count = count > 0 ? count > 4 ? 4 : count : 0;
@@ -2568,7 +2920,7 @@ static void test__creat(void)
pos = _tell(fd);
ok(pos == 4, "expected pos 4 (binary mode), got %d\n", pos);
}
- ok(_lseek(fd, SEEK_SET, 0) == 0, "_lseek failed\n");
+ ok(_lseek(fd, 0, SEEK_SET) == 0, "_lseek failed\n");
count = _read(fd, buf, 6);
ok(count == 4, "_read returned %d, expected 4\n", count);
count = count > 0 ? count > 4 ? 4 : count : 0;
@@ -2583,6 +2935,215 @@ static void test__creat(void)
p__set_fmode(old_fmode);
}
+static void test_lseek(void)
+{
+ int fd;
+ char testdata[4] = {'a', '\n', 'b', '\n'};
+
+ errno = 0xdeadbeef;
+ ok(_lseek(-42, 0, SEEK_SET) == -1, "expected failure\n");
+ ok(errno == EBADF, "errno = %d\n", errno);
+
+ fd = _creat("_creat.tst", _S_IWRITE);
+ ok(fd > 0, "_creat failed\n");
+ _write(fd, testdata, 4);
+
+ errno = 0xdeadbeef;
+ ok(_lseek(fd, 0, 42) == -1, "expected failure\n");
+ ok(errno == EINVAL, "errno = %d\n", errno);
+
+ errno = 0xdeadbeef;
+ ok(_lseek(fd, -42, SEEK_SET) == -1, "expected failure\n");
+ ok(errno == EINVAL, "errno = %d\n", errno);
+
+ _close(fd);
+ DeleteFileA("_creat.tst");
+}
+
+static BOOL has_sequential_hint(int fd)
+{
+ HANDLE handle;
+ FILE_MODE_INFORMATION mode_info;
+ IO_STATUS_BLOCK io;
+ NTSTATUS status;
+
+ handle = (HANDLE)_get_osfhandle(fd);
+ status = NtQueryInformationFile(handle, &io, &mode_info, sizeof(mode_info),
+ FileModeInformation);
+ ok(!status, "NtQueryInformationFile failed\n");
+ return (mode_info.Mode & FILE_SEQUENTIAL_ONLY) != 0;
+}
+
+static void test_fopen_hints(void)
+{
+ static const struct {
+ const char *mode;
+ BOOL seq;
+ } tests[] = {
+ { "rb", FALSE },
+ { "rbS", TRUE },
+ { "rbR", FALSE },
+ { "rbSR", TRUE },
+ { "rbRS", FALSE }
+ };
+
+ char temppath[MAX_PATH], tempfile[MAX_PATH];
+ FILE *fp;
+ int i;
+
+ GetTempPathA(MAX_PATH, temppath);
+ GetTempFileNameA(temppath, "", 0, tempfile);
+
+ for (i = 0; i < ARRAY_SIZE(tests); ++i)
+ {
+ fp = fopen(tempfile, tests[i].mode);
+ ok(fp != NULL, "unable to fopen test file with mode
\"%s\"\n", tests[i].mode);
+ ok(has_sequential_hint(_fileno(fp)) == tests[i].seq,
+ "unexpected sequential hint for fopen mode \"%s\"\n",
tests[i].mode);
+ fclose(fp);
+ }
+ unlink(tempfile);
+}
+
+static void test_open_hints(void)
+{
+ static const struct {
+ int mode;
+ BOOL seq;
+ } tests[] = {
+ { _O_RDONLY | _O_BINARY, FALSE },
+ { _O_RDONLY | _O_BINARY | _O_SEQUENTIAL, TRUE },
+ { _O_RDONLY | _O_BINARY | _O_RANDOM, FALSE },
+ { _O_RDONLY | _O_BINARY | _O_RANDOM | _O_SEQUENTIAL, TRUE }
+ };
+
+ char temppath[MAX_PATH], tempfile[MAX_PATH];
+ int fd;
+ int i;
+
+ GetTempPathA(MAX_PATH, temppath);
+ GetTempFileNameA(temppath, "", 0, tempfile);
+
+ for (i = 0; i < ARRAY_SIZE(tests); ++i)
+ {
+ fd = open(tempfile, tests[i].mode);
+ ok(fd != -1, "unable to _open test file with flags %x\n",
tests[i].mode);
+ ok(has_sequential_hint(fd) == tests[i].seq,
+ "unexpected sequential hint for _open flags %x\n",
tests[i].mode);
+ close(fd);
+ }
+ unlink(tempfile);
+}
+
+static void test_ioinfo_flags(void)
+{
+ HANDLE handle;
+ ioinfo *info;
+ char *tempf;
+ int tempfd;
+
+ tempf = _tempnam(".","wne");
+
+ tempfd = _open(tempf, _O_CREAT|_O_TRUNC|_O_WRONLY|_O_WTEXT, _S_IWRITE);
+ ok(tempfd != -1, "_open failed with error: %d\n", errno);
+
+ handle = (HANDLE)_get_osfhandle(tempfd);
+ info = &__pioinfo[tempfd / MSVCRT_FD_BLOCK_SIZE][tempfd % MSVCRT_FD_BLOCK_SIZE];
+ ok(!!info, "NULL info.\n");
+ ok(info->handle == handle, "Unexpected handle %p, expected %p.\n",
info->handle, handle);
+ ok(info->exflag == (EF_UTF16 | EF_CRIT_INIT | EF_UNK_UNICODE), "Unexpected
exflag %#x.\n", info->exflag);
+ ok(info->wxflag == (WX_TEXT | WX_OPEN), "Unexpected wxflag %#x.\n",
info->wxflag);
+
+ close(tempfd);
+
+ ok(info->handle == INVALID_HANDLE_VALUE, "Unexpected handle %p.\n",
info->handle);
+ ok(info->exflag == (EF_UTF16 | EF_CRIT_INIT | EF_UNK_UNICODE), "Unexpected
exflag %#x.\n", info->exflag);
+ ok(!info->wxflag, "Unexpected wxflag %#x.\n", info->wxflag);
+
+ info = &__pioinfo[(tempfd + 4) / MSVCRT_FD_BLOCK_SIZE][(tempfd + 4) %
MSVCRT_FD_BLOCK_SIZE];
+ ok(!!info, "NULL info.\n");
+ ok(info->handle == INVALID_HANDLE_VALUE, "Unexpected handle %p.\n",
info->handle);
+ ok(!info->exflag, "Unexpected exflag %#x.\n", info->exflag);
+
+ unlink(tempf);
+ free(tempf);
+}
+
+static void test_std_stream_buffering(void)
+{
+ int dup_fd, ret, pos;
+ FILE *file;
+ char ch;
+
+ dup_fd = _dup(STDOUT_FILENO);
+ ok(dup_fd != -1, "_dup failed\n");
+
+ file = freopen("std_stream_test.tmp", "w", stdout);
+ ok(file != NULL, "freopen failed\n");
+
+ ret = fprintf(stdout, "test");
+ pos = _telli64(STDOUT_FILENO);
+
+ fflush(stdout);
+ _dup2(dup_fd, STDOUT_FILENO);
+ close(dup_fd);
+ setvbuf(stdout, NULL, _IONBF, 0);
+
+ ok(ret == 4, "fprintf(stdout) returned %d\n", ret);
+ ok(!pos, "expected stdout to be buffered\n");
+
+ dup_fd = _dup(STDERR_FILENO);
+ ok(dup_fd != -1, "_dup failed\n");
+
+ file = freopen("std_stream_test.tmp", "w", stderr);
+ ok(file != NULL, "freopen failed\n");
+
+ ret = fprintf(stderr, "test");
+ ok(ret == 4, "fprintf(stderr) returned %d\n", ret);
+ pos = _telli64(STDERR_FILENO);
+ ok(!pos, "expected stderr to be buffered\n");
+
+ fflush(stderr);
+ _dup2(dup_fd, STDERR_FILENO);
+ close(dup_fd);
+
+ dup_fd = _dup(STDIN_FILENO);
+ ok(dup_fd != -1, "_dup failed\n");
+
+ file = freopen("std_stream_test.tmp", "r", stdin);
+ ok(file != NULL, "freopen failed\n");
+
+ ch = 0;
+ ret = fscanf(stdin, "%c", &ch);
+ ok(ret == 1, "fscanf returned %d\n", ret);
+ ok(ch == 't', "ch = 0x%x\n", (unsigned char)ch);
+ pos = _telli64(STDIN_FILENO);
+ ok(pos == 4, "pos = %d\n", pos);
+
+ fflush(stdin);
+ _dup2(dup_fd, STDIN_FILENO);
+ close(dup_fd);
+
+ ok(DeleteFileA("std_stream_test.tmp"), "DeleteFile failed\n");
+}
+
+static void test_std_stream_open(void)
+{
+ FILE *f;
+ int fd;
+
+ fd = _dup(STDIN_FILENO);
+ ok(fd != -1, "_dup failed\n");
+
+ ok(!fclose(stdin), "fclose failed\n");
+ f = fopen("nul", "r");
+ ok(f == stdin, "f = %p, expected %p\n", f, stdin);
+ ok(_fileno(f) == STDIN_FILENO, "_fileno(f) = %d\n", _fileno(f));
+
+ _dup2(fd, STDIN_FILENO);
+ close(fd);
+}
+
START_TEST(file)
{
int arg_c;
@@ -2596,7 +3157,7 @@ START_TEST(file)
if (arg_c >= 3)
{
if (strcmp(arg_v[2], "inherit") == 0)
- test_file_inherit_child(arg_v[3]);
+ test_file_inherit_child(arg_v[3], arg_c > 4 ? arg_v[4] : NULL);
else if (strcmp(arg_v[2], "inherit_no") == 0)
test_file_inherit_child_no(arg_v[3]);
else if (strcmp(arg_v[2], "pipes") == 0)
@@ -2642,6 +3203,7 @@ START_TEST(file)
test_fgetwc_locale("AB\x83\xa9", "C", 0);
test_fgetwc_unicode();
test_fputwc();
+ test_freopen();
test_ctrlz();
test_file_put_get();
test_tmpnam();
@@ -2654,6 +3216,12 @@ START_TEST(file)
test_write_flush();
test_close();
test__creat();
+ test_lseek();
+ test_fopen_hints();
+ test_open_hints();
+ test_ioinfo_flags();
+ test_std_stream_buffering();
+ test_std_stream_open();
/* Wait for the (_P_NOWAIT) spawned processes to finish to make sure the report
* file contains lines in the correct order
diff --git a/modules/rostests/winetests/msvcrt/heap.c
b/modules/rostests/winetests/msvcrt/heap.c
index d934bf0c542..e8da95bb867 100644
--- a/modules/rostests/winetests/msvcrt/heap.c
+++ b/modules/rostests/winetests/msvcrt/heap.c
@@ -23,17 +23,13 @@
#include <errno.h>
#include "wine/test.h"
-#ifdef __REACTOS__
-#if defined(__GNUC__) && __GNUC__ >= 7
-#pragma GCC diagnostic ignored "-Walloc-size-larger-than=9223372036854775807"
-#endif
-#endif
-
-static void (__cdecl *p_aligned_free)(void*) = NULL;
-static void * (__cdecl *p_aligned_malloc)(size_t,size_t) = NULL;
-static void * (__cdecl *p_aligned_offset_malloc)(size_t,size_t,size_t) = NULL;
-static void * (__cdecl *p_aligned_realloc)(void*,size_t,size_t) = NULL;
-static void * (__cdecl *p_aligned_offset_realloc)(void*,size_t,size_t,size_t) = NULL;
+static void (__cdecl *p_aligned_free)(void*);
+static void * (__cdecl *p_aligned_malloc)(size_t,size_t);
+static void * (__cdecl *p_aligned_offset_malloc)(size_t,size_t,size_t);
+static void * (__cdecl *p_aligned_realloc)(void*,size_t,size_t);
+static void * (__cdecl *p_aligned_offset_realloc)(void*,size_t,size_t,size_t);
+static int (__cdecl *p__set_sbh_threshold)(size_t);
+static size_t (__cdecl *p__get_sbh_threshold)(void);
static void test_aligned_malloc(unsigned int size, unsigned int alignment)
{
@@ -421,28 +417,37 @@ static void test_aligned(void)
static void test_sbheap(void)
{
+ HMODULE msvcrt = GetModuleHandleA("msvcrt.dll");
void *mem;
int threshold;
+ p__set_sbh_threshold = (void*)GetProcAddress(msvcrt,
"_set_sbh_threshold");
+ p__get_sbh_threshold = (void*)GetProcAddress(msvcrt,
"_get_sbh_threshold");
+ if (!p__set_sbh_threshold || !p__get_sbh_threshold)
+ {
+ win_skip("_set_sbh_threshold not available\n");
+ return;
+ }
+
if(sizeof(void*) == 8) {
- ok(!_set_sbh_threshold(0), "_set_sbh_threshold succeeded\n");
- ok(!_set_sbh_threshold(1000), "_set_sbh_threshold succeeded\n");
+ ok(!p__set_sbh_threshold(0), "_set_sbh_threshold succeeded\n");
+ ok(!p__set_sbh_threshold(1000), "_set_sbh_threshold succeeded\n");
return;
}
mem = malloc(1);
ok(mem != NULL, "malloc failed\n");
- ok(_set_sbh_threshold(1), "_set_sbh_threshold failed\n");
- threshold = _get_sbh_threshold();
+ ok(p__set_sbh_threshold(1), "_set_sbh_threshold failed\n");
+ threshold = p__get_sbh_threshold();
ok(threshold == 16, "threshold = %d\n", threshold);
- ok(_set_sbh_threshold(8), "_set_sbh_threshold failed\n");
- threshold = _get_sbh_threshold();
+ ok(p__set_sbh_threshold(8), "_set_sbh_threshold failed\n");
+ threshold = p__get_sbh_threshold();
ok(threshold == 16, "threshold = %d\n", threshold);
- ok(_set_sbh_threshold(1000), "_set_sbh_threshold failed\n");
- threshold = _get_sbh_threshold();
+ ok(p__set_sbh_threshold(1000), "_set_sbh_threshold failed\n");
+ threshold = p__get_sbh_threshold();
ok(threshold == 1008, "threshold = %d\n", threshold);
free(mem);
@@ -455,13 +460,42 @@ static void test_sbheap(void)
ok(mem != NULL, "realloc failed\n");
ok(!((UINT_PTR)mem & 0xf), "incorrect alignment (%p)\n", mem);
- ok(_set_sbh_threshold(0), "_set_sbh_threshold failed\n");
- threshold = _get_sbh_threshold();
+ ok(p__set_sbh_threshold(0), "_set_sbh_threshold failed\n");
+ threshold = p__get_sbh_threshold();
ok(threshold == 0, "threshold = %d\n", threshold);
free(mem);
}
+static void test_malloc(void)
+{
+ /* use function pointers to bypass gcc builtins */
+ void *(__cdecl *p_malloc)(size_t);
+ void *(__cdecl *p_realloc)(void *,size_t);
+ void *mem;
+
+ p_malloc = (void *)GetProcAddress( GetModuleHandleA("msvcrt.dll"),
"malloc");
+ p_realloc = (void *)GetProcAddress( GetModuleHandleA("msvcrt.dll"),
"realloc");
+
+ mem = p_malloc(0);
+ ok(mem != NULL, "memory not allocated for size 0\n");
+ free(mem);
+
+ mem = p_realloc(NULL, 10);
+ ok(mem != NULL, "memory not allocated\n");
+
+ mem = p_realloc(mem, 20);
+ ok(mem != NULL, "memory not reallocated\n");
+
+ mem = p_realloc(mem, 0);
+ ok(mem == NULL, "memory not freed\n");
+
+ mem = p_realloc(NULL, 0);
+ ok(mem != NULL, "memory not (re)allocated for size 0\n");
+
+ free(mem);
+}
+
static void test_calloc(void)
{
/* use function pointer to bypass gcc builtin */
@@ -489,29 +523,16 @@ static void test_calloc(void)
free(ptr);
}
-START_TEST(heap)
+static void test__get_heap_handle(void)
{
- void *mem;
-
- mem = malloc(0);
- ok(mem != NULL, "memory not allocated for size 0\n");
- free(mem);
-
- mem = realloc(NULL, 10);
- ok(mem != NULL, "memory not allocated\n");
-
- mem = realloc(mem, 20);
- ok(mem != NULL, "memory not reallocated\n");
-
- mem = realloc(mem, 0);
- ok(mem == NULL, "memory not freed\n");
-
- mem = realloc(NULL, 0);
- ok(mem != NULL, "memory not (re)allocated for size 0\n");
-
- free(mem);
+ ok((HANDLE)_get_heap_handle() != GetProcessHeap(), "Expected _get_heap_handle()
not to return GetProcessHeap()\n");
+}
+START_TEST(heap)
+{
test_aligned();
test_sbheap();
+ test_malloc();
test_calloc();
+ test__get_heap_handle();
}
diff --git a/modules/rostests/winetests/msvcrt/locale.c
b/modules/rostests/winetests/msvcrt/locale.c
index 08abac00bed..62632ce4b9d 100644
--- a/modules/rostests/winetests/msvcrt/locale.c
+++ b/modules/rostests/winetests/msvcrt/locale.c
@@ -19,6 +19,7 @@
*/
#include <locale.h>
+#include <process.h>
#include "wine/test.h"
#include "winnls.h"
@@ -27,6 +28,9 @@ static BOOL (__cdecl *p__crtGetStringTypeW)(DWORD, DWORD, const
wchar_t*, int, W
static int (__cdecl *pmemcpy_s)(void *, size_t, void*, size_t);
static int (__cdecl *p___mb_cur_max_func)(void);
static int *(__cdecl *p__p___mb_cur_max)(void);
+static _locale_t(__cdecl *p_create_locale)(int, const char*);
+static void(__cdecl *p_free_locale)(_locale_t);
+static int (__cdecl *p_wcsicmp_l)(const wchar_t*, const wchar_t*, _locale_t);
void* __cdecl _Gettnames(void);
static void init(void)
@@ -37,6 +41,9 @@ static void init(void)
pmemcpy_s = (void*)GetProcAddress(hmod, "memcpy_s");
p___mb_cur_max_func = (void*)GetProcAddress(hmod, "___mb_cur_max_func");
p__p___mb_cur_max = (void*)GetProcAddress(hmod, "__p___mb_cur_max");
+ p_create_locale = (void*)GetProcAddress(hmod, "_create_locale");
+ p_free_locale = (void*)GetProcAddress(hmod, "_free_locale");
+ p_wcsicmp_l = (void*)GetProcAddress(hmod, "_wcsicmp_l");
}
static void test_setlocale(void)
@@ -45,6 +52,8 @@ static void test_setlocale(void)
"LC_MONETARY=Greek_Greece.1253;LC_NUMERIC=Polish_Poland.1250;LC_TIME=C";
char *ret, buf[100];
+ char *ptr;
+ int len;
ret = setlocale(20, "C");
ok(ret == NULL, "ret = %s\n", ret);
@@ -571,12 +580,14 @@ static void test_setlocale(void)
ret = setlocale(LC_ALL, "trk");
ok(ret != NULL || broken (ret == NULL), "ret == NULL\n");
if(ret)
- ok(!strcmp(ret, "Turkish_Turkey.1254"), "ret = %s\n", ret);
+ ok(!strcmp(ret, "Turkish_Turkey.1254")
+ || !strcmp(ret, "Turkish_T\xfcrkiye.1254"), "ret = %s\n",
ret);
ret = setlocale(LC_ALL, "turkish");
ok(ret != NULL || broken (ret == NULL), "ret == NULL\n");
if(ret)
- ok(!strcmp(ret, "Turkish_Turkey.1254"), "ret = %s\n", ret);
+ ok(!strcmp(ret, "Turkish_Turkey.1254")
+ || !strcmp(ret, "Turkish_T\xfcrkiye.1254"), "ret = %s\n",
ret);
ret = setlocale(LC_ALL, "uk");
ok(ret != NULL, "ret == NULL\n");
@@ -612,6 +623,27 @@ static void test_setlocale(void)
ok(!strcmp(ret, buf), "ret = %s, expected %s\n", ret, buf);
}
+ GetLocaleInfoA(GetUserDefaultLCID(), LOCALE_IDEFAULTCODEPAGE, buf, sizeof(buf));
+ if(IsValidCodePage(atoi(buf))) {
+ ret = setlocale(LC_ALL, ".OCP");
+ ok(ret != NULL, "ret == NULL\n");
+ ptr = strchr(ret, '.');
+ ok(ptr && !strcmp(ptr + 1, buf), "ret %s, buf %s.\n", ret,
buf);
+ }
+
+ len = GetLocaleInfoA(GetUserDefaultLCID(), LOCALE_IDEFAULTANSICODEPAGE, buf,
sizeof(buf)) - 1;
+ if(buf[0] == '0' && !buf[1])
+ len = sprintf(buf, "%d", GetACP());
+ ret = setlocale(LC_ALL, ".ACP");
+ ok(ret != NULL, "ret == NULL\n");
+ ptr = strchr(ret, '.');
+ ok(ptr && !strncmp(ptr + 1, buf, len), "ret %s, buf %s.\n", ret,
buf);
+
+ ret = setlocale(LC_ALL, ".1250");
+ ok(ret != NULL, "ret == NULL\n");
+ ptr = strchr(ret, '.');
+ ok(ptr && !strcmp(ptr, ".1250"), "ret %s, buf %s.\n",
ret, buf);
+
ret = setlocale(LC_ALL, "English_United States.UTF8");
ok(ret == NULL, "ret != NULL\n");
@@ -621,13 +653,7 @@ static void test_setlocale(void)
static void test_crtGetStringTypeW(void)
{
- static const wchar_t str0[] = { '0', '\0' };
- static const wchar_t strA[] = { 'A', '\0' };
- static const wchar_t str_space[] = { ' ', '\0' };
- static const wchar_t str_null[] = { '\0', '\0' };
- static const wchar_t str_rand[] = { 1234, '\0' };
-
- const wchar_t *str[] = { str0, strA, str_space, str_null, str_rand };
+ const wchar_t *str[] = { L"0", L"A", L" ",
L"\0", L"\x04d2" };
WORD out_crt, out;
BOOL ret_crt, ret;
@@ -712,10 +738,14 @@ static void test__Gettnames(void)
{
size = GetLocaleInfoA(MAKELCID(LANG_ENGLISH, SORT_DEFAULT),
time_data[i], buf, sizeof(buf));
- ok(size, "GetLocaleInfo failed: %x\n", GetLastError());
+ ok(size, "GetLocaleInfo failed: %lx\n", GetLastError());
ok(!strcmp(ret->str[i], buf), "ret->str[%i] = %s, expected %s\n",
i, ret->str[i], buf);
}
+ ok(ret->wstr[0] != NULL, "ret->wstr[0] = NULL\n");
+ ok(ret->str[42] + strlen(ret->str[42])+1 != (char*)ret->wstr[0],
+ "ret->str[42] = %p len = %Id, ret->wstr[0] = %p\n",
+ ret->str[42], strlen(ret->str[42]), ret->wstr[0]);
free(ret);
if(!setlocale(LC_TIME, "german"))
@@ -726,7 +756,7 @@ static void test__Gettnames(void)
{
size = GetLocaleInfoA(MAKELCID(LANG_GERMAN, SORT_DEFAULT),
time_data[i], buf, sizeof(buf));
- ok(size, "GetLocaleInfo failed: %x\n", GetLastError());
+ ok(size, "GetLocaleInfo failed: %lx\n", GetLastError());
ok(!strcmp(ret->str[i], buf), "ret->str[%i] = %s, expected %s\n",
i, ret->str[i], buf);
}
free(ret);
@@ -775,6 +805,178 @@ static void test___mb_cur_max_func(void)
}
}
+static void test__wcsicmp_l(void)
+{
+ const struct {
+ const wchar_t *str1;
+ const wchar_t *str2;
+ int exp;
+ const char *loc;
+ } tests[] = {
+ { L"i", L"i", 0 },
+ { L"I", L"i", 0 },
+ { L"I", L"i", 0, "Turkish" },
+ { L"i", L"a", 8 },
+ { L"a", L"i", -8 },
+ { L"i", L"a", 8, "Turkish" },
+ };
+ int ret, i;
+
+ if (!p_wcsicmp_l || !p_create_locale)
+ {
+ win_skip("_wcsicmp_l or _create_locale not available\n");
+ return;
+ }
+ ok(!!p_free_locale, "_free_locale not available\n");
+
+ for(i=0; i<ARRAY_SIZE(tests); i++) {
+ _locale_t loc = NULL;
+
+ if(tests[i].loc && !(loc = p_create_locale(LC_ALL, tests[i].loc))) {
+ win_skip("locale %s not available. skipping\n", tests[i].loc);
+ continue;
+ }
+
+ ret = p_wcsicmp_l(tests[i].str1, tests[i].str2, loc);
+ ok(ret == tests[i].exp, "_wcsicmp_l = %d, expected %d for test %d
'%ls' vs '%ls' using %s locale\n",
+ ret, tests[i].exp, i, tests[i].str1, tests[i].str2, loc ? tests[i].loc :
"current");
+
+ if(loc)
+ p_free_locale(loc);
+ }
+}
+
+static unsigned __stdcall test_thread_setlocale_func(void *arg)
+{
+ char *ret;
+
+ ret = setlocale(LC_ALL, NULL);
+ ok(!strcmp(ret, "C"), "expected ret=C, but received ret=%s\n",
ret);
+
+ ret = setlocale(LC_ALL, "");
+ ok(strcmp(ret, "Invariant Language_Invariant Country.0"), "expected
valid locale\n");
+
+ return 0;
+}
+
+static void test_thread_setlocale(void)
+{
+ HANDLE hThread;
+
+ hThread = (HANDLE)_beginthreadex(NULL, 0, test_thread_setlocale_func, NULL, 0,
NULL);
+ ok(hThread != INVALID_HANDLE_VALUE, "_beginthread failed (%d)\n", errno);
+ WaitForSingleObject(hThread, 5000);
+ CloseHandle(hThread);
+}
+
+static void test_locale_info(void)
+{
+ pthreadlocinfo locinfo, locinfo2;
+ _locale_t locale, locale2;
+ int ret;
+
+ if (!p_create_locale)
+ {
+ win_skip("_create_locale isn't available.\n");
+ return;
+ }
+
+ if (PRIMARYLANGID(GetUserDefaultLangID()) == LANG_JAPANESE)
+ skip("Skip language-specific tests on Japanese system.\n");
+ else
+ {
+ locale = p_create_locale(LC_ALL, "Japanese_Japan.932");
+ locale2 = p_create_locale(LC_ALL, ".932");
+ locinfo = locale->locinfo;
+ locinfo2 = locale2->locinfo;
+
+ ok(locinfo->mb_cur_max == locinfo2->mb_cur_max, "Got wrong max char
size %d %d.\n",
+ locinfo->mb_cur_max, locinfo2->mb_cur_max);
+ ok(locinfo->ctype1_refcount != locinfo2->ctype1_refcount, "Got wrong
refcount pointer %p vs %p.\n",
+ locinfo->ctype1_refcount, locinfo2->ctype1_refcount);
+ ok(locinfo->lc_codepage == 932 && locinfo->lc_codepage ==
locinfo2->lc_codepage,
+ "Got wrong codepage %d vs %d.\n", locinfo->lc_codepage,
locinfo2->lc_codepage);
+ ok(locinfo->lc_id[LC_CTYPE].wCodePage == 932
+ && locinfo->lc_id[LC_CTYPE].wCodePage ==
locinfo2->lc_id[LC_CTYPE].wCodePage,
+ "Got wrong LC_CTYPE codepage %d vs %d.\n",
locinfo->lc_id[LC_CTYPE].wCodePage,
+ locinfo2->lc_id[LC_CTYPE].wCodePage);
+ ret = strcmp(locinfo->lc_category[LC_CTYPE].locale,
locinfo2->lc_category[LC_CTYPE].locale);
+ ok(!!ret, "Got locale name %s vs %s.\n",
locinfo->lc_category[LC_CTYPE].locale,
+ locinfo2->lc_category[LC_CTYPE].locale);
+ ret = memcmp(locinfo->ctype1, locinfo2->ctype1, 257 *
sizeof(*locinfo->ctype1));
+ ok(!ret, "Got wrong ctype1 data.\n");
+ ret = memcmp(locinfo->pclmap, locinfo2->pclmap, 256 *
sizeof(*locinfo->pclmap));
+ ok(!ret, "Got wrong pclmap data.\n");
+ ret = memcmp(locinfo->pcumap, locinfo2->pcumap, 256 *
sizeof(*locinfo->pcumap));
+ ok(!ret, "Got wrong pcumap data.\n");
+ ok(locinfo->lc_handle[LC_CTYPE] != locinfo2->lc_handle[LC_CTYPE],
+ "Got wrong LC_CTYPE %#lx vs %#lx.\n",
locinfo->lc_handle[LC_CTYPE], locinfo2->lc_handle[LC_CTYPE]);
+
+ p_free_locale(locale2);
+ locale2 = p_create_locale(LC_ALL, "Japanese_Japan.1252");
+ locinfo2 = locale2->locinfo;
+
+ ok(locinfo->mb_cur_max != locinfo2->mb_cur_max, "Got wrong max char
size %d %d.\n",
+ locinfo->mb_cur_max, locinfo2->mb_cur_max);
+ ok(locinfo->ctype1_refcount != locinfo2->ctype1_refcount, "Got wrong
refcount pointer %p vs %p.\n",
+ locinfo->ctype1_refcount, locinfo2->ctype1_refcount);
+ ok(locinfo2->lc_codepage == 1252, "Got wrong codepage %d.\n",
locinfo2->lc_codepage);
+ ok(locinfo2->lc_id[LC_CTYPE].wCodePage == 1252, "Got wrong LC_CTYPE
codepage %d.\n",
+ locinfo2->lc_id[LC_CTYPE].wCodePage);
+ ok(locinfo->lc_codepage != locinfo2->lc_codepage, "Got wrong codepage
%d vs %d.\n",
+ locinfo->lc_codepage, locinfo2->lc_codepage);
+ ok(locinfo->lc_id[LC_CTYPE].wCodePage !=
locinfo2->lc_id[LC_CTYPE].wCodePage,
+ "Got wrong LC_CTYPE codepage %d vs %d.\n",
locinfo->lc_id[LC_CTYPE].wCodePage,
+ locinfo2->lc_id[LC_CTYPE].wCodePage);
+ ret = strcmp(locinfo->lc_category[LC_CTYPE].locale,
locinfo2->lc_category[LC_CTYPE].locale);
+ ok(!!ret, "Got locale name %s vs %s.\n",
locinfo->lc_category[LC_CTYPE].locale,
+ locinfo2->lc_category[LC_CTYPE].locale);
+ ret = memcmp(locinfo->ctype1, locinfo2->ctype1, 257 *
sizeof(*locinfo->ctype1));
+ ok(!!ret, "Got wrong ctype1 data.\n");
+ ret = memcmp(locinfo->pclmap, locinfo2->pclmap, 256 *
sizeof(*locinfo->pclmap));
+ ok(!!ret, "Got wrong pclmap data.\n");
+ ret = memcmp(locinfo->pcumap, locinfo2->pcumap, 256 *
sizeof(*locinfo->pcumap));
+ ok(!!ret, "Got wrong pcumap data.\n");
+ ok(locinfo->lc_handle[LC_CTYPE] == locinfo2->lc_handle[LC_CTYPE],
+ "Got wrong LC_CTYPE %#lx vs %#lx.\n",
locinfo->lc_handle[LC_CTYPE], locinfo2->lc_handle[LC_CTYPE]);
+
+ p_free_locale(locale2);
+ locale2 = p_create_locale(LC_ALL, "Japanese_Japan.3000"); /* an invalid
codepage */
+ ok(!locale2, "Got %p.\n", locale2);
+
+ p_free_locale(locale);
+ }
+
+ locale = p_create_locale(LC_ALL, "German_Germany.437");
+ locale2 = p_create_locale(LC_ALL, "German_Germany.1252");
+ locinfo = locale->locinfo;
+ locinfo2 = locale2->locinfo;
+
+ ok(locinfo->mb_cur_max == locinfo2->mb_cur_max, "Got wrong max char size
%d %d.\n",
+ locinfo->mb_cur_max, locinfo2->mb_cur_max);
+ ok(locinfo->ctype1_refcount != locinfo2->ctype1_refcount, "Got wrong
refcount pointer %p vs %p.\n",
+ locinfo->ctype1_refcount, locinfo2->ctype1_refcount);
+ ok(locinfo->lc_codepage != locinfo2->lc_codepage, "Got wrong codepage %d
vs %d.\n",
+ locinfo->lc_codepage, locinfo2->lc_codepage);
+ ok(locinfo->lc_id[LC_CTYPE].wCodePage != locinfo2->lc_id[LC_CTYPE].wCodePage,
+ "Got wrong LC_CTYPE codepage %d vs %d.\n",
locinfo->lc_id[LC_CTYPE].wCodePage,
+ locinfo2->lc_id[LC_CTYPE].wCodePage);
+ ret = strcmp(locinfo->lc_category[LC_CTYPE].locale,
locinfo2->lc_category[LC_CTYPE].locale);
+ ok(!!ret, "Got locale name %s vs %s.\n",
locinfo->lc_category[LC_CTYPE].locale,
+ locinfo2->lc_category[LC_CTYPE].locale);
+ ret = memcmp(locinfo->ctype1, locinfo2->ctype1, 257 *
sizeof(*locinfo->ctype1));
+ ok(!!ret, "Got wrong ctype1 data.\n");
+ ret = memcmp(locinfo->pclmap, locinfo2->pclmap, 256 *
sizeof(*locinfo->pclmap));
+ ok(!!ret, "Got wrong pclmap data.\n");
+ ret = memcmp(locinfo->pcumap, locinfo2->pcumap, 256 *
sizeof(*locinfo->pcumap));
+ ok(!!ret, "Got wrong pcumap data.\n");
+ ok(locinfo->lc_handle[LC_CTYPE] == locinfo2->lc_handle[LC_CTYPE],
+ "Got wrong LC_CTYPE %#lx vs %#lx.\n",
locinfo->lc_handle[LC_CTYPE], locinfo2->lc_handle[LC_CTYPE]);
+
+ p_free_locale(locale2);
+ p_free_locale(locale);
+}
+
START_TEST(locale)
{
init();
@@ -783,4 +985,7 @@ START_TEST(locale)
test_setlocale();
test__Gettnames();
test___mb_cur_max_func();
+ test__wcsicmp_l();
+ test_thread_setlocale();
+ test_locale_info();
}
diff --git a/modules/rostests/winetests/msvcrt/misc.c
b/modules/rostests/winetests/msvcrt/misc.c
index d82f71e122e..7b54b3aeb88 100644
--- a/modules/rostests/winetests/msvcrt/misc.c
+++ b/modules/rostests/winetests/msvcrt/misc.c
@@ -20,31 +20,12 @@
#include "wine/test.h"
#include <errno.h>
+#include <fcntl.h>
+#include <io.h>
#include <stdio.h>
#include <math.h>
-#include "msvcrt.h"
#include <process.h>
-static inline float __port_infinity(void)
-{
- static const unsigned __inf_bytes = 0x7f800000;
- return *(const float *)&__inf_bytes;
-}
-#ifdef __REACTOS__
-#undef INFINITY
-#endif
-#define INFINITY __port_infinity()
-
-static inline float __port_nan(void)
-{
- static const unsigned __nan_bytes = 0x7fc00000;
- return *(const float *)&__nan_bytes;
-}
-#ifdef __REACTOS__
-#undef NAN
-#endif
-#define NAN __port_nan()
-
static inline BOOL almost_equal(double d1, double d2) {
if(d1-d2>-1e-30 && d1-d2<1e-30)
return TRUE;
@@ -56,14 +37,14 @@ struct uld { ULONG lo, hi, exp; };
static int (__cdecl *prand_s)(unsigned int *);
static int (__cdecl *pI10_OUTPUT)(struct uld, int, int, void*);
-static int (__cdecl *pstrerror_s)(char *, MSVCRT_size_t, int);
+static int (__cdecl *pstrerror_s)(char *, size_t, int);
static int (__cdecl *p_get_doserrno)(int *);
static int (__cdecl *p_get_errno)(int *);
static int (__cdecl *p_set_doserrno)(int);
static int (__cdecl *p_set_errno)(int);
static void (__cdecl *p__invalid_parameter)(const wchar_t*,
const wchar_t*, const wchar_t*, unsigned int, uintptr_t);
-static void (__cdecl *p_qsort_s)(void*, MSVCRT_size_t, MSVCRT_size_t,
+static void (__cdecl *p_qsort_s)(void*, size_t, size_t,
int (__cdecl*)(void*, const void*, const void*), void*);
static double (__cdecl *p_atan)(double);
static double (__cdecl *p_exp)(double);
@@ -194,7 +175,7 @@ static void test_I10_OUTPUT(void)
j = strlen(I10_OUTPUT_tests[i].remain);
todo_wine_if(j && I10_OUTPUT_tests[i].remain[j-1]=='9')
ok(!strncmp(out.str+out.len+1, I10_OUTPUT_tests[i].remain, j),
- "%d: &out.str[%d] = %.25s...\n", i, out.len+1,
out.str+out.len+1);
+ "%d: &out.str[%d] = %.25s...\n", i, out.len+1,
out.str+out.len+1);
for(j=out.len+strlen(I10_OUTPUT_tests[i].remain)+1; j<sizeof(out.str); j++)
if(out.str[j] != '#')
@@ -233,7 +214,7 @@ static void test_strerror_s(void)
memset(buf, 'X', sizeof(buf));
ret = pstrerror_s(buf, 1, 0);
ok(ret == 0, "Expected strerror_s to return 0, got %d\n", ret);
- ok(strlen(buf) == 0, "Expected output buffer to be null terminated\n");
+ ok(buf[0] == 0, "Expected output buffer to be null terminated\n");
memset(buf, 'X', sizeof(buf));
ret = pstrerror_s(buf, 2, 0);
@@ -263,7 +244,7 @@ static void test__get_doserrno(void)
errno = EBADF;
ret = p_get_doserrno(NULL);
ok(ret == EINVAL, "Expected _get_doserrno to return EINVAL, got %d\n",
ret);
- ok(_doserrno == ERROR_INVALID_CMM, "Expected _doserrno to be ERROR_INVALID_CMM,
got %d\n", _doserrno);
+ ok(_doserrno == ERROR_INVALID_CMM, "Expected _doserrno to be ERROR_INVALID_CMM,
got %ld\n", _doserrno);
ok(errno == EBADF, "Expected errno to be EBADF, got %d\n", errno);
_doserrno = ERROR_INVALID_CMM;
@@ -310,19 +291,19 @@ static void test__set_doserrno(void)
ret = p_set_doserrno(ERROR_FILE_NOT_FOUND);
ok(ret == 0, "Expected _set_doserrno to return 0, got %d\n", ret);
ok(_doserrno == ERROR_FILE_NOT_FOUND,
- "Expected _doserrno to be ERROR_FILE_NOT_FOUND, got %d\n", _doserrno);
+ "Expected _doserrno to be ERROR_FILE_NOT_FOUND, got %ld\n", _doserrno);
_doserrno = ERROR_INVALID_CMM;
ret = p_set_doserrno(-1);
ok(ret == 0, "Expected _set_doserrno to return 0, got %d\n", ret);
ok(_doserrno == -1,
- "Expected _doserrno to be -1, got %d\n", _doserrno);
+ "Expected _doserrno to be -1, got %ld\n", _doserrno);
_doserrno = ERROR_INVALID_CMM;
ret = p_set_doserrno(0xdeadbeef);
ok(ret == 0, "Expected _set_doserrno to return 0, got %d\n", ret);
ok(_doserrno == 0xdeadbeef,
- "Expected _doserrno to be 0xdeadbeef, got %d\n", _doserrno);
+ "Expected _doserrno to be 0xdeadbeef, got %ld\n", _doserrno);
}
static void test__set_errno(void)
@@ -351,21 +332,42 @@ static void test__set_errno(void)
ok(errno == 0xdeadbeef, "Expected errno to be 0xdeadbeef, got %d\n",
errno);
}
-static void test__popen_child(void)
+static void test__popen_child(int fd)
{
/* don't execute any tests here */
/* ExitProcess is used to set return code of _pclose */
printf("child output\n");
+ if ((HANDLE)_get_osfhandle(fd) != INVALID_HANDLE_VALUE)
+ ExitProcess(1);
ExitProcess(0x37);
}
+static void test__popen_read_child(void)
+{
+ char buf[1024], *rets;
+
+ rets = fgets(buf, sizeof(buf), stdin);
+ if (strcmp(buf, "child-to-parent\n") != 0)
+ ExitProcess(1);
+
+ rets = fgets(buf, sizeof(buf), stdin);
+ if (rets)
+ ExitProcess(2);
+ ExitProcess(3);
+}
+
static void test__popen(const char *name)
{
FILE *pipe;
- char buf[1024];
- int ret;
+ char *tempf, buf[1024];
+ int ret, fd;
+
+ tempf = _tempnam(".", "wne");
+ ok(tempf != NULL, "_tempnam failed\n");
+ fd = _open(tempf, _O_CREAT | _O_WRONLY);
+ ok(fd != -1, "open failed\n");
- sprintf(buf, "\"%s\" misc popen", name);
+ sprintf(buf, "\"%s\" misc popen %d", name, fd);
pipe = _popen(buf, "r");
ok(pipe != NULL, "_popen failed with error: %d\n", errno);
@@ -374,12 +376,25 @@ static void test__popen(const char *name)
ret = _pclose(pipe);
ok(ret == 0x37, "_pclose returned %x, expected 0x37\n", ret);
+ _close(fd);
+ _unlink(tempf);
+ free(tempf);
errno = 0xdeadbeef;
ret = _pclose((FILE*)0xdeadbeef);
ok(ret == -1, "_pclose returned %x, expected -1\n", ret);
if(p_set_errno)
ok(errno == EBADF, "errno = %d\n", errno);
+
+ sprintf(buf, "\"%s\" misc popen_read", name);
+ pipe = _popen(buf, "w");
+ ok(pipe != NULL, "_popen failed with error: %d\n", errno);
+
+ ret = fputs("child-to-parent\n", pipe);
+ ok(ret != EOF, "fputs returned %x\n", ret);
+
+ ret = _pclose(pipe);
+ ok(ret == 0x3, "_pclose returned %x, expected 0x3\n", ret);
}
static void test__invalid_parameter(void)
@@ -512,8 +527,35 @@ static void test_qsort_s(void)
ok(tab[i] == i, "data sorted incorrectly on position %d: %d\n", i,
tab[i]);
}
+static int eq_nan(UINT64 ai, double b)
+{
+ UINT64 bi = *(UINT64*)&b;
+ UINT64 mask;
+
+#if defined(__i386__)
+ mask = 0xFFFFFFFF00000000ULL;
+#else
+ mask = ~0;
+#endif
+
+ ok((ai & mask) == (bi & mask), "comparing %s and %s\n",
+ wine_dbgstr_longlong(ai), wine_dbgstr_longlong(bi));
+ return (ai & mask) == (bi & mask);
+}
+
+static int eq_nanf(DWORD ai, float b)
+{
+ DWORD bi = *(DWORD*)&b;
+ ok(ai == bi, "comparing %08lx and %08lx\n", ai, bi);
+ return ai == bi;
+}
+
static void test_math_functions(void)
{
+ static const UINT64 test_nan_i = 0xFFF0000123456780ULL;
+ static const DWORD test_nanf_i = 0xFF801234;
+ double test_nan = *(double*)&test_nan_i;
+ float test_nanf = *(float*)&test_nanf_i;
double ret;
errno = 0xdeadbeef;
@@ -546,6 +588,13 @@ static void test_math_functions(void)
errno = 0xdeadbeef;
p_exp(INFINITY);
ok(errno == 0xdeadbeef, "errno = %d\n", errno);
+
+ ok(eq_nan(test_nan_i | (1ULL << 51), cosh(test_nan)), "cosh not preserving
nan\n");
+ ok(eq_nan(test_nan_i | (1ULL << 51), sinh(test_nan)), "sinh not preserving
nan\n");
+ ok(eq_nan(test_nan_i | (1ULL << 51), tanh(test_nan)), "tanh not preserving
nan\n");
+ ok(eq_nanf(test_nanf_i | (1 << 22), coshf(test_nanf)), "coshf not
preserving nan\n");
+ ok(eq_nanf(test_nanf_i | (1 << 22), sinhf(test_nanf)), "sinhf not
preserving nan\n");
+ ok(eq_nanf(test_nanf_i | (1 << 22), tanhf(test_nanf)), "tanhf not
preserving nan\n");
}
static void __cdecl test_thread_func(void *end_thread_type)
@@ -574,38 +623,51 @@ static void test_thread_handle_close(void)
ok(hThread != INVALID_HANDLE_VALUE, "_beginthread failed (%d)\n", errno);
WaitForSingleObject(hThread, INFINITE);
ret = CloseHandle(hThread);
- ok(!ret, "ret = %d\n", ret);
+ ok(!ret, "ret = %ld\n", ret);
hThread = (HANDLE)_beginthread(test_thread_func, 0, (void*)1);
ok(hThread != INVALID_HANDLE_VALUE, "_beginthread failed (%d)\n", errno);
WaitForSingleObject(hThread, INFINITE);
ret = CloseHandle(hThread);
- ok(!ret, "ret = %d\n", ret);
+ ok(!ret, "ret = %ld\n", ret);
hThread = (HANDLE)_beginthread(test_thread_func, 0, (void*)2);
ok(hThread != INVALID_HANDLE_VALUE, "_beginthread failed (%d)\n", errno);
Sleep(150);
ret = WaitForSingleObject(hThread, INFINITE);
- ok(ret == WAIT_OBJECT_0, "ret = %d\n", ret);
+ ok(ret == WAIT_OBJECT_0, "ret = %ld\n", ret);
ret = CloseHandle(hThread);
- ok(ret, "ret = %d\n", ret);
+ ok(ret, "ret = %ld\n", ret);
hThread = (HANDLE)_beginthread(test_thread_func, 0, (void*)3);
ok(hThread != INVALID_HANDLE_VALUE, "_beginthread failed (%d)\n", errno);
Sleep(150);
ret = WaitForSingleObject(hThread, INFINITE);
- ok(ret == WAIT_OBJECT_0, "ret = %d\n", ret);
+ ok(ret == WAIT_OBJECT_0, "ret = %ld\n", ret);
ret = CloseHandle(hThread);
- ok(ret, "ret = %d\n", ret);
+ ok(ret, "ret = %ld\n", ret);
/* _beginthreadex: handle is not closed on _endthread */
hThread = (HANDLE)_beginthreadex(NULL,0, test_thread_func_ex, NULL, 0, NULL);
ok(hThread != NULL, "_beginthreadex failed (%d)\n", errno);
Sleep(150);
ret = WaitForSingleObject(hThread, INFINITE);
- ok(ret == WAIT_OBJECT_0, "ret = %d\n", ret);
+ ok(ret == WAIT_OBJECT_0, "ret = %ld\n", ret);
ret = CloseHandle(hThread);
- ok(ret, "ret = %d\n", ret);
+ ok(ret, "ret = %ld\n", ret);
+}
+
+static void test_thread_suspended(void)
+{
+ HANDLE hThread;
+ DWORD ret;
+
+ hThread = (HANDLE)_beginthreadex(NULL, 0, test_thread_func_ex, NULL,
CREATE_SUSPENDED, NULL);
+ ok(hThread != NULL, "_beginthreadex failed (%d)\n", errno);
+ ret = ResumeThread(hThread);
+ ok(ret == 1, "suspend count = %ld\n", ret);
+ ret = WaitForSingleObject(hThread, 200);
+ ok(ret == WAIT_OBJECT_0, "ret = %ld\n", ret);
}
static int __cdecl _lfind_s_comp(void *ctx, const void *l, const void *r)
@@ -685,8 +747,10 @@ START_TEST(misc)
arg_c = winetest_get_mainargs(&arg_v);
if(arg_c >= 3) {
- if(!strcmp(arg_v[2], "popen"))
- test__popen_child();
+ if (!strcmp(arg_v[2], "popen_read"))
+ test__popen_read_child();
+ else if(arg_c == 4 && !strcmp(arg_v[2], "popen"))
+ test__popen_child(atoi(arg_v[3]));
else
ok(0, "invalid argument '%s'\n", arg_v[2]);
@@ -705,5 +769,6 @@ START_TEST(misc)
test_qsort_s();
test_math_functions();
test_thread_handle_close();
+ test_thread_suspended();
test__lfind_s();
}
diff --git a/modules/rostests/winetests/msvcrt/printf.c
b/modules/rostests/winetests/msvcrt/printf.c
index 4bf55afc1ff..dc0038b3372 100644
--- a/modules/rostests/winetests/msvcrt/printf.c
+++ b/modules/rostests/winetests/msvcrt/printf.c
@@ -23,9 +23,7 @@
/* With Visual Studio >= 2005, swprintf() takes an extra parameter unless
* the following macro is defined.
*/
-#ifndef _CRT_NON_CONFORMING_SWPRINTFS
#define _CRT_NON_CONFORMING_SWPRINTFS
-#endif
#include <stdio.h>
#include <errno.h>
@@ -38,24 +36,6 @@
#include "wine/test.h"
-#ifndef __REACTOS__
-
-static inline float __port_infinity(void)
-{
- static const unsigned __inf_bytes = 0x7f800000;
- return *(const float *)&__inf_bytes;
-}
-#define INFINITY __port_infinity()
-
-static inline float __port_nan(void)
-{
- static const unsigned __nan_bytes = 0x7fc00000;
- return *(const float *)&__nan_bytes;
-}
-#define NAN __port_nan()
-
-#endif
-
static inline float __port_ind(void)
{
static const unsigned __ind_bytes = 0xffc00000;
@@ -63,11 +43,11 @@ static inline float __port_ind(void)
}
#define IND __port_ind()
-static int (__cdecl *p__vscprintf)(const char *format, __ms_va_list valist);
-static int (__cdecl *p__vscwprintf)(const wchar_t *format, __ms_va_list valist);
+static int (__cdecl *p__vscprintf)(const char *format, va_list valist);
+static int (__cdecl *p__vscwprintf)(const wchar_t *format, va_list valist);
static int (__cdecl *p__vsnwprintf_s)(wchar_t *str, size_t sizeOfBuffer,
size_t count, const wchar_t *format,
- __ms_va_list valist);
+ va_list valist);
static int (__cdecl *p__ecvt_s)(char *buffer, size_t length, double number,
int ndigits, int *decpt, int *sign);
static int (__cdecl *p__fcvt_s)(char *buffer, size_t length, double number,
@@ -75,17 +55,17 @@ static int (__cdecl *p__fcvt_s)(char *buffer, size_t length, double
number,
static unsigned int (__cdecl *p__get_output_format)(void);
static unsigned int (__cdecl *p__set_output_format)(unsigned int);
static int (WINAPIV *p_sprintf)(char*, ...);
-static int (__cdecl *p__vsprintf_p)(char*, size_t, const char*, __ms_va_list);
-static int (__cdecl *p_vswprintf)(wchar_t *str, const wchar_t *format, __ms_va_list
valist);
-static int (__cdecl *p__vswprintf)(wchar_t *str, const wchar_t *format, __ms_va_list
valist);
+static int (__cdecl *p__vsprintf_p)(char*, size_t, const char*, va_list);
+static int (__cdecl *p_vswprintf)(wchar_t *str, const wchar_t *format, va_list valist);
+static int (__cdecl *p__vswprintf)(wchar_t *str, const wchar_t *format, va_list valist);
static int (__cdecl *p__vswprintf_l)(wchar_t *str, const wchar_t *format,
- void *locale, __ms_va_list valist);
+ void *locale, va_list valist);
static int (__cdecl *p__vswprintf_c)(wchar_t *str, size_t size, const wchar_t *format,
- __ms_va_list valist);
+ va_list valist);
static int (__cdecl *p__vswprintf_c_l)(wchar_t *str, size_t size, const wchar_t *format,
- void *locale, __ms_va_list valist);
+ void *locale, va_list valist);
static int (__cdecl *p__vswprintf_p_l)(wchar_t *str, size_t size, const wchar_t *format,
- void *locale, __ms_va_list valist);
+ void *locale, va_list valist);
static void init( void )
{
@@ -110,466 +90,295 @@ static void init( void )
static void test_sprintf( void )
{
- char buffer[100];
- const char *format;
- double pnumber=789456123;
- int x, r;
- WCHAR wide[] = { 'w','i','d','e',0};
- WCHAR buf_w[2];
-
- format = "%+#23.15e";
- r = p_sprintf(buffer,format,pnumber);
- ok(!strcmp(buffer,"+7.894561230000000e+008"),"+#23.15e failed:
'%s'\n", buffer);
- ok( r==23, "return count wrong\n");
-
- format = "%-#23.15e";
- r = p_sprintf(buffer,format,pnumber);
- ok(!strcmp(buffer,"7.894561230000000e+008 "),"-#23.15e failed:
'%s'\n", buffer);
- ok( r==23, "return count wrong\n");
-
- format = "%#23.15e";
- r = p_sprintf(buffer,format,pnumber);
- ok(!strcmp(buffer," 7.894561230000000e+008"),"#23.15e failed:
'%s'\n", buffer);
- ok( r==23, "return count wrong\n");
-
- format = "%#1.1g";
- r = p_sprintf(buffer,format,pnumber);
- ok(!strcmp(buffer,"8.e+008"),"#1.1g failed: '%s'\n",
buffer);
- ok( r==7, "return count wrong\n");
-
- format = "%I64d";
- r = p_sprintf(buffer,format,((ULONGLONG)0xffffffff)*0xffffffff);
- ok(!strcmp(buffer,"-8589934591"),"Problem with long long\n");
- ok( r==11, "return count wrong\n");
-
- format = "%+8I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer," +100") && r==8,"+8I64d failed:
'%s'\n", buffer);
-
- format = "%+.8I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer,"+00000100") && r==9,"+.8I64d failed:
'%s'\n", buffer);
-
- format = "%+10.8I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer," +00000100") && r==10,"+10.8I64d failed:
'%s'\n", buffer);
- format = "%_1I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer,"_1I64d") && r==6,"_1I64d failed\n");
-
- format = "%-1.5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer,"-00100") && r==6,"-1.5I64d failed:
'%s'\n", buffer);
-
- format = "%5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer," 100") && r==5,"5I64d failed:
'%s'\n", buffer);
-
- format = "%5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer," -100") && r==5,"5I64d failed:
'%s'\n", buffer);
-
- format = "%-5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer,"100 ") && r==5,"-5I64d failed:
'%s'\n", buffer);
-
- format = "%-5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer,"-100 ") && r==5,"-5I64d failed:
'%s'\n", buffer);
-
- format = "%-.5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer,"00100") && r==5,"-.5I64d failed:
'%s'\n", buffer);
-
- format = "%-.5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer,"-00100") && r==6,"-.5I64d failed:
'%s'\n", buffer);
-
- format = "%-8.5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer,"00100 ") && r==8,"-8.5I64d failed:
'%s'\n", buffer);
-
- format = "%-8.5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer,"-00100 ") && r==8,"-8.5I64d failed:
'%s'\n", buffer);
-
- format = "%05I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer,"00100") && r==5,"05I64d failed:
'%s'\n", buffer);
-
- format = "%05I64d";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer,"-0100") && r==5,"05I64d failed:
'%s'\n", buffer);
-
- format = "% I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer," 100") && r==4,"' I64d' failed:
'%s'\n", buffer);
-
- format = "% I64d";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer,"-100") && r==4,"' I64d' failed:
'%s'\n", buffer);
-
- format = "% 5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer," 100") && r==5,"' 5I64d' failed:
'%s'\n", buffer);
-
- format = "% 5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer," -100") && r==5,"' 5I64d' failed:
'%s'\n", buffer);
-
- format = "% .5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer," 00100") && r==6,"' .5I64d' failed:
'%s'\n", buffer);
-
- format = "% .5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer,"-00100") && r==6,"' .5I64d' failed:
'%s'\n", buffer);
-
- format = "% 8.5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer," 00100") && r==8,"' 8.5I64d'
failed: '%s'\n", buffer);
-
- format = "% 8.5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer," -00100") && r==8,"' 8.5I64d'
failed: '%s'\n", buffer);
-
- format = "%.0I64d";
- r = p_sprintf(buffer,format,(LONGLONG)0);
- ok(r==0,".0I64d failed: '%s'\n", buffer);
-
- format = "%#+21.18I64x";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer," 0x00ffffffffffffff9c") &&
r==21,"#+21.18I64x failed: '%s'\n", buffer);
-
- format = "%#.25I64o";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer,"0001777777777777777777634") &&
r==25,"#.25I64o failed: '%s'\n", buffer);
-
- format = "%#+24.20I64o";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer," 01777777777777777777634") &&
r==24,"#+24.20I64o failed: '%s'\n", buffer);
-
- format = "%#+18.21I64X";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer,"0X00000FFFFFFFFFFFFFF9C") &&
r==23,"#+18.21I64X failed: '%s '\n", buffer);
-
- format = "%#+20.24I64o";
- r = p_sprintf(buffer,format,(LONGLONG)-100);
- ok(!strcmp(buffer,"001777777777777777777634") &&
r==24,"#+20.24I64o failed: '%s'\n", buffer);
-
- format = "%#+25.22I64u";
- r = p_sprintf(buffer,format,(LONGLONG)-1);
- ok(!strcmp(buffer," 0018446744073709551615") &&
r==25,"#+25.22I64u conversion failed: '%s'\n", buffer);
-
- format = "%#+25.22I64u";
- r = p_sprintf(buffer,format,(LONGLONG)-1);
- ok(!strcmp(buffer," 0018446744073709551615") &&
r==25,"#+25.22I64u failed: '%s'\n", buffer);
-
- format = "%#+30.25I64u";
- r = p_sprintf(buffer,format,(LONGLONG)-1);
- ok(!strcmp(buffer," 0000018446744073709551615") &&
r==30,"#+30.25I64u failed: '%s'\n", buffer);
-
- format = "%+#25.22I64d";
- r = p_sprintf(buffer,format,(LONGLONG)-1);
- ok(!strcmp(buffer," -0000000000000000000001") &&
r==25,"+#25.22I64d failed: '%s'\n", buffer);
-
- format = "%#-8.5I64o";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer,"00144 ") && r==8,"-8.5I64o failed:
'%s'\n", buffer);
-
- format = "%#-+ 08.5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer,"+00100 ") && r==8,"'#-+ 08.5I64d
failed: '%s'\n", buffer);
-
- format = "%#-+ 08.5I64d";
- r = p_sprintf(buffer,format,(LONGLONG)100);
- ok(!strcmp(buffer,"+00100 ") && r==8,"#-+ 08.5I64d failed:
'%s'\n", buffer);
-
- format = "%.80I64d";
- r = p_sprintf(buffer,format,(LONGLONG)1);
- ok(r==80,"%s format failed\n", format);
-
- format = "% .80I64d";
- r = p_sprintf(buffer,format,(LONGLONG)1);
- ok(r==81,"%s format failed\n", format);
-
- format = "% .80d";
- r = p_sprintf(buffer,format,1);
- ok(r==81,"%s format failed\n", format);
-
- format = "%lld";
- r = p_sprintf(buffer,format,((ULONGLONG)0xffffffff)*0xffffffff);
- ok( r == 1 || r == 11, "return count wrong %d\n", r);
- if (r == 11) /* %ll works on Vista */
- ok(!strcmp(buffer, "-8589934591"), "Problem with \"ll\"
interpretation '%s'\n", buffer);
- else
- ok(!strcmp(buffer, "1"), "Problem with \"ll\"
interpretation '%s'\n", buffer);
+ enum {
+ NO_ARG,
+ INT_ARG,
+ ULONGLONG_ARG,
+ DOUBLE_ARG,
+ PTR_ARG,
+ TODO_FLAG = 0x1000
+ };
- format = "%I";
- r = p_sprintf(buffer,format,1);
- ok(!strcmp(buffer, "I"), "Problem with \"I\"
interpretation\n");
- ok( r==1, "return count wrong\n");
+ struct {
+ const char *format;
+ const char *out;
+ const char *broken;
+ int type;
+ int arg_i;
+ ULONGLONG arg_ull;
+ double arg_d;
+ const void *arg_ptr;
+ } tests[] = {
+ { "%+#23.15e", "+7.894561230000000e+008", 0, DOUBLE_ARG, 0,
0, 789456123 },
+ { "%-#23.15e", "7.894561230000000e+008 ", 0, DOUBLE_ARG, 0,
0, 789456123 },
+ { "%#23.15e", " 7.894561230000000e+008", 0, DOUBLE_ARG, 0, 0,
789456123 },
+ { "%#1.1g", "8.e+008", 0, DOUBLE_ARG, 0, 0, 789456123 },
+ { "%I64d", "-8589934591", 0, ULONGLONG_ARG, 0,
((ULONGLONG)0xffffffff)*0xffffffff },
+ { "%+8I64d", " +100", 0, ULONGLONG_ARG, 0, 100 },
+ { "%+.8I64d", "+00000100", 0, ULONGLONG_ARG, 0, 100 },
+ { "%+10.8I64d", " +00000100", 0, ULONGLONG_ARG, 0, 100 },
+ { "%_1I64d", "_1I64d", 0, ULONGLONG_ARG, 0, 100 },
+ { "%-1.5I64d", "-00100", 0, ULONGLONG_ARG, 0, -100 },
+ { "%5I64d", " 100", 0, ULONGLONG_ARG, 0, 100 },
+ { "%5I64d", " -100", 0, ULONGLONG_ARG, 0, -100 },
+ { "%-5I64d", "100 ", 0, ULONGLONG_ARG, 0, 100 },
+ { "%-5I64d", "-100 ", 0, ULONGLONG_ARG, 0, -100 },
+ { "%-.5I64d", "00100", 0, ULONGLONG_ARG, 0, 100 },
+ { "%-.5I64d", "-00100", 0, ULONGLONG_ARG, 0, -100 },
+ { "%-8.5I64d", "00100 ", 0, ULONGLONG_ARG, 0, 100 },
+ { "%-8.5I64d", "-00100 ", 0, ULONGLONG_ARG, 0, -100 },
+ { "%05I64d", "00100", 0, ULONGLONG_ARG, 0, 100 },
+ { "%05I64d", "-0100", 0, ULONGLONG_ARG, 0, -100 },
+ { "% I64d", " 100", 0, ULONGLONG_ARG, 0, 100 },
+ { "% I64d", "-100", 0, ULONGLONG_ARG, 0, -100 },
+ { "% 5I64d", " 100", 0, ULONGLONG_ARG, 0, 100 },
+ { "% 5I64d", " -100", 0, ULONGLONG_ARG, 0, -100 },
+ { "% .5I64d", " 00100", 0, ULONGLONG_ARG, 0, 100 },
+ { "% .5I64d", "-00100", 0, ULONGLONG_ARG, 0, -100 },
+ { "% 8.5I64d", " 00100", 0, ULONGLONG_ARG, 0, 100 },
+ { "% 8.5I64d", " -00100", 0, ULONGLONG_ARG, 0, -100 },
+ { "%.0I64d", "", 0, ULONGLONG_ARG },
+ { "%#+21.18I64x", " 0x00ffffffffffffff9c", 0, ULONGLONG_ARG,
0, -100 },
+ { "%#.25I64o", "0001777777777777777777634", 0, ULONGLONG_ARG,
0, -100 },
+ { "%#+24.20I64o", " 01777777777777777777634", 0,
ULONGLONG_ARG, 0, -100 },
+ { "%#+18.21I64X", "0X00000FFFFFFFFFFFFFF9C", 0,
ULONGLONG_ARG, 0, -100 },
+ { "%#+20.24I64o", "001777777777777777777634", 0,
ULONGLONG_ARG, 0, -100 },
+ { "%#+25.22I64u", " 0018446744073709551615", 0,
ULONGLONG_ARG, 0, -1 },
+ { "%#+25.22I64u", " 0018446744073709551615", 0,
ULONGLONG_ARG, 0, -1 },
+ { "%#+30.25I64u", " 0000018446744073709551615", 0,
ULONGLONG_ARG, 0, -1 },
+ { "%+#25.22I64d", " -0000000000000000000001", 0,
ULONGLONG_ARG, 0, -1 },
+ { "%#-8.5I64o", "00144 ", 0, ULONGLONG_ARG, 0, 100 },
+ { "%#-+ 08.5I64d", "+00100 ", 0, ULONGLONG_ARG, 0, 100 },
+ { "%.80I64d",
+
"00000000000000000000000000000000000000000000000000000000000000000000000000000001",
+ 0, ULONGLONG_ARG, 0, 1 },
+ { "% .80I64d",
+ "
00000000000000000000000000000000000000000000000000000000000000000000000000000001",
+ 0, ULONGLONG_ARG, 0, 1 },
+ { "% .80d",
+ "
00000000000000000000000000000000000000000000000000000000000000000000000000000001",
+ 0, INT_ARG, 1 },
+ { "%I", "I", 0, INT_ARG, 1 },
+ { "%Iq", "Iq", 0, INT_ARG, 1 },
+ { "%Ihd", "Ihd", 0, INT_ARG, 1 },
+ { "%I0d", "I0d", 0, INT_ARG, 1 },
+ { "%I64D", "D", 0, ULONGLONG_ARG, 0, -1 },
+ { "%zx", "1", "zx", INT_ARG, 1 },
+ { "%z", "z", 0, INT_ARG, 1 },
+ { "%tx", "1", "tx", INT_ARG, 1 },
+ { "%t", "t", 0, INT_ARG, 1 },
+ { "% d", " 1", 0, INT_ARG, 1 },
+ { "%+ d", "+1", 0, INT_ARG, 1 },
+ { "%S", "wide", 0, PTR_ARG, 0, 0, 0, L"wide" },
+ { "%04c", "0001", 0, INT_ARG, '1' },
+ { "%-04c", "1 ", 0, INT_ARG, '1' },
+ { "%#012x", "0x0000000001", 0, INT_ARG, 1 },
+ { "%#012x", "000000000000", 0, INT_ARG, 0 },
+ { "%#04.8x", "0x00000001", 0, INT_ARG, 1 },
+ { "%#04.8x", "00000000", 0, INT_ARG, 0 },
+ { "%#-08.2x", "0x01 ", 0, INT_ARG, 1 },
+ { "%#-08.2x", "00 ", 0, INT_ARG, 0 },
+ { "%#.0x", "0x1", 0, INT_ARG, 1 },
+ { "%#.0x", "", 0, INT_ARG, 0 },
+ { "%#08o", "00000001", 0, INT_ARG, 1 },
+ { "%#o", "01", 0, INT_ARG, 1 },
+ { "%#o", "0", 0, INT_ARG, 0 },
+ { "%04s", "0foo", 0, PTR_ARG, 0, 0, 0, "foo" },
+ { "%.1s", "f", 0, PTR_ARG, 0, 0, 0, "foo" },
+ { "hello", "hello", 0, NO_ARG },
+ { "%ws", "wide", 0, PTR_ARG, 0, 0, 0, L"wide" },
+ { "%-10ws", "wide ", 0, PTR_ARG, 0, 0, 0,
L"wide" },
+ { "%10ws", " wide", 0, PTR_ARG, 0, 0, 0,
L"wide" },
+ { "%#+ -03whlls", "wide", 0, PTR_ARG, 0, 0, 0,
L"wide" },
+ { "%w0s", "0s", 0, PTR_ARG, 0, 0, 0, L"wide" },
+ { "%w-s", "-s", 0, PTR_ARG, 0, 0, 0, L"wide" },
+ { "%ls", "wide", 0, PTR_ARG, 0, 0, 0, L"wide" },
+ { "%Ls", "not wide", 0, PTR_ARG, 0, 0, 0, "not
wide" },
+ { "%b", "b", 0, NO_ARG },
+ { "%3c", " a", 0, INT_ARG, 'a' },
+ { "%3d", "1234", 0, INT_ARG, 1234 },
+ { "%3h", "", 0, NO_ARG },
+ { "%k%m%q%r%t%v%y%z", "kmqrtvyz", 0, NO_ARG },
+ { "%-1d", "2", 0, INT_ARG, 2 },
+ { "%2.4f", "8.6000", 0, DOUBLE_ARG, 0, 0, 8.6 },
+ { "%0f", "0.600000", 0, DOUBLE_ARG, 0, 0, 0.6 },
+ { "%.0f", "1", 0, DOUBLE_ARG, 0, 0, 0.6 },
+ { "%2.4e", "8.6000e+000", 0, DOUBLE_ARG, 0, 0, 8.6 },
+ { "% 2.4e", " 8.6000e+000", 0, DOUBLE_ARG, 0, 0, 8.6 },
+ { "% 014.4e", " 008.6000e+000", 0, DOUBLE_ARG, 0, 0, 8.6 },
+ { "% 2.4e", "-8.6000e+000", 0, DOUBLE_ARG, 0, 0, -8.6 },
+ { "%+2.4e", "+8.6000e+000", 0, DOUBLE_ARG, 0, 0, 8.6 },
+ { "%2.4g", "8.6", 0, DOUBLE_ARG, 0, 0, 8.6 },
+ { "%-i", "-1", 0, INT_ARG, -1 },
+ { "%-i", "1", 0, INT_ARG, 1 },
+ { "%+i", "+1", 0, INT_ARG, 1 },
+ { "%o", "12", 0, INT_ARG, 10 },
+ { "%s", "(null)", 0, PTR_ARG, 0, 0, 0, NULL },
+ { "%s", "%%%%", 0, PTR_ARG, 0, 0, 0, "%%%%" },
+ { "%u", "4294967295", 0, INT_ARG, -1 },
+ { "%w", "", 0, INT_ARG, -1 },
+ { "%h", "", 0, INT_ARG, -1 },
+ { "%j", "", "j", ULONGLONG_ARG, 0, -1 },
+ { "%jd", "-1", "jd", ULONGLONG_ARG, 0, -1 },
+ { "%F", "", 0, INT_ARG, -1 },
+ { "%N", "", 0, INT_ARG, -1 },
+ { "%H", "H", 0, INT_ARG, -1 },
+ { "x%cx", "xXx", 0, INT_ARG, 0x100+'X' },
+ { "%%0", "%0", 0, NO_ARG },
+ { "%hx", "2345", 0, INT_ARG, 0x12345 },
+ { "%hhx", "123", 0, INT_ARG, 0x123 },
+ { "%hhx", "2345", 0, INT_ARG, 0x12345 },
+ { "%lf", "-1.#IND00", 0, DOUBLE_ARG, 0, 0, IND },
+ { "%lf", "1.#QNAN0", 0, DOUBLE_ARG, 0, 0, NAN },
+ { "%lf", "1.#INF00", 0, DOUBLE_ARG, 0, 0, INFINITY },
+ { "%le", "-1.#IND00e+000", 0, DOUBLE_ARG, 0, 0, IND },
+ { "%le", "1.#QNAN0e+000", 0, DOUBLE_ARG, 0, 0, NAN },
+ { "%le", "1.#INF00e+000", 0, DOUBLE_ARG, 0, 0, INFINITY },
+ { "%lg", "-1.#IND", 0, DOUBLE_ARG, 0, 0, IND },
+ { "%lg", "1.#QNAN", 0, DOUBLE_ARG, 0, 0, NAN },
+ { "%lg", "1.#INF", 0, DOUBLE_ARG, 0, 0, INFINITY },
+ { "%010.2lf", "-000001.#J", 0, DOUBLE_ARG, 0, 0, IND },
+ { "%010.2lf", "0000001.#R", 0, DOUBLE_ARG, 0, 0, NAN },
+ { "%010.2lf", "0000001.#J", 0, DOUBLE_ARG, 0, 0, INFINITY },
+ { "%c", "a", 0, INT_ARG, 'a' },
+ { "%c", "\x82", 0, INT_ARG, 0xa082 },
+ { "%C", "a", 0, INT_ARG, 'a' },
+ { "%C", "", 0, INT_ARG, 0x3042 },
+ { "a%Cb", "ab", 0, INT_ARG, 0x3042 },
+ { "%lld", "-8589934591", "1", ULONGLONG_ARG, 0,
((ULONGLONG)0xffffffff)*0xffffffff },
+ { "%I32d", "1", "I32d", INT_ARG, 1 },
+ { "%.0f", "-2", 0, DOUBLE_ARG, 0, 0, -1.5 },
+ { "%.0f", "-1", 0, DOUBLE_ARG, 0, 0, -0.5 },
+ { "%.0f", "1", 0, DOUBLE_ARG, 0, 0, 0.5 },
+ { "%.0f", "2", 0, DOUBLE_ARG, 0, 0, 1.5 },
+ { "%.30f", "0.333333333333333310000000000000", 0, TODO_FLAG |
DOUBLE_ARG, 0, 0, 1.0/3.0 },
+ { "%.30lf", "1.414213562373095100000000000000", 0, TODO_FLAG
| DOUBLE_ARG, 0, 0, sqrt(2) },
+ { "%f", "3.141593", 0, DOUBLE_ARG, 0, 0, 3.141592653590000
},
+ { "%.10f", "3.1415926536", 0, DOUBLE_ARG, 0, 0,
3.141592653590000 },
+ { "%.11f", "3.14159265359", 0, DOUBLE_ARG, 0, 0,
3.141592653590000 },
+ { "%.15f", "3.141592653590000", 0, DOUBLE_ARG, 0, 0,
3.141592653590000 },
+ { "%.15f", "3.141592653589793", 0, DOUBLE_ARG, 0, 0, M_PI },
+ { "%.13f", "37.8662615745371", 0, DOUBLE_ARG, 0, 0,
37.866261574537077 },
+ { "%.14f", "37.86626157453708", 0, DOUBLE_ARG, 0, 0,
37.866261574537077 },
+ { "%.15f", "37.866261574537077", 0, DOUBLE_ARG, 0, 0,
37.866261574537077 },
+ { "%g", "0.0005", 0, DOUBLE_ARG, 0, 0, 0.0005 },
+ { "%g", "5e-005", 0, DOUBLE_ARG, 0, 0, 0.00005 },
+ { "%g", "5e-006", 0, DOUBLE_ARG, 0, 0, 0.000005 },
+ { "%g", "1e+015", 0, DOUBLE_ARG, 0, 0, 999999999999999.0 },
+ { "%g", "1e+015", 0, DOUBLE_ARG, 0, 0, 1000000000000000.0 },
+ { "%.15g", "0.0005", 0, DOUBLE_ARG, 0, 0, 0.0005 },
+ { "%.15g", "5e-005", 0, DOUBLE_ARG, 0, 0, 0.00005 },
+ { "%.15g", "5e-006", 0, DOUBLE_ARG, 0, 0, 0.000005 },
+ { "%.15g", "999999999999999", 0, DOUBLE_ARG, 0, 0,
999999999999999.0 },
+ { "%.15g", "1e+015", 0, DOUBLE_ARG, 0, 0, 1000000000000000.0
},
+ };
- format = "%I0d";
- r = p_sprintf(buffer,format,1);
- ok(!strcmp(buffer,"I0d"),"I0d failed\n");
- ok( r==3, "return count wrong\n");
+ char buffer[100];
+ int i, x, r;
+
+ for (i=0; i<ARRAY_SIZE(tests); i++) {
+ memset(buffer, 'x', sizeof(buffer));
+ switch(tests[i].type & 0xff) {
+ case NO_ARG:
+ r = p_sprintf(buffer, tests[i].format);
+ break;
+ case INT_ARG:
+ r = p_sprintf(buffer, tests[i].format, tests[i].arg_i);
+ break;
+ case ULONGLONG_ARG:
+ r = p_sprintf(buffer, tests[i].format, tests[i].arg_ull);
+ break;
+ case DOUBLE_ARG:
+ r = p_sprintf(buffer, tests[i].format, tests[i].arg_d);
+ break;
+ case PTR_ARG:
+ r = p_sprintf(buffer, tests[i].format, tests[i].arg_ptr);
+ break;
+ default:
+ ok(0, "tests[%d].type = %x\n", i, tests[i].type);
+ continue;
+ }
- format = "%I32d";
- r = p_sprintf(buffer,format,1);
- if (r == 1)
- {
- ok(!strcmp(buffer,"1"),"I32d failed, got
'%s'\n",buffer);
- }
- else
- {
- /* Older versions don't grok I32 format */
- ok(r == 4 && !strcmp(buffer,"I32d"),"I32d failed, got
'%s',%d\n",buffer,r);
+ ok(r == strlen(buffer), "%d) r = %d, buffer = \"%s\"\n", i,
r, buffer);
+ todo_wine_if(tests[i].type & TODO_FLAG)
+ {
+ ok(!strcmp(buffer, tests[i].out) ||
+ broken(tests[i].broken && !strcmp(buffer, tests[i].broken)),
+ "%d) buffer = \"%s\"\n", i, buffer);
+ }
}
- format = "%I64D";
- r = p_sprintf(buffer,format,(LONGLONG)-1);
- ok(!strcmp(buffer,"D"),"I64D failed: %s\n",buffer);
- ok( r==1, "return count wrong\n");
-
- format = "%zx";
- r = p_sprintf(buffer,format,1);
- ok(!strcmp(buffer, "zx"), "Problem with \"z\"
interpretation\n");
- ok( r==2, "return count wrong\n");
-
- format = "% d";
- r = p_sprintf(buffer,format,1);
- ok(!strcmp(buffer, " 1"),"Problem with sign place-holder:
'%s'\n",buffer);
- ok( r==2, "return count wrong\n");
-
- format = "%+ d";
- r = p_sprintf(buffer,format,1);
- ok(!strcmp(buffer, "+1"),"Problem with sign flags:
'%s'\n",buffer);
- ok( r==2, "return count wrong\n");
-
- format = "%S";
- r = p_sprintf(buffer,format,wide);
- ok(!strcmp(buffer,"wide"),"Problem with wide string format\n");
- ok( r==4, "return count wrong\n");
-
- format = "%04c";
- r = p_sprintf(buffer,format,'1');
- ok(!strcmp(buffer,"0001"),"Character not zero-prefixed
\"%s\"\n",buffer);
- ok( r==4, "return count wrong\n");
-
- format = "%-04c";
- r = p_sprintf(buffer,format,'1');
- ok(!strcmp(buffer,"1 "),"Character zero-padded and/or not
left-adjusted \"%s\"\n",buffer);
- ok( r==4, "return count wrong\n");
-
- format = "%#012x";
- r = p_sprintf(buffer,format,1);
- ok(!strcmp(buffer,"0x0000000001"),"Hexadecimal zero-padded
\"%s\"\n",buffer);
- ok( r==12, "return count wrong\n");
-
- r = p_sprintf(buffer,format,0);
- ok(!strcmp(buffer,"000000000000"),"Hexadecimal zero-padded
\"%s\"\n",buffer);
- ok( r==12, "return count wrong\n");
-
- format = "%#04.8x";
- r = p_sprintf(buffer,format,1);
- ok(!strcmp(buffer,"0x00000001"), "Hexadecimal zero-padded precision
\"%s\"\n",buffer);
- ok( r==10, "return count wrong\n");
-
- r = p_sprintf(buffer,format,0);
- ok(!strcmp(buffer,"00000000"), "Hexadecimal zero-padded precision
\"%s\"\n",buffer);
- ok( r==8, "return count wrong\n");
-
- format = "%#-08.2x";
- r = p_sprintf(buffer,format,1);
- ok(!strcmp(buffer,"0x01 "), "Hexadecimal zero-padded not
left-adjusted \"%s\"\n",buffer);
- ok( r==8, "return count wrong\n");
-
- r = p_sprintf(buffer,format,0);
- ok(!strcmp(buffer,"00 "), "Hexadecimal zero-padded not
left-adjusted \"%s\"\n",buffer);
- ok( r==8, "return count wrong\n");
-
- format = "%#.0x";
- r = p_sprintf(buffer,format,1);
- ok(!strcmp(buffer,"0x1"), "Hexadecimal zero-padded zero-precision
\"%s\"\n",buffer);
- ok( r==3, "return count wrong\n");
-
- r = p_sprintf(buffer,format,0);
- ok(!strcmp(buffer,""), "Hexadecimal zero-padded zero-precision
\"%s\"\n",buffer);
- ok( r==0, "return count wrong\n");
-
- format = "%#08o";
- r = p_sprintf(buffer,format,1);
- ok(!strcmp(buffer,"00000001"), "Octal zero-padded
\"%s\"\n",buffer);
- ok( r==8, "return count wrong\n");
-
- format = "%#o";
- r = p_sprintf(buffer,format,1);
- ok(!strcmp(buffer,"01"), "Octal zero-padded
\"%s\"\n",buffer);
- ok( r==2, "return count wrong\n");
-
- r = p_sprintf(buffer,format,0);
- ok(!strcmp(buffer,"0"), "Octal zero-padded
\"%s\"\n",buffer);
- ok( r==1, "return count wrong\n");
-
if (sizeof(void *) == 8)
{
- format = "%p";
- r = p_sprintf(buffer,format,(void *)57);
+ r = p_sprintf(buffer, "%p", (void *)57);
ok(!strcmp(buffer,"0000000000000039"),"Pointer formatted
incorrectly \"%s\"\n",buffer);
ok( r==16, "return count wrong\n");
- format = "%#020p";
- r = p_sprintf(buffer,format,(void *)57);
+ r = p_sprintf(buffer, "%#020p", (void *)57);
ok(!strcmp(buffer," 0X0000000000000039"),"Pointer formatted
incorrectly\n");
ok( r==20, "return count wrong\n");
- format = "%Fp";
- r = p_sprintf(buffer,format,(void *)57);
+ r = p_sprintf(buffer, "%Fp", (void *)57);
ok(!strcmp(buffer,"0000000000000039"),"Pointer formatted
incorrectly \"%s\"\n",buffer);
ok( r==16, "return count wrong\n");
- format = "%Np";
- r = p_sprintf(buffer,format,(void *)57);
+ r = p_sprintf(buffer, "%Np", (void *)57);
ok(!strcmp(buffer,"0000000000000039"),"Pointer formatted
incorrectly \"%s\"\n",buffer);
ok( r==16, "return count wrong\n");
- format = "%#-020p";
- r = p_sprintf(buffer,format,(void *)57);
+ r = p_sprintf(buffer, "%#-020p", (void *)57);
ok(!strcmp(buffer,"0X0000000000000039 "),"Pointer formatted
incorrectly\n");
ok( r==20, "return count wrong\n");
- format = "%Ix %d";
- r = p_sprintf(buffer,format,(size_t)0x12345678123456,1);
+ r = p_sprintf(buffer, "%Ix %d", (size_t)0x12345678123456,1);
ok(!strcmp(buffer,"12345678123456 1"),"buffer =
%s\n",buffer);
ok( r==16, "return count wrong\n");
+
+ r = p_sprintf(buffer, "%p", 0);
+ ok(!strcmp(buffer,"0000000000000000"), "failed\n");
+ ok( r==16, "return count wrong\n");
}
else
{
- format = "%p";
- r = p_sprintf(buffer,format,(void *)57);
+ r = p_sprintf(buffer, "%p", (void *)57);
ok(!strcmp(buffer,"00000039"),"Pointer formatted incorrectly
\"%s\"\n",buffer);
ok( r==8, "return count wrong\n");
- format = "%#012p";
- r = p_sprintf(buffer,format,(void *)57);
+ r = p_sprintf(buffer, "%#012p", (void *)57);
ok(!strcmp(buffer," 0X00000039"),"Pointer formatted
incorrectly\n");
ok( r==12, "return count wrong\n");
- format = "%Fp";
- r = p_sprintf(buffer,format,(void *)57);
+ r = p_sprintf(buffer, "%Fp", (void *)57);
ok(!strcmp(buffer,"00000039"),"Pointer formatted incorrectly
\"%s\"\n",buffer);
ok( r==8, "return count wrong\n");
- format = "%Np";
- r = p_sprintf(buffer,format,(void *)57);
+ r = p_sprintf(buffer, "%Np",(void *)57);
ok(!strcmp(buffer,"00000039"),"Pointer formatted incorrectly
\"%s\"\n",buffer);
ok( r==8, "return count wrong\n");
- format = "%#-012p";
- r = p_sprintf(buffer,format,(void *)57);
+ r = p_sprintf(buffer, "%#-012p", (void *)57);
ok(!strcmp(buffer,"0X00000039 "),"Pointer formatted
incorrectly\n");
ok( r==12, "return count wrong\n");
- format = "%Ix %d";
- r = p_sprintf(buffer,format,0x123456,1);
+ r = p_sprintf(buffer, "%Ix %d", 0x123456, 1);
ok(!strcmp(buffer,"123456 1"),"buffer = %s\n",buffer);
ok( r==8, "return count wrong\n");
- }
- format = "%04s";
- r = p_sprintf(buffer,format,"foo");
- ok(!strcmp(buffer,"0foo"),"String not zero-prefixed
\"%s\"\n",buffer);
- ok( r==4, "return count wrong\n");
-
- format = "%.1s";
- r = p_sprintf(buffer,format,"foo");
- ok(!strcmp(buffer,"f"),"Precision ignored
\"%s\"\n",buffer);
- ok( r==1, "return count wrong\n");
+ r = p_sprintf(buffer, "%p", 0);
+ ok(!strcmp(buffer,"00000000"), "failed\n");
+ ok( r==8, "return count wrong\n");
+ }
- format = "%.*s";
- r = p_sprintf(buffer,format,1,"foo");
+ r = p_sprintf(buffer, "%.*s", 1, "foo");
ok(!strcmp(buffer,"f"),"Precision ignored
\"%s\"\n",buffer);
ok( r==1, "return count wrong\n");
- format = "%*s";
- r = p_sprintf(buffer,format,-5,"foo");
+ r = p_sprintf(buffer, "%*s", -5, "foo");
ok(!strcmp(buffer,"foo "),"Negative field width ignored
\"%s\"\n",buffer);
ok( r==5, "return count wrong\n");
- format = "hello";
- r = p_sprintf(buffer, format);
- ok(!strcmp(buffer,"hello"), "failed\n");
- ok( r==5, "return count wrong\n");
-
- format = "%ws";
- r = p_sprintf(buffer, format, wide);
- ok(!strcmp(buffer,"wide"), "failed\n");
- ok( r==4, "return count wrong\n");
-
- format = "%-10ws";
- r = p_sprintf(buffer, format, wide );
- ok(!strcmp(buffer,"wide "), "failed\n");
- ok( r==10, "return count wrong\n");
-
- format = "%10ws";
- r = p_sprintf(buffer, format, wide );
- ok(!strcmp(buffer," wide"), "failed\n");
- ok( r==10, "return count wrong\n");
-
- format = "%#+ -03whlls";
- r = p_sprintf(buffer, format, wide );
- ok(!strcmp(buffer,"wide"), "failed\n");
- ok( r==4, "return count wrong\n");
-
- format = "%w0s";
- r = p_sprintf(buffer, format, wide );
- ok(!strcmp(buffer,"0s"), "failed\n");
- ok( r==2, "return count wrong\n");
-
- format = "%w-s";
- r = p_sprintf(buffer, format, wide );
- ok(!strcmp(buffer,"-s"), "failed\n");
- ok( r==2, "return count wrong\n");
-
- format = "%ls";
- r = p_sprintf(buffer, format, wide );
- ok(!strcmp(buffer,"wide"), "failed\n");
- ok( r==4, "return count wrong\n");
-
- format = "%Ls";
- r = p_sprintf(buffer, format, "not wide" );
- ok(!strcmp(buffer,"not wide"), "failed\n");
- ok( r==8, "return count wrong\n");
-
- format = "%b";
- r = p_sprintf(buffer, format);
- ok(!strcmp(buffer,"b"), "failed\n");
- ok( r==1, "return count wrong\n");
-
- format = "%3c";
- r = p_sprintf(buffer, format,'a');
- ok(!strcmp(buffer," a"), "failed\n");
- ok( r==3, "return count wrong\n");
-
- format = "%3d";
- r = p_sprintf(buffer, format,1234);
- ok(!strcmp(buffer,"1234"), "failed\n");
- ok( r==4, "return count wrong\n");
-
- format = "%3h";
- r = p_sprintf(buffer, format);
- ok(!strcmp(buffer,""), "failed\n");
- ok( r==0, "return count wrong\n");
-
- format = "%j%k%m%q%r%t%v%y%z";
- r = p_sprintf(buffer, format);
- ok(!strcmp(buffer,"jkmqrtvyz"), "failed\n");
- ok( r==9, "return count wrong\n");
-
- format = "asdf%n";
x = 0;
- r = p_sprintf(buffer, format, &x );
+ r = p_sprintf(buffer, "asdf%n", &x );
if (r == -1)
{
/* %n format is disabled by default on vista */
@@ -583,228 +392,7 @@ static void test_sprintf( void )
ok( r==4, "return count wrong: %d\n", r);
}
- format = "%-1d";
- r = p_sprintf(buffer, format,2);
- ok(!strcmp(buffer,"2"), "failed\n");
- ok( r==1, "return count wrong\n");
-
- format = "%2.4f";
- r = p_sprintf(buffer, format,8.6);
- ok(!strcmp(buffer,"8.6000"), "failed\n");
- ok( r==6, "return count wrong\n");
-
- format = "%0f";
- r = p_sprintf(buffer, format,0.6);
- ok(!strcmp(buffer,"0.600000"), "failed\n");
- ok( r==8, "return count wrong\n");
-
- format = "%.0f";
- r = p_sprintf(buffer, format,0.6);
- ok(!strcmp(buffer,"1"), "failed\n");
- ok( r==1, "return count wrong\n");
-
- format = "%2.4e";
- r = p_sprintf(buffer, format,8.6);
- ok(!strcmp(buffer,"8.6000e+000"), "failed\n");
- ok( r==11, "return count wrong\n");
-
- format = "% 2.4e";
- r = p_sprintf(buffer, format,8.6);
- ok(!strcmp(buffer," 8.6000e+000"), "failed: %s\n", buffer);
- ok( r==12, "return count wrong\n");
-
- format = "% 014.4e";
- r = p_sprintf(buffer, format,8.6);
- ok(!strcmp(buffer," 008.6000e+000"), "failed: %s\n", buffer);
- ok( r==14, "return count wrong\n");
-
- format = "% 2.4e";
- r = p_sprintf(buffer, format,-8.6);
- ok(!strcmp(buffer,"-8.6000e+000"), "failed: %s\n", buffer);
- ok( r==12, "return count wrong\n");
-
- format = "%+2.4e";
- r = p_sprintf(buffer, format,8.6);
- ok(!strcmp(buffer,"+8.6000e+000"), "failed: %s\n", buffer);
- ok( r==12, "return count wrong\n");
-
- format = "%2.4g";
- r = p_sprintf(buffer, format,8.6);
- ok(!strcmp(buffer,"8.6"), "failed\n");
- ok( r==3, "return count wrong\n");
-
- format = "%-i";
- r = p_sprintf(buffer, format,-1);
- ok(!strcmp(buffer,"-1"), "failed\n");
- ok( r==2, "return count wrong\n");
-
- format = "%-i";
- r = p_sprintf(buffer, format,1);
- ok(!strcmp(buffer,"1"), "failed\n");
- ok( r==1, "return count wrong\n");
-
- format = "%+i";
- r = p_sprintf(buffer, format,1);
- ok(!strcmp(buffer,"+1"), "failed\n");
- ok( r==2, "return count wrong\n");
-
- format = "%o";
- r = p_sprintf(buffer, format,10);
- ok(!strcmp(buffer,"12"), "failed\n");
- ok( r==2, "return count wrong\n");
-
- format = "%p";
- r = p_sprintf(buffer, format,0);
- if (sizeof(void *) == 8)
- {
- ok(!strcmp(buffer,"0000000000000000"), "failed\n");
- ok( r==16, "return count wrong\n");
- }
- else
- {
- ok(!strcmp(buffer,"00000000"), "failed\n");
- ok( r==8, "return count wrong\n");
- }
-
- format = "%s";
- r = p_sprintf(buffer, format,0);
- ok(!strcmp(buffer,"(null)"), "failed\n");
- ok( r==6, "return count wrong\n");
-
- format = "%s";
- r = p_sprintf(buffer, format,"%%%%");
- ok(!strcmp(buffer,"%%%%"), "failed\n");
- ok( r==4, "return count wrong\n");
-
- format = "%u";
- r = p_sprintf(buffer, format,-1);
- ok(!strcmp(buffer,"4294967295"), "failed\n");
- ok( r==10, "return count wrong\n");
-
- format = "%w";
- r = p_sprintf(buffer, format,-1);
- ok(!strcmp(buffer,""), "failed\n");
- ok( r==0, "return count wrong\n");
-
- format = "%h";
- r = p_sprintf(buffer, format,-1);
- ok(!strcmp(buffer,""), "failed\n");
- ok( r==0, "return count wrong\n");
-
- format = "%z";
- r = p_sprintf(buffer, format,-1);
- ok(!strcmp(buffer,"z"), "failed\n");
- ok( r==1, "return count wrong\n");
-
- format = "%j";
- r = p_sprintf(buffer, format,-1);
- ok(!strcmp(buffer,"j"), "failed\n");
- ok( r==1, "return count wrong\n");
-
- format = "%F";
- r = p_sprintf(buffer, format,-1);
- ok(!strcmp(buffer,""), "failed\n");
- ok( r==0, "return count wrong\n");
-
- format = "%N";
- r = p_sprintf(buffer, format,-1);
- ok(!strcmp(buffer,""), "failed\n");
- ok( r==0, "return count wrong\n");
-
- format = "%H";
- r = p_sprintf(buffer, format,-1);
- ok(!strcmp(buffer,"H"), "failed\n");
- ok( r==1, "return count wrong\n");
-
- format = "x%cx";
- r = p_sprintf(buffer, format, 0x100+'X');
- ok(!strcmp(buffer,"xXx"), "failed\n");
- ok( r==3, "return count wrong\n");
-
- format = "%%0";
- r = p_sprintf(buffer, format);
- ok(!strcmp(buffer,"%0"), "failed: \"%s\"\n", buffer);
- ok( r==2, "return count wrong\n");
-
- format = "%hx";
- r = p_sprintf(buffer, format, 0x12345);
- ok(!strcmp(buffer,"2345"), "failed \"%s\"\n", buffer);
-
- format = "%hhx";
- r = p_sprintf(buffer, format, 0x123);
- ok(!strcmp(buffer,"123"), "failed: \"%s\"\n", buffer);
- r = p_sprintf(buffer, format, 0x12345);
- ok(!strcmp(buffer,"2345"), "failed \"%s\"\n", buffer);
-
- format = "%lf";
- r = p_sprintf(buffer, format, IND);
- ok(r==9, "r = %d\n", r);
- ok(!strcmp(buffer, "-1.#IND00"), "failed: \"%s\"\n",
buffer);
- r = p_sprintf(buffer, format, NAN);
- ok(r==8, "r = %d\n", r);
- ok(!strcmp(buffer, "1.#QNAN0"), "failed: \"%s\"\n",
buffer);
- r = p_sprintf(buffer, format, INFINITY);
- ok(r==8, "r = %d\n", r);
- ok(!strcmp(buffer, "1.#INF00"), "failed: \"%s\"\n",
buffer);
-
- format = "%le";
- r = p_sprintf(buffer, format, IND);
- ok(r==14, "r = %d\n", r);
- ok(!strcmp(buffer, "-1.#IND00e+000"), "failed:
\"%s\"\n", buffer);
- r = p_sprintf(buffer, format, NAN);
- ok(r==13, "r = %d\n", r);
- ok(!strcmp(buffer, "1.#QNAN0e+000"), "failed:
\"%s\"\n", buffer);
- r = p_sprintf(buffer, format, INFINITY);
- ok(r==13, "r = %d\n", r);
- ok(!strcmp(buffer, "1.#INF00e+000"), "failed:
\"%s\"\n", buffer);
-
- format = "%lg";
- r = p_sprintf(buffer, format, IND);
- ok(r==7, "r = %d\n", r);
- ok(!strcmp(buffer, "-1.#IND"), "failed: \"%s\"\n",
buffer);
- r = p_sprintf(buffer, format, NAN);
- ok(r==7, "r = %d\n", r);
- ok(!strcmp(buffer, "1.#QNAN"), "failed: \"%s\"\n",
buffer);
- r = p_sprintf(buffer, format, INFINITY);
- ok(r==6, "r = %d\n", r);
- ok(!strcmp(buffer, "1.#INF"), "failed: \"%s\"\n",
buffer);
-
- format = "%010.2lf";
- r = p_sprintf(buffer, format, IND);
- ok(r==10, "r = %d\n", r);
- ok(!strcmp(buffer, "-000001.#J"), "failed: \"%s\"\n",
buffer);
- r = p_sprintf(buffer, format, NAN);
- ok(r==10, "r = %d\n", r);
- ok(!strcmp(buffer, "0000001.#R"), "failed: \"%s\"\n",
buffer);
- r = p_sprintf(buffer, format, INFINITY);
- ok(r==10, "r = %d\n", r);
- ok(!strcmp(buffer, "0000001.#J"), "failed: \"%s\"\n",
buffer);
-
- format = "%c";
- r = p_sprintf(buffer, format, 'a');
- ok(r==1, "r = %d\n", r);
- ok(!strcmp(buffer, "a"), "failed: \"%s\"\n", buffer);
- r = p_sprintf(buffer, format, 0xa082);
- ok(r==1, "r = %d\n", r);
- ok(!strcmp(buffer, "\x82"), "failed: \"%s\"\n",
buffer);
-
- format = "%C";
- r = p_sprintf(buffer, format, 'a');
- ok(r==1, "r = %d\n", r);
- ok(!strcmp(buffer, "a"), "failed: \"%s\"\n", buffer);
- r = p_sprintf(buffer, format, 0x3042);
- ok(r==0, "r = %d\n", r);
- ok(!strcmp(buffer, ""), "failed: \"%s\"\n", buffer);
-
- format = "a%Cb";
- r = p_sprintf(buffer, format, 0x3042);
- ok(r==2, "r = %d\n", r);
- ok(!strcmp(buffer, "ab"), "failed: \"%s\"\n", buffer);
-
- format = "%S";
- buf_w[0] = 0x3042;
- buf_w[1] = 0;
- r = p_sprintf(buffer, format, buf_w);
+ r = p_sprintf(buffer, "%S", L"\x3042");
ok(r==-1 || broken(!r), "r = %d\n", r);
if(!setlocale(LC_ALL, "Japanese_Japan.932")) {
@@ -812,13 +400,11 @@ static void test_sprintf( void )
return;
}
- format = "%c";
- r = p_sprintf(buffer, format, 0xa082);
+ r = p_sprintf(buffer, "%c", 0xa082);
ok(r==1, "r = %d\n", r);
ok(!strcmp(buffer, "\x82"), "failed: \"%s\"\n",
buffer);
- format = "%C";
- r = p_sprintf(buffer, format, 0x3042);
+ r = p_sprintf(buffer, "%C", 0x3042);
ok(r==2, "r = %d\n", r);
ok(!strcmp(buffer, "\x82\xa0"), "failed: \"%s\"\n",
buffer);
@@ -828,28 +414,34 @@ static void test_sprintf( void )
ok(!strcmp(buffer, "string to copy"), "failed:
\"%s\"\n", buffer);
setlocale(LC_ALL, "C");
+
+ r = p_sprintf(buffer, "%*1d", 1, 3);
+ ok(r==11, "r = %d\n", r);
+ ok(!strcmp(buffer, " 3"), "failed: \"%s\"\n",
buffer);
+
+ r = p_sprintf(buffer, "%0*0d", 1, 2);
+ ok(r==10, "r = %d\n", r);
+ ok(!strcmp(buffer, "0000000002"), "failed: \"%s\"\n",
buffer);
+
+ r = p_sprintf(buffer, "% *2d", 0, 7);
+ ok(r==2, "r = %d\n", r);
+ ok(!strcmp(buffer, " 7"), "failed: \"%s\"\n", buffer);
}
static void test_swprintf( void )
{
wchar_t buffer[100];
- const wchar_t I64d[] =
{'%','I','6','4','d',0};
- double pnumber=789456123;
- const wchar_t TwentyThreePoint15e[]=
{'%','+','#','2','3','.','1','5','e',0};
- const wchar_t e008[] =
{'e','+','0','0','8',0};
- const wchar_t string_w[] =
{'s','t','r','i','n','g',0};
+ double pnumber = 789456123;
const char string[] = "string";
- const wchar_t S[]={'%','S',0};
- const wchar_t hs[] = {'%', 'h', 's', 0};
-
- swprintf(buffer,TwentyThreePoint15e,pnumber);
- ok(wcsstr(buffer,e008) != 0,"Sprintf different\n");
- swprintf(buffer,I64d,((ULONGLONG)0xffffffff)*0xffffffff);
- ok(wcslen(buffer) == 11,"Problem with long long\n");
- swprintf(buffer,S,string);
- ok(wcslen(buffer) == 6,"Problem with \"%%S\"
interpretation\n");
- swprintf(buffer, hs, string);
- ok( wcscmp(string_w,buffer) == 0, "swprintf failed with %%hs\n");
+
+ swprintf(buffer, L"%+#23.15e", pnumber);
+ ok(wcsstr(buffer, L"e+008") != 0, "Sprintf different\n");
+ swprintf(buffer, L"%I64d", ((ULONGLONG)0xffffffff)*0xffffffff);
+ ok(wcslen(buffer) == 11, "Problem with long long\n");
+ swprintf(buffer, L"%S", string);
+ ok(wcslen(buffer) == 6, "Problem with \"%%S\"
interpretation\n");
+ swprintf(buffer, L"%hs", string);
+ ok(!wcscmp(L"string", buffer), "swprintf failed with %%hs\n");
}
static void test_snprintf (void)
@@ -867,10 +459,12 @@ static void test_snprintf (void)
const int bufsiz = sizeof buffer;
unsigned int i;
+ int (__cdecl *p_snprintf)(char*,size_t,const char*,...) = _snprintf;
+
for (i = 0; i < ARRAY_SIZE(tests); i++) {
const char *fmt = tests[i].format;
const int expect = tests[i].expected;
- const int n = _snprintf (buffer, bufsiz, fmt);
+ const int n = p_snprintf(buffer, bufsiz, fmt);
const int valid = n < 0 ? bufsiz : (n == bufsiz ? n : n+1);
ok (n == expect, "\"%s\": expected %d, returned %d\n",
@@ -882,10 +476,7 @@ static void test_snprintf (void)
static void test_fprintf(void)
{
- static const char file_name[] = "fprintf.tst";
- static const WCHAR utf16_test[] =
{'u','n','i','c','o','d','e','\n',0};
-
- FILE *fp = fopen(file_name, "wb");
+ FILE *fp = fopen("fprintf.tst", "wb");
char buf[1024];
int ret;
@@ -899,14 +490,14 @@ static void test_fprintf(void)
ret = ftell(fp);
ok(ret == 26, "ftell returned %d\n", ret);
- ret = fwprintf(fp, utf16_test);
+ ret = fwprintf(fp, L"unicode\n");
ok(ret == 8, "ret = %d\n", ret);
ret = ftell(fp);
ok(ret == 42, "ftell returned %d\n", ret);
fclose(fp);
- fp = fopen(file_name, "rb");
+ fp = fopen("fprintf.tst", "rb");
ret = fscanf(fp, "%[^\n] ", buf);
ok(ret == 1, "ret = %d\n", ret);
ret = ftell(fp);
@@ -922,12 +513,11 @@ static void test_fprintf(void)
fgets(buf, sizeof(buf), fp);
ret = ftell(fp);
ok(ret == 41, "ret = %d\n", ret);
- ok(!memcmp(buf, utf16_test, sizeof(utf16_test)),
- "buf = %s\n", wine_dbgstr_w((WCHAR*)buf));
+ ok(!wcscmp((wchar_t*)buf, L"unicode\n"), "buf = %s\n",
wine_dbgstr_w((WCHAR*)buf));
fclose(fp);
- fp = fopen(file_name, "wt");
+ fp = fopen("fprintf.tst", "wt");
ret = fprintf(fp, "simple test\n");
ok(ret == 12, "ret = %d\n", ret);
@@ -939,14 +529,14 @@ static void test_fprintf(void)
ret = ftell(fp);
ok(ret == 28, "ftell returned %d\n", ret);
- ret = fwprintf(fp, utf16_test);
+ ret = fwprintf(fp, L"unicode\n");
ok(ret == 8, "ret = %d\n", ret);
ret = ftell(fp);
ok(ret == 37, "ftell returned %d\n", ret);
fclose(fp);
- fp = fopen(file_name, "rb");
+ fp = fopen("fprintf.tst", "rb");
ret = fscanf(fp, "%[^\n] ", buf);
ok(ret == 1, "ret = %d\n", ret);
ret = ftell(fp);
@@ -964,7 +554,7 @@ static void test_fprintf(void)
ok(!strcmp(buf, "unicode\r\n"), "buf = %s\n", buf);
fclose(fp);
- unlink(file_name);
+ unlink("fprintf.tst");
}
static void test_fcvt(void)
@@ -1076,27 +666,23 @@ static struct {
int expsign;
} test_cvt_testcases[] = {
{ 45.0, 2, "45", "4500", 2,
2, 0 },
- /* Numbers less than 1.0 with different precisions */
{ 0.0001, 1, "1", "", -3,
-3, 0 },
{ 0.0001, 10,"1000000000", "1000000", -3,
-3, 0 },
- /* Basic sign test */
{ -111.0001, 5, "11100", "11100010", 3,
3, 1 },
{ 111.0001, 5, "11100", "11100010", 3,
3, 0 },
- /* big numbers with low precision */
{ 3333.3, 2, "33", "333330", 4,
4, 0 },
{999999999999.9, 3, "100","999999999999900", 13,
12, 0 },
- /* 0.0 with different precisions */
{ 0.0, 5, "00000", "00000", 0,
0, 0 },
{ 0.0, 0, "", "", 0,
0, 0 },
{ 0.0, -1, "", "", 0,
0, 0 },
- /* Numbers > 1.0 with 0 or -ve precision */
+ { -0.0, 5, "00000", "00000", 0,
0, 1 },
+ { -0.0, 0, "", "", 0,
0, 1 },
+ { -0.0, -1, "", "", 0,
0, 1 },
{ -123.0001, 0, "", "123", 3,
3, 1 },
{ -123.0001, -1, "", "12", 3,
3, 1 },
{ -123.0001, -2, "", "1", 3,
3, 1 },
{ -123.0001, -3, "", "", 3,
3, 1 },
- /* Numbers > 1.0, but with rounding at the point of precision */
{ 99.99, 1, "1", "1000", 3,
3, 0 },
- /* Numbers < 1.0 where rounding occurs at the point of precision */
{ 0.0063, 2, "63", "1", -2,
-1, 0 },
{ 0.0063, 3, "630", "6", -2,
-2, 0 },
{ 0.09999999996, 2, "10", "10", 0,
0, 0 },
@@ -1105,12 +691,18 @@ static struct {
{ 0.4, 0, "", "", 0,
0, 0 },
{ 0.49, 0, "", "", 0,
0, 0 },
{ 0.51, 0, "", "1", 1,
1, 0 },
- /* ask for ridiculous precision, ruin formatting this table */
+ { NAN, 2, "1$", "1#R", 1,
1, 0 },
+ { NAN, 5, "1#QNB", "1#QNAN", 1,
1, 0 },
+ { -NAN, 2, "1$", "1#J", 1,
1, 1 },
+ { -NAN, 5, "1#IND", "1#IND0", 1,
1, 1 },
+ { INFINITY, 2, "1$", "1#J", 1,
1, 0 },
+ { INFINITY, 5, "1#INF", "1#INF0", 1,
1, 0 },
+ { -INFINITY, 2, "1$", "1#J", 1,
1, 1 },
+ { -INFINITY, 5, "1#INF", "1#INF0", 1,
1, 1 },
{ 1.0, 30, "100000000000000000000000000000",
"1000000000000000000000000000000", 1, 1,
0},
{ 123456789012345678901.0, 30,
"123456789012345680000000000000",
"123456789012345680000000000000000000000000000000000",
21, 21, 0},
- /* end marker */
{ 0, 0, "END"}
};
@@ -1125,14 +717,14 @@ static void test_xcvt(void)
test_cvt_testcases[i].nrdigits,
&decpt,
&sign);
- ok( 0 == strncmp( str, test_cvt_testcases[i].expstr_e, 15),
- "_ecvt() bad return, got \n'%s' expected
\n'%s'\n", str,
+ ok( !strncmp( str, test_cvt_testcases[i].expstr_e, 15),
+ "%d) _ecvt() bad return, got '%s' expected
'%s'\n", i, str,
test_cvt_testcases[i].expstr_e);
ok( decpt == test_cvt_testcases[i].expdecpt_e,
- "_ecvt() decimal point wrong, got %d expected %d\n", decpt,
+ "%d) _ecvt() decimal point wrong, got %d expected %d\n", i,
decpt,
test_cvt_testcases[i].expdecpt_e);
ok( sign == test_cvt_testcases[i].expsign,
- "_ecvt() sign wrong, got %d expected %d\n", sign,
+ "%d) _ecvt() sign wrong, got %d expected %d\n", i, sign,
test_cvt_testcases[i].expsign);
}
for( i = 0; strcmp( test_cvt_testcases[i].expstr_e, "END"); i++){
@@ -1141,14 +733,14 @@ static void test_xcvt(void)
test_cvt_testcases[i].nrdigits,
&decpt,
&sign);
- ok( 0 == strncmp( str, test_cvt_testcases[i].expstr_f, 15),
- "_fcvt() bad return, got \n'%s' expected
\n'%s'\n", str,
+ ok( !strncmp( str, test_cvt_testcases[i].expstr_f, 15),
+ "%d) _fcvt() bad return, got '%s' expected
'%s'\n", i, str,
test_cvt_testcases[i].expstr_f);
ok( decpt == test_cvt_testcases[i].expdecpt_f,
- "_fcvt() decimal point wrong, got %d expected %d\n", decpt,
+ "%d) _fcvt() decimal point wrong, got %d expected %d\n", i,
decpt,
test_cvt_testcases[i].expdecpt_f);
ok( sign == test_cvt_testcases[i].expsign,
- "_fcvt() sign wrong, got %d expected %d\n", sign,
+ "%d) _fcvt() sign wrong, got %d expected %d\n", i, sign,
test_cvt_testcases[i].expsign);
}
@@ -1159,14 +751,14 @@ static void test_xcvt(void)
decpt = sign = 100;
err = p__ecvt_s(str, 1024, test_cvt_testcases[i].value,
test_cvt_testcases[i].nrdigits, &decpt, &sign);
ok(err == 0, "_ecvt_s() failed with error code %d\n", err);
- ok( 0 == strncmp( str, test_cvt_testcases[i].expstr_e, 15),
- "_ecvt_s() bad return, got \n'%s' expected
\n'%s'\n", str,
+ ok( !strncmp( str, test_cvt_testcases[i].expstr_e, 15),
+ "%d) _ecvt_s() bad return, got '%s' expected
'%s'\n", i, str,
test_cvt_testcases[i].expstr_e);
ok( decpt == test_cvt_testcases[i].expdecpt_e,
- "_ecvt_s() decimal point wrong, got %d expected %d\n",
decpt,
+ "%d) _ecvt_s() decimal point wrong, got %d expected %d\n",
i, decpt,
test_cvt_testcases[i].expdecpt_e);
ok( sign == test_cvt_testcases[i].expsign,
- "_ecvt_s() sign wrong, got %d expected %d\n", sign,
+ "%d) _ecvt_s() sign wrong, got %d expected %d\n", i, sign,
test_cvt_testcases[i].expsign);
}
free(str);
@@ -1203,15 +795,15 @@ static void test_xcvt(void)
for( i = 0; strcmp( test_cvt_testcases[i].expstr_e, "END"); i++){
decpt = sign = 100;
err = p__fcvt_s(str, 1024, test_cvt_testcases[i].value,
test_cvt_testcases[i].nrdigits, &decpt, &sign);
- ok(err == 0, "_fcvt_s() failed with error code %d\n", err);
- ok( 0 == strncmp( str, test_cvt_testcases[i].expstr_f, 15),
- "_fcvt_s() bad return, got '%s' expected '%s'.
test %d\n", str,
+ ok(!err, "%d) _fcvt_s() failed with error code %d\n", i, err);
+ ok( !strncmp( str, test_cvt_testcases[i].expstr_f, 15),
+ "%d) _fcvt_s() bad return, got '%s' expected
'%s'. test %d\n", i, str,
test_cvt_testcases[i].expstr_f, i);
ok( decpt == test_cvt_testcases[i].expdecpt_f,
- "_fcvt_s() decimal point wrong, got %d expected %d\n",
decpt,
+ "%d) _fcvt_s() decimal point wrong, got %d expected %d\n",
i, decpt,
test_cvt_testcases[i].expdecpt_f);
ok( sign == test_cvt_testcases[i].expsign,
- "_fcvt_s() sign wrong, got %d expected %d\n", sign,
+ "%d) _fcvt_s() sign wrong, got %d expected %d\n", i, sign,
test_cvt_testcases[i].expsign);
}
free(str);
@@ -1223,104 +815,94 @@ static void test_xcvt(void)
static int WINAPIV _vsnwprintf_wrapper(wchar_t *str, size_t len, const wchar_t *format,
...)
{
int ret;
- __ms_va_list valist;
- __ms_va_start(valist, format);
+ va_list valist;
+ va_start(valist, format);
ret = _vsnwprintf(str, len, format, valist);
- __ms_va_end(valist);
+ va_end(valist);
return ret;
}
static void test_vsnwprintf(void)
{
- const wchar_t format[] =
{'%','w','s','%','w','s','%','w','s',0};
- const wchar_t one[] = {'o','n','e',0};
- const wchar_t two[] = {'t','w','o',0};
- const wchar_t three[] =
{'t','h','r','e','e',0};
-
int ret;
wchar_t str[32];
char buf[32];
- ret = _vsnwprintf_wrapper( str, ARRAY_SIZE(str), format, one, two, three );
-
+ ret = _vsnwprintf_wrapper( str, ARRAY_SIZE(str), L"%ws%ws%ws",
L"one", L"two", L"three" );
ok( ret == 11, "got %d expected 11\n", ret );
WideCharToMultiByte( CP_ACP, 0, str, -1, buf, sizeof(buf), NULL, NULL );
ok( !strcmp(buf, "onetwothree"), "got %s expected
'onetwothree'\n", buf );
- ret = _vsnwprintf_wrapper( str, 0, format, one, two, three );
+ ret = _vsnwprintf_wrapper( str, 0, L"%ws%ws%ws", L"one",
L"two", L"three" );
ok( ret == -1, "got %d, expected -1\n", ret );
- ret = _vsnwprintf_wrapper( NULL, 0, format, one, two, three );
+ ret = _vsnwprintf_wrapper( NULL, 0, L"%ws%ws%ws", L"one",
L"two", L"three" );
ok( ret == 11 || broken(ret == -1 /* Win2k */), "got %d, expected 11\n",
ret );
}
static int WINAPIV vswprintf_wrapper(wchar_t *str, const wchar_t *format, ...)
{
int ret;
- __ms_va_list valist;
- __ms_va_start(valist, format);
+ va_list valist;
+ va_start(valist, format);
ret = p_vswprintf(str, format, valist);
- __ms_va_end(valist);
+ va_end(valist);
return ret;
}
static int WINAPIV _vswprintf_wrapper(wchar_t *str, const wchar_t *format, ...)
{
int ret;
- __ms_va_list valist;
- __ms_va_start(valist, format);
+ va_list valist;
+ va_start(valist, format);
ret = p__vswprintf(str, format, valist);
- __ms_va_end(valist);
+ va_end(valist);
return ret;
}
static int WINAPIV _vswprintf_l_wrapper(wchar_t *str, const wchar_t *format, void
*locale, ...)
{
int ret;
- __ms_va_list valist;
- __ms_va_start(valist, locale);
+ va_list valist;
+ va_start(valist, locale);
ret = p__vswprintf_l(str, format, locale, valist);
- __ms_va_end(valist);
+ va_end(valist);
return ret;
}
static int WINAPIV _vswprintf_c_wrapper(wchar_t *str, size_t size, const wchar_t *format,
...)
{
int ret;
- __ms_va_list valist;
- __ms_va_start(valist, format);
+ va_list valist;
+ va_start(valist, format);
ret = p__vswprintf_c(str, size, format, valist);
- __ms_va_end(valist);
+ va_end(valist);
return ret;
}
static int WINAPIV _vswprintf_c_l_wrapper(wchar_t *str, size_t size, const wchar_t
*format, void *locale, ...)
{
int ret;
- __ms_va_list valist;
- __ms_va_start(valist, locale);
+ va_list valist;
+ va_start(valist, locale);
ret = p__vswprintf_c_l(str, size, format, locale, valist);
- __ms_va_end(valist);
+ va_end(valist);
return ret;
}
static int WINAPIV _vswprintf_p_l_wrapper(wchar_t *str, size_t size, const wchar_t
*format, void *locale, ...)
{
int ret;
- __ms_va_list valist;
- __ms_va_start(valist, locale);
+ va_list valist;
+ va_start(valist, locale);
ret = p__vswprintf_p_l(str, size, format, locale, valist);
- __ms_va_end(valist);
+ va_end(valist);
return ret;
}
static void test_vswprintf(void)
{
- const wchar_t format[] = {'%','s','
','%','d',0};
- const wchar_t number[] =
{'n','u','m','b','e','r',0};
- const wchar_t out[] =
{'n','u','m','b','e','r','
','1','2','3',0};
wchar_t buf[20];
-
int ret;
if (!p_vswprintf || !p__vswprintf || !p__vswprintf_l ||!p__vswprintf_c
@@ -1330,43 +912,48 @@ static void test_vswprintf(void)
return;
}
- ret = vswprintf_wrapper(buf, format, number, 123);
+ ret = vswprintf_wrapper(buf, L"%s %d", L"number", 123);
ok(ret == 10, "got %d, expected 10\n", ret);
- ok(!memcmp(buf, out, sizeof(out)), "buf = %s\n", wine_dbgstr_w(buf));
+ ok(!wcscmp(buf, L"number 123"), "buf = %s\n",
wine_dbgstr_w(buf));
memset(buf, 0, sizeof(buf));
- ret = _vswprintf_wrapper(buf, format, number, 123);
+ ret = _vswprintf_wrapper(buf, L"%s %d", L"number", 123);
ok(ret == 10, "got %d, expected 10\n", ret);
- ok(!memcmp(buf, out, sizeof(out)), "buf = %s\n", wine_dbgstr_w(buf));
+ ok(!wcscmp(buf, L"number 123"), "buf = %s\n",
wine_dbgstr_w(buf));
memset(buf, 0, sizeof(buf));
- ret = _vswprintf_l_wrapper(buf, format, NULL, number, 123);
+ ret = _vswprintf_l_wrapper(buf, L"%s %d", NULL, L"number", 123);
ok(ret == 10, "got %d, expected 10\n", ret);
- ok(!memcmp(buf, out, sizeof(out)), "buf = %s\n", wine_dbgstr_w(buf));
+ ok(!wcscmp(buf, L"number 123"), "buf = %s\n",
wine_dbgstr_w(buf));
memset(buf, 0, sizeof(buf));
- ret = _vswprintf_c_wrapper(buf, 20, format, number, 123);
+ ret = _vswprintf_c_wrapper(buf, 20, L"%s %d", L"number", 123);
ok(ret == 10, "got %d, expected 10\n", ret);
- ok(!memcmp(buf, out, sizeof(out)), "buf = %s\n", wine_dbgstr_w(buf));
+ ok(!wcscmp(buf, L"number 123"), "buf = %s\n",
wine_dbgstr_w(buf));
+
+ memset(buf, 'x', sizeof(buf));
+ ret = _vswprintf_c_wrapper(buf, 10, L"%s %d", L"number", 123);
+ ok(ret == -1, "got %d, expected -1\n", ret);
+ ok(!wcscmp(buf, L"number 12"), "buf = %s\n",
wine_dbgstr_w(buf));
memset(buf, 0, sizeof(buf));
- ret = _vswprintf_c_l_wrapper(buf, 20, format, NULL, number, 123);
+ ret = _vswprintf_c_l_wrapper(buf, 20, L"%s %d", NULL, L"number",
123);
ok(ret == 10, "got %d, expected 10\n", ret);
- ok(!memcmp(buf, out, sizeof(out)), "buf = %s\n", wine_dbgstr_w(buf));
+ ok(!wcscmp(buf, L"number 123"), "buf = %s\n",
wine_dbgstr_w(buf));
memset(buf, 0, sizeof(buf));
- ret = _vswprintf_p_l_wrapper(buf, 20, format, NULL, number, 123);
+ ret = _vswprintf_p_l_wrapper(buf, 20, L"%s %d", NULL, L"number",
123);
ok(ret == 10, "got %d, expected 10\n", ret);
- ok(!memcmp(buf, out, sizeof(out)), "buf = %s\n", wine_dbgstr_w(buf));
+ ok(!wcscmp(buf, L"number 123"), "buf = %s\n",
wine_dbgstr_w(buf));
}
static int WINAPIV _vscprintf_wrapper(const char *format, ...)
{
int ret;
- __ms_va_list valist;
- __ms_va_start(valist, format);
+ va_list valist;
+ va_start(valist, format);
ret = p__vscprintf(format, valist);
- __ms_va_end(valist);
+ va_end(valist);
return ret;
}
@@ -1387,18 +974,15 @@ static void test_vscprintf(void)
static int WINAPIV _vscwprintf_wrapper(const wchar_t *format, ...)
{
int ret;
- __ms_va_list valist;
- __ms_va_start(valist, format);
+ va_list valist;
+ va_start(valist, format);
ret = p__vscwprintf(format, valist);
- __ms_va_end(valist);
+ va_end(valist);
return ret;
}
static void test_vscwprintf(void)
{
- const wchar_t format[] = {'%','s','
','%','d',0};
- const wchar_t number[] =
{'n','u','m','b','e','r',0};
-
int ret;
if (!p__vscwprintf)
@@ -1407,7 +991,7 @@ static void test_vscwprintf(void)
return;
}
- ret = _vscwprintf_wrapper( format, number, 1 );
+ ret = _vscwprintf_wrapper(L"%s %d", L"number", 1 );
ok( ret == 8, "got %d expected 8\n", ret );
}
@@ -1415,22 +999,17 @@ static int WINAPIV _vsnwprintf_s_wrapper(wchar_t *str, size_t
sizeOfBuffer,
size_t count, const wchar_t *format, ...)
{
int ret;
- __ms_va_list valist;
- __ms_va_start(valist, format);
+ va_list valist;
+ va_start(valist, format);
ret = p__vsnwprintf_s(str, sizeOfBuffer, count, format, valist);
- __ms_va_end(valist);
+ va_end(valist);
return ret;
}
static void test_vsnwprintf_s(void)
{
- const wchar_t format[] = {
'A','B','%','u','C',0 };
- const wchar_t out7[] = {
'A','B','1','2','3','C',0 };
- const wchar_t out6[] = {
'A','B','1','2','3',0 };
- const wchar_t out2[] = { 'A',0 };
- const wchar_t out1[] = { 0 };
wchar_t buffer[14] = { 0 };
- int exp, got;
+ int ret;
if (!p__vsnwprintf_s)
{
@@ -1439,44 +1018,40 @@ static void test_vsnwprintf_s(void)
}
/* Enough room. */
- exp = wcslen(out7);
-
- got = _vsnwprintf_s_wrapper(buffer, 14, _TRUNCATE, format, 123);
- ok( exp == got, "length wrong, expect=%d, got=%d\n", exp, got);
- ok( !wcscmp(out7, buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
+ ret = _vsnwprintf_s_wrapper(buffer, 14, _TRUNCATE, L"AB%uC", 123);
+ ok( ret == 6, "length wrong, expect=6, got=%d\n", ret);
+ ok( !wcscmp(L"AB123C", buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
- got = _vsnwprintf_s_wrapper(buffer, 12, _TRUNCATE, format, 123);
- ok( exp == got, "length wrong, expect=%d, got=%d\n", exp, got);
- ok( !wcscmp(out7, buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
+ ret = _vsnwprintf_s_wrapper(buffer, 12, _TRUNCATE, L"AB%uC", 123);
+ ok( ret == 6, "length wrong, expect=6, got=%d\n", ret);
+ ok( !wcscmp(L"AB123C", buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
- got = _vsnwprintf_s_wrapper(buffer, 7, _TRUNCATE, format, 123);
- ok( exp == got, "length wrong, expect=%d, got=%d\n", exp, got);
- ok( !wcscmp(out7, buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
+ ret = _vsnwprintf_s_wrapper(buffer, 7, _TRUNCATE, L"AB%uC", 123);
+ ok( ret == 6, "length wrong, expect=6, got=%d\n", ret);
+ ok( !wcscmp(L"AB123C", buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
/* Not enough room. */
- exp = -1;
-
- got = _vsnwprintf_s_wrapper(buffer, 6, _TRUNCATE, format, 123);
- ok( exp == got, "length wrong, expect=%d, got=%d\n", exp, got);
- ok( !wcscmp(out6, buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
+ ret = _vsnwprintf_s_wrapper(buffer, 6, _TRUNCATE, L"AB%uC", 123);
+ ok( ret == -1, "length wrong, expect=-1, got=%d\n", ret);
+ ok( !wcscmp(L"AB123", buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
- got = _vsnwprintf_s_wrapper(buffer, 2, _TRUNCATE, format, 123);
- ok( exp == got, "length wrong, expect=%d, got=%d\n", exp, got);
- ok( !wcscmp(out2, buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
+ ret = _vsnwprintf_s_wrapper(buffer, 2, _TRUNCATE, L"AB%uC", 123);
+ ok( ret == -1, "length wrong, expect=-1, got=%d\n", ret);
+ ok( !wcscmp(L"A", buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
- got = _vsnwprintf_s_wrapper(buffer, 1, _TRUNCATE, format, 123);
- ok( exp == got, "length wrong, expect=%d, got=%d\n", exp, got);
- ok( !wcscmp(out1, buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
+ ret = _vsnwprintf_s_wrapper(buffer, 1, _TRUNCATE, L"AB%uC", 123);
+ ok( ret == -1, "length wrong, expect=-1, got=%d\n", ret);
+ ok( !wcscmp(L"", buffer), "buffer wrong, got=%s\n",
wine_dbgstr_w(buffer));
}
static int WINAPIV _vsprintf_p_wrapper(char *str, size_t sizeOfBuffer,
const char *format, ...)
{
int ret;
- __ms_va_list valist;
- __ms_va_start(valist, format);
+ va_list valist;
+ va_start(valist, format);
ret = p__vsprintf_p(str, sizeOfBuffer, format, valist);
- __ms_va_end(valist);
+ va_end(valist);
return ret;
}
diff --git a/modules/rostests/winetests/msvcrt/scanf.c
b/modules/rostests/winetests/msvcrt/scanf.c
index 6d38e438c8c..e175342796b 100644
--- a/modules/rostests/winetests/msvcrt/scanf.c
+++ b/modules/rostests/winetests/msvcrt/scanf.c
@@ -22,6 +22,41 @@
#include "wine/test.h"
+static void test_fscanf( void )
+{
+ static const char file_name[] = "fscanf.tst";
+ static const char contents[] =
+ "line1\n"
+ "line2 "
+ ;
+ char buf[1024];
+ FILE *fp;
+ int ret;
+
+ fp = fopen(file_name, "wb");
+ ok(fp != NULL, "fp = %p\n", fp);
+ if(!fp) {
+ skip("failed to create temporary test file\n");
+ return;
+ }
+
+ ret = fprintf(fp, contents);
+ fclose(fp);
+
+ fp = fopen(file_name, "rb");
+ ret = fscanf(fp, "%s", buf);
+ ok(ret == 1, "ret = %d\n", ret);
+ ok(strcmp(buf, "line1") == 0, "buf = %s\n", buf);
+ ret = fscanf(fp, "%s", buf);
+ ok(ret == 1, "ret = %d\n", ret);
+ ok(strcmp(buf, "line2") == 0, "buf = %s\n", buf);
+ ret = fscanf(fp, "%s", buf);
+ ok(ret == EOF, "ret = %d\n", ret);
+ fclose(fp);
+
+ unlink(file_name);
+}
+
static void test_sscanf( void )
{
/* use function pointers to bypass gcc builtin */
@@ -48,6 +83,14 @@ static void test_sscanf( void )
ret = p_sscanf(buffer, "%d", &result);
ok( ret == EOF,"sscanf returns %x instead of %x\n", ret, EOF );
+ ret = p_sscanf(" \t\n\n", "%s", buffer);
+ ok( ret == EOF, "ret = %d\n", ret );
+
+ buffer1[0] = 'a';
+ ret = p_sscanf("test\n", "%s%c", buffer, buffer1);
+ ok( ret == 2, "ret = %d\n", ret );
+ ok( buffer1[0] == '\n', "buffer1[0] = %d\n", buffer1[0] );
+
/* check %p */
ok( p_sscanf("000000000046F170", "%p", &ptr) == 1,
"sscanf failed\n" );
ok( ptr == (void *)0x46F170,"sscanf reads %p instead of %x\n", ptr,
0x46F170 );
@@ -122,6 +165,12 @@ static void test_sscanf( void )
ok(double_res >= 1.1e-30-1e-45 && double_res <= 1.1e-30+1e-45,
"Got %.18le, expected %.18le\n", double_res, 1.1e-30);
+ buffer[0] = 0;
+ double_res = 1;
+ ret = p_sscanf(buffer, "%lf", &double_res);
+ ok(ret == -1, "expected 0, got %u\n", ret);
+ ok(double_res == 1, "Got %lf, expected 1\n", double_res);
+
/* check strings */
ret = p_sprintf(buffer," %s", pname);
ok( ret == 26, "expected 26, got %u\n", ret);
@@ -137,6 +186,22 @@ static void test_sscanf( void )
ok( ret == 1, "Error with format
\"%s\"\n","%*[a-cd-dg-e]%c");
ok( buffer[0] == 'h', "Error with \"abcefgdh\"
\"%c\"\n", buffer[0]);
+ ret = p_sscanf("-123", "%[-0-9]", buffer);
+ ok( ret == 1, "Error with format \"%s\"\n",
"%[-0-9]");
+ ok( strcmp("-123", buffer) == 0, "Error with \"-123\"
\"%s\"\n", buffer);
+
+ ret = p_sscanf("-321", "%[0-9-]", buffer);
+ ok( ret == 1, "Error with format \"%s\"\n",
"%[0-9-]");
+ ok( strcmp("-321", buffer) == 0, "Error with \"-321\"
\"%s\"\n", buffer);
+
+ ret = p_sscanf("-4123", "%[1-2-4]", buffer);
+ ok( ret == 1, "Error with format \"%s\"\n",
"%[1-2-4]");
+ ok( strcmp("-412", buffer) == 0, "Error with \"-412\"
\"%s\"\n", buffer);
+
+ ret = p_sscanf("-456123", "%[1-2-45-6]", buffer);
+ ok( ret == 1, "Error with format \"%s\"\n",
"%[1-2-45-6]");
+ ok( strcmp("-45612", buffer) == 0, "Error with \"-45612\"
\"%s\"\n", buffer);
+
buffer1[0] = 'b';
ret = p_sscanf("a","%s%s", buffer, buffer1);
ok( ret == 1, "expected 1, got %u\n", ret);
@@ -162,6 +227,30 @@ static void test_sscanf( void )
ok(ret == 1, "Wrong number of arguments read: %d\n", ret);
ok(result == 0xdead614e, "Wrong number read (%x)\n", result);
+ result = 0xdeadbeef;
+ strcpy(buffer,"12345678");
+ ret = p_sscanf(buffer, "%02hd", &result);
+ ok(ret == 1, "Wrong number of arguments read: %d\n", ret);
+ ok(result == 0xdead000c, "Wrong number read (%x)\n", result);
+
+ result = 0xdeadbeef;
+ strcpy(buffer,"12345678");
+ ret = p_sscanf(buffer, "%h02d", &result);
+ ok(ret == 1, "Wrong number of arguments read: %d\n", ret);
+ ok(result == 0xdead000c, "Wrong number read (%x)\n", result);
+
+ result = 0xdeadbeef;
+ strcpy(buffer,"12345678");
+ ret = p_sscanf(buffer, "%000h02d", &result);
+ ok(ret == 1, "Wrong number of arguments read: %d\n", ret);
+ ok(result == 0xdead000c, "Wrong number read (%x)\n", result);
+
+ result = 0xdeadbeef;
+ strcpy(buffer,"12345678");
+ ret = p_sscanf(buffer, "%2h0d", &result);
+ ok(ret == 1, "Wrong number of arguments read: %d\n", ret);
+ ok(result == 0xdead614e, "Wrong number read (%x)\n", result);
+
result = 0xdeadbeef;
ret = p_sscanf(buffer, "%hhd", &result);
ok(ret == 1, "Wrong number of arguments read: %d\n", ret);
@@ -313,35 +402,34 @@ static void test_sscanf_s(void)
static void test_swscanf( void )
{
- wchar_t buffer[100];
+ wchar_t buffer[100], results[100];
int result, ret;
- static const WCHAR formatd[] = {'%','d',0};
- const WCHAR format2[] =
{'a',0x1234,'%',0x1234,'%','c',0};
WCHAR c;
/* check WEOF */
/* WEOF is an unsigned short -1 but swscanf returns int
so it should be sign-extended */
buffer[0] = 0;
- ret = swscanf(buffer, formatd, &result);
+ ret = swscanf(buffer, L"%d", &result);
/* msvcrt returns 0 but should return -1 (later versions do) */
ok( ret == (short)WEOF || broken(ret == 0),
"swscanf returns %x instead of %x\n", ret, WEOF );
+ ret = swscanf(L" \t\n\n", L"%s", results);
+ /* sscanf returns EOF under this case, but swscanf does not return WEOF */
+ ok( ret == 0, "ret = %d\n", ret );
+
buffer[0] = 'a';
buffer[1] = 0x1234;
buffer[2] = 0x1234;
buffer[3] = 'b';
- ret = swscanf(buffer, format2, &c);
+ ret = swscanf(buffer, L"a\x1234%\x1234%c", &c);
ok(ret == 1, "swscanf returned %d\n", ret);
ok(c == 'b', "c = %x\n", c);
}
static void test_swscanf_s(void)
{
- static const wchar_t fmt1[] = {'%','c',0};
- static const wchar_t fmt2[] =
{'%','[','a','-','z',']',0};
-
int (WINAPIV *pswscanf_s)(const wchar_t*,const wchar_t*,...);
HMODULE hmod = GetModuleHandleA("msvcrt.dll");
wchar_t buf[2], out[2];
@@ -356,15 +444,15 @@ static void test_swscanf_s(void)
buf[0] = 'a';
buf[1] = '1';
out[1] = 'b';
- ret = pswscanf_s(buf, fmt1, out, 1);
+ ret = pswscanf_s(buf, L"%c", out, 1);
ok(ret == 1, "swscanf_s returned %d\n", ret);
ok(out[0] == 'a', "out[0] = %x\n", out[0]);
ok(out[1] == 'b', "out[1] = %x\n", out[1]);
- ret = pswscanf_s(buf, fmt2, out, 1);
+ ret = pswscanf_s(buf, L"%[a-z]", out, 1);
ok(!ret, "swscanf_s returned %d\n", ret);
- ret = pswscanf_s(buf, fmt2, out, 2);
+ ret = pswscanf_s(buf, L"%[a-z]", out, 2);
... 2945 lines suppressed ...