msvcr120: Add fegetenv implementation.

Signed-off-by: Piotr Caban <piotr@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Piotr Caban 2016-07-04 11:04:23 +02:00 committed by Alexandre Julliard
parent 6526ac1999
commit 1150c0454d
7 changed files with 46 additions and 4 deletions

View File

@ -88,7 +88,7 @@
@ cdecl abort() ucrtbase.abort
@ cdecl exit(long) ucrtbase.exit
@ stub feclearexcept
@ stub fegetenv
@ cdecl fegetenv(ptr) ucrtbase.fegetenv
@ stub fegetexceptflag
@ stub fegetround
@ stub feholdexcept

View File

@ -2144,7 +2144,7 @@
@ stub fdimf
@ stub fdiml
@ stub feclearexcept
@ stub fegetenv
@ cdecl fegetenv(ptr) MSVCRT_fegetenv
@ stub fegetexceptflag
@ stub fegetround
@ stub feholdexcept

View File

@ -147,6 +147,12 @@ struct MSVCRT_lconv
wchar_t* _W_negative_sign;
};
typedef struct
{
unsigned int control;
unsigned int status;
} fenv_t;
static char* (CDECL *p_setlocale)(int category, const char* locale);
static struct MSVCRT_lconv* (CDECL *p_localeconv)(void);
static size_t (CDECL *p_wcstombs_s)(size_t *ret, char* dest, size_t sz, const wchar_t* src, size_t max);
@ -162,6 +168,8 @@ static int (CDECL *p__finite)(double);
static float (CDECL *p_wcstof)(const wchar_t*, wchar_t**);
static double (CDECL *p_remainder)(double, double);
static int* (CDECL *p_errno)(void);
static int (CDECL *p_fegetenv)(fenv_t*);
static int (CDECL *p__clearfp)(void);
/* make sure we use the correct errno */
#undef errno
@ -207,6 +215,8 @@ static BOOL init(void)
p_wcstof = (void*)GetProcAddress(module, "wcstof");
p_remainder = (void*)GetProcAddress(module, "remainder");
p_errno = (void*)GetProcAddress(module, "_errno");
SET(p_fegetenv, "fegetenv");
SET(p__clearfp, "_clearfp");
if(sizeof(void*) == 8) { /* 64-bit initialization */
SET(p_critical_section_ctor,
"??0critical_section@Concurrency@@QEAA@XZ");
@ -686,6 +696,20 @@ static void test_critical_section(void)
call_func1(p_critical_section_dtor, &cs);
}
static void test_fegetenv(void)
{
int ret;
fenv_t env;
p__clearfp();
ret = p_fegetenv(&env);
ok(!ret, "fegetenv returned %x\n", ret);
ok(env.control == (_EM_INEXACT|_EM_UNDERFLOW|_EM_OVERFLOW|_EM_ZERODIVIDE|_EM_INVALID),
"env.control = %x\n", env.control);
ok(!env.status, "env.status = %x\n", env.status);
}
START_TEST(msvcr120)
{
if (!init()) return;
@ -699,4 +723,5 @@ START_TEST(msvcr120)
test__strtof();
test_remainder();
test_critical_section();
test_fegetenv();
}

View File

@ -1810,7 +1810,7 @@
@ stub fdimf
@ stub fdiml
@ stub feclearexcept
@ stub fegetenv
@ cdecl fegetenv(ptr) msvcr120.fegetenv
@ stub fegetexceptflag
@ stub fegetround
@ stub feholdexcept

View File

@ -1198,6 +1198,17 @@ int CDECL _controlfp_s(unsigned int *cur, unsigned int newval, unsigned int mask
return 0;
}
/*********************************************************************
* fegetenv (MSVCR120.@)
*/
int CDECL MSVCRT_fegetenv(fenv_t *env)
{
env->control = _controlfp(0, 0) & (MSVCRT__EM_INEXACT | MSVCRT__EM_UNDERFLOW |
MSVCRT__EM_OVERFLOW | MSVCRT__EM_ZERODIVIDE | MSVCRT__EM_INVALID);
env->status = _statusfp();
return 0;
}
/*********************************************************************
* __fpe_flt_rounds (UCRTBASE.@)
*/

View File

@ -910,6 +910,12 @@ struct MSVCRT__stat64 {
#define MSVCRT__DN_SAVE_OPERANDS_FLUSH_RESULTS 0x03000000
#define MSVCRT__EM_AMBIGUOUS 0x80000000
typedef struct
{
unsigned int control;
unsigned int status;
} fenv_t;
#define MSVCRT_CLOCKS_PER_SEC 1000
/* signals */

View File

@ -2286,7 +2286,7 @@
@ stub fdimf
@ stub fdiml
@ stub feclearexcept
@ stub fegetenv
@ cdecl fegetenv(ptr) MSVCRT_fegetenv
@ stub fegetexceptflag
@ stub fegetround
@ stub feholdexcept