1
2#include <stdio.h>
3#include <stdlib.h>
4
5double do_fsqrt ( double x )
6{
7  double block[2];
8  block[0] = x;
9  __asm__ __volatile__(
10     "lfd %%f1, 0(%0)\n\t"
11     "fsqrt %%f1,%%f1\n\t"
12     "stfd %%f1, 8(%0)"
13     : /*out*/
14     : /*in*/ "b" (&block[0])
15     : /*trash*/ "memory", "fr1"
16  );
17  return block[1];
18}
19
20double do_fsqrts ( double x )
21{
22  double block[2];
23  block[0] = x;
24  __asm__ __volatile__(
25     "lfd %%f1, 0(%0)\n\t"
26     "fsqrts %%f1,%%f1\n\t"
27     "stfd %%f1, 8(%0)"
28     : /*out*/
29     : /*in*/ "b" (&block[0])
30     : /*trash*/ "memory", "fr1"
31     );
32  return block[1];
33}
34
35////////////////////////////////////////////////////////////
36
37void do_one ( char* name,
38              double(*f)(double),
39              double* args, int nargs,
40              char* argfmt, char* resfmt )
41{
42  int i;
43  double a, r;
44  printf("\n");
45
46  for (i = 0; i < nargs; i++) {
47    a = args[i];
48    r = f(a);
49    printf("%s ", name);
50    printf(argfmt, a);
51    printf(" -> ");
52    printf(resfmt, r);
53    printf("\n");
54  }
55}
56
57int main ( void )
58{
59  int nargs = 19;
60  double* args = malloc(nargs * sizeof(double));
61  args[0]  =  0.0;
62  args[1]  =  1.0 / 0.0; // inf
63  args[2]  = -args[1]; //  -inf
64  args[3]  = args[2]/args[2]; // nan
65  args[4]  = -args[3]; // -nan
66  args[5]  = -5e100;
67  args[6]  = -5e20;
68  args[7]  = -501.0;
69  args[8]  = -6.0;
70  args[9]  = -1.0;
71  args[10] = -2e-20;
72  args[11] = -2e-200;
73  args[12] =  2e-200;
74  args[13] =  2e-20;
75  args[14] =  1.0;
76  args[15] =  6.0;
77  args[16] =  501.0;
78  args[17] =  5e20;
79  args[18] =  5e100;
80
81  do_one( "fsqrt",  do_fsqrt,  args, nargs, "%e", "%20.14e");
82  do_one( "fsqrts", do_fsqrts, args, nargs, "%e", "%e");
83
84  free(args);
85  return 0;
86}
87