1ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
2ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/* Derived from: */
3ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
4ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*
5ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  x86 CPU test
6ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *
7ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  Copyright (c) 2003 Fabrice Bellard
8ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *
9ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  This program is free software; you can redistribute it and/or modify
10ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  it under the terms of the GNU General Public License as published by
11ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  the Free Software Foundation; either version 2 of the License, or
12ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  (at your option) any later version.
13ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *
14ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  This program is distributed in the hope that it will be useful,
15ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  GNU General Public License for more details.
18ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *
19ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  You should have received a copy of the GNU General Public License
20ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  along with this program; if not, write to the Free Software
21ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown */
23ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
24ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
25ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#include <stdlib.h>
26ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#include <stdio.h>
27ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#include <string.h>
28ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#include <inttypes.h>
29ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#include <math.h>
30ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
31ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/**********************************************/
32ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
33ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownvoid test_fops(double a, double b)
34ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown{
35ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f b=%f a+b=%f\n", a, b, a + b);
36ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f b=%f a-b=%f\n", a, b, a - b);
37ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f b=%f a*b=%f\n", a, b, a * b);
38ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f b=%f a/b=%f\n", a, b, a / b);
39ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f b=%f fmod(a, b)=%f\n", a, b, fmod(a, b));
40ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f sqrt(a)=%f\n", a, sqrt(a));
41ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f sin(a)=%f\n", a, sin(a));
42ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f cos(a)=%f\n", a, cos(a));
43ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f tan(a)=%f\n", a, tan(a));
44ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f log(a)=%f\n", a, log(a));
45ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f exp(a)=%f\n", a, exp(a));
46ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f b=%f atan2(a, b)=%f\n", a, b, atan2(a, b));
47ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    /* just to test some op combining */
48ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f asin(sin(a))=%f\n", a, asin(sin(a)));
49ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f acos(cos(a))=%f\n", a, acos(cos(a)));
50ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f atan(tan(a))=%f\n", a, atan(tan(a)));
51ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown}
52ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define CC_C    0x0001
53ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define CC_P    0x0004
54ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define CC_A    0x0010
55ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define CC_Z    0x0040
56ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define CC_S    0x0080
57ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define CC_O    0x0800
58ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
59ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
60ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownvoid test_fcmp(double a, double b)
61ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown{
62ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("(%f<%f)=%d\n",
63ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown           a, b, a < b);
64ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("(%f<=%f)=%d\n",
65ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown           a, b, a <= b);
66ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("(%f==%f)=%d\n",
67ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown           a, b, a == b);
68ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("(%f>%f)=%d\n",
69ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown           a, b, a > b);
70ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("(%f<=%f)=%d\n",
71ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown           a, b, a >= b);
72ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    {
73ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        unsigned int eflags;
74ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        /* test f(u)comi instruction */
75ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        asm("fcomi %2, %1\n"
76ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown            "pushf\n"
77ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown            "pop %0\n"
78ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown            : "=r" (eflags)
79ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown            : "t" (a), "u" (b));
80ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        printf("fcomi(%f %f)=%08x\n", a, b, eflags & (CC_Z | CC_P | CC_C));
81ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    }
82ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown}
83ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
84ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownvoid test_fcvt(double a)
85ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown{
86ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    float fa;
87ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    long double la;
88ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    int16_t fpuc;
89ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    int i;
90ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    int64_t lla;
91ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    int ia;
92ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    int16_t wa;
93ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    double ra;
94ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
95ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    fa = a;
96ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    la = a;
97ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("(float)%f = %f\n", a, fa);
98ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("(long double)%f = %Lf\n", a, la);
99ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%016llx\n", *(long long *)&a);
100ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("la=%016llx %04x\n", *(long long *)&la,
101ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown           *(unsigned short *)((char *)(&la) + 8));
102ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
103ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    /* test all roundings */
104ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    asm volatile ("fstcw %0" : "=m" (fpuc));
105ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    for(i=0;i<4;i++) {
106ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown      int16_t tmp = (fpuc & ~0x0c00) | (i << 10);
107ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        asm volatile ("fldcw %0" : : "m" (tmp));
108663860b1408516d02ebfcb3a9999a134e6cfb223Ben Cheng        asm volatile ("fists %0" : "=m" (wa) : "t" (a));
109ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        asm volatile ("fistl %0" : "=m" (ia) : "t" (a));
110ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        asm volatile ("fistpll %0" : "=m" (lla) : "t" (a) : "st");
111ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        asm volatile ("frndint ; fstl %0" : "=m" (ra) : "t" (a));
112ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        asm volatile ("fldcw %0" : : "m" (fpuc));
113ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        printf("(short)a = %d\n", wa);
114ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        printf("(int)a = %d\n", ia);
115ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        printf("(int64_t)a = %lld\n", lla);
116ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        printf("rint(a) = %f\n", ra);
117ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    }
118ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown}
119ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
120ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define TEST(N) \
121ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    asm("fld" #N : "=t" (a)); \
122ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("fld" #N "= %f\n", a);
123ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
124ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownvoid test_fconst(void)
125ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown{
126ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    double a;
127ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST(1);
128ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST(l2t);
129ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST(l2e);
130ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST(pi);
131ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST(lg2);
132ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST(ln2);
133ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST(z);
134ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown}
135ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
136ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownvoid test_fbcd(double a)
137ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown{
138ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    unsigned short bcd[5];
139ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    double b;
140ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
141ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    asm("fbstp %0" : "=m" (bcd[0]) : "t" (a) : "st");
142ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    asm("fbld %1" : "=t" (b) : "m" (bcd[0]));
143ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("a=%f bcd=%04x%04x%04x%04x%04x b=%f\n",
144ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown           a, bcd[4], bcd[3], bcd[2], bcd[1], bcd[0], b);
145ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown}
146ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
147ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define TEST_ENV(env, save, restore)\
148ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown{\
149ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    memset((env), 0xaa, sizeof(*(env)));\
150ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    for(i=0;i<5;i++)\
151ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        asm volatile ("fldl %0" : : "m" (dtab[i]));\
152ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    asm(save " %0\n" : : "m" (*(env)));\
153ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    asm(restore " %0\n": : "m" (*(env)));\
154ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    for(i=0;i<5;i++)\
155ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        asm volatile ("fstpl %0" : "=m" (rtab[i]));\
156ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    for(i=0;i<5;i++)\
157ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        printf("res[%d]=%f\n", i, rtab[i]);\
158ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("fpuc=%04x fpus=%04x fptag=%04x\n",\
159ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown           (env)->fpuc,\
160ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown           (env)->fpus & 0xff00,\
161ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown           (env)->fptag);\
162ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown}
163ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
164ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownvoid test_fenv(void)
165ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown{
166ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    struct __attribute__((packed)) {
167ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        uint16_t fpuc;
168ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        uint16_t dummy1;
169ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        uint16_t fpus;
170ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        uint16_t dummy2;
171ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        uint16_t fptag;
172ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        uint16_t dummy3;
173ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        uint32_t ignored[4];
174ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        long double fpregs[8];
175ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    } float_env32;
176ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    struct __attribute__((packed)) {
177ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        uint16_t fpuc;
178ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        uint16_t fpus;
179ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        uint16_t fptag;
180ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        uint16_t ignored[4];
181ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        long double fpregs[8];
182ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    } float_env16;
183ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    double dtab[8];
184ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    double rtab[8];
185ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    int i;
186ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
187ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    for(i=0;i<8;i++)
188ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        dtab[i] = i + 1;
189ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
190ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST_ENV(&float_env16, "data16/fnstenv", "data16/fldenv");
191ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST_ENV(&float_env16, "data16/fnsave", "data16/frstor");
192ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST_ENV(&float_env32, "fnstenv", "fldenv");
193ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST_ENV(&float_env32, "fnsave", "frstor");
194ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
195ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    /* test for ffree */
196ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    for(i=0;i<5;i++)
197ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        asm volatile ("fldl %0" : : "m" (dtab[i]));
198ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    asm volatile("ffree %st(2)");
199ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    asm volatile ("fnstenv %0\n" : : "m" (float_env32));
200ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    asm volatile ("fninit");
201ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("fptag=%04x\n", float_env32.fptag);
202ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown}
203ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
204ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
205ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define TEST_FCMOV(a, b, eflags, CC)\
206ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown{\
207ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    double res;\
208ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    asm("push %3\n"\
209ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        "popf\n"\
210ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        "fcmov" CC " %2, %0\n"\
211ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        : "=t" (res)\
212ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        : "0" (a), "u" (b), "g" (eflags));\
213ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    printf("fcmov%s eflags=0x%04x-> %f\n", \
214ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown           CC, eflags, res);\
215ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown}
216ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
217ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownvoid test_fcmov(void)
218ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown{
219ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    double a, b;
220ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    int eflags, i;
221ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
222ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    a = 1.0;
223ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    b = 2.0;
224ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    for(i = 0; i < 4; i++) {
225ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        eflags = 0;
226ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        if (i & 1)
227ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown            eflags |= CC_C;
228ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        if (i & 2)
229ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown            eflags |= CC_Z;
230ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        TEST_FCMOV(a, b, eflags, "b");
231ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        TEST_FCMOV(a, b, eflags, "e");
232ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        TEST_FCMOV(a, b, eflags, "be");
233ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        TEST_FCMOV(a, b, eflags, "nb");
234ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        TEST_FCMOV(a, b, eflags, "ne");
235ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown        TEST_FCMOV(a, b, eflags, "nbe");
236ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    }
237ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST_FCMOV(a, b, 0, "u");
238ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST_FCMOV(a, b, CC_P, "u");
239ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST_FCMOV(a, b, 0, "nu");
240ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    TEST_FCMOV(a, b, CC_P, "nu");
241ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown}
242ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
243ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownvoid test_floats(void)
244ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown{
245ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fops(2, 3);
246ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fops(1.4, -5);
247ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fcmp(2, -1);
248ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fcmp(2, 2);
249ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fcmp(2, 3);
250ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fcvt(0.5);
251ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fcvt(-0.5);
252ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fcvt(1.0/7.0);
253ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fcvt(-1.0/9.0);
254ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fcvt(32768);
255ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fcvt(-1e20);
256ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown    test_fconst();
257ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown}
258ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown
259ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownint main ( void )
260ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown{
261ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown  test_floats();
262ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown  return 0;
263ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown}
264