1 #include <stdio.h>
2
3 double foo = -1.0;
4 double FRT1;
5 double FRT2;
base256(int val)6 int base256(int val)
7 {
8 /* interpret the bitstream representing val as a base 256 number for testing
9 * the parity instrs
10 */
11 int sum = 0;
12 int scale = 1;
13 int i;
14
15 for (i = 0; i < 8; i++) {
16 int bit = val & 1;
17 sum = sum + bit * scale;
18 val <<= 1;
19 scale *= 256;
20 }
21 return sum;
22 }
23
test_parity_instrs()24 void test_parity_instrs()
25 {
26 unsigned long long_word;
27 unsigned int word;
28 int i, parity;
29
30 for (i = 0; i < 50; i++) {
31 word = base256(i);
32 long_word = word;
33 __asm__ volatile ("prtyd %0, %1":"=r" (parity):"r"(long_word));
34 printf("prtyd (%x) => parity=%x\n", i, parity);
35 __asm__ volatile ("prtyw %0, %1":"=r" (parity):"r"(word));
36 printf("prtyw (%x) => parity=%x\n", i, parity);
37 }
38 }
39
test_lfiwax()40 void test_lfiwax()
41 {
42 unsigned long base;
43 unsigned long offset;
44
45 typedef struct {
46 unsigned int hi;
47 unsigned int lo;
48 } int_pair_t;
49
50 int_pair_t *ip;
51 foo = -1024.0;
52 base = (unsigned long) &foo;
53 offset = 0;
54 __asm__ volatile ("lfiwax %0, %1, %2":"=f" (FRT1):"r"(base),
55 "r"(offset));
56 ip = (int_pair_t *) & FRT1;
57 printf("lfiwax (%f) => FRT=(%x, %x)\n", foo, ip->hi, ip->lo);
58
59
60 }
61
62
63
64 /* lfdp FPp, DS(RA) : load float double pair
65 ** FPp = leftmost 64 bits stored at DS(RA)
66 ** FPp+1= rightmost 64 bits stored at DS(RA)
67 ** FPp must be an even float register
68 */
test_double_pair_instrs()69 int test_double_pair_instrs()
70 {
71 typedef struct {
72 double hi;
73 double lo;
74 } dbl_pair_t;
75
76 /* the following decls are for alignment */
77 int i;
78 int j;
79 int k;
80 int l;
81 #ifdef __powerpc64__
82 int m;
83 int n;
84 int o;
85 #endif
86 dbl_pair_t dbl_pair[3]; /* must be quad word aligned */
87 unsigned long base;
88 unsigned long offset;
89
90 for (i = 0; i < 3; i++) {
91 dbl_pair[i].hi = -1024.0 + i;
92 dbl_pair[i].lo = 1024.0 + i + 1;
93 }
94
95 __asm__ volatile ("lfdp 10, %0"::"m" (dbl_pair[0]));
96 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
97 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
98 printf("lfdp (%f, %f) => F_hi=%f, F_lo=%f\n",
99 dbl_pair[0].hi, dbl_pair[0].lo, FRT1, FRT2);
100
101
102 FRT1 = 2.2048;
103 FRT2 = -4.1024;
104 __asm__ volatile ("fmr 10, %0"::"f" (FRT1));
105 __asm__ volatile ("fmr 11, %0"::"f" (FRT2));
106 __asm__ volatile ("stfdp 10, %0"::"m" (dbl_pair[1]));
107 printf("stfdp (%f, %f) => F_hi=%f, F_lo=%f\n",
108 FRT1, FRT2, dbl_pair[1].hi, dbl_pair[1].lo);
109
110 FRT1 = 0.0;
111 FRT2 = -1.0;
112 base = (unsigned long) &dbl_pair;
113 offset = (unsigned long) &dbl_pair[1] - base;
114 __asm__ volatile ("or 20, 0, %0"::"r" (base));
115 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
116 __asm__ volatile ("lfdpx 10, 20, 21");
117 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
118 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
119 printf("lfdpx (%f, %f) => F_hi=%f, F_lo=%f\n",
120 dbl_pair[1].hi, dbl_pair[1].lo, FRT1, FRT2);
121
122 FRT1 = 8.2048;
123 FRT2 = -16.1024;
124 base = (unsigned long) &dbl_pair;
125 offset = (unsigned long) &dbl_pair[2] - base;
126 __asm__ volatile ("or 20, 0, %0"::"r" (base));
127 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
128 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
129 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
130 __asm__ volatile ("stfdpx 10, 20, 21");
131 printf("stfdpx (%f, %f) => F_hi=%f, F_lo=%f\n",
132 FRT1, FRT2, dbl_pair[2].hi, dbl_pair[2].lo);
133 #ifdef __powerpc64__
134 return i + j + k + l + m + n + o;
135 #else
136 return i + j + k + l;
137 #endif
138 }
139
140
141 /* The contents of FRB with bit set 0 set to bit 0 of FRA copied into FRT */
test_fcpsgn()142 void test_fcpsgn()
143 {
144 double A[] = {
145 10.101010,
146 -0.0,
147 0.0,
148 -10.101010
149 };
150
151 double B[] = {
152 11.111111,
153 -0.0,
154 0.0,
155 -11.111111
156 };
157
158 double FRT, FRA, FRB;
159 int i, j;
160
161 for (i = 0; i < 4; i++) {
162 FRA = A[i];
163 for (j = 0; j < 4; j++) {
164 FRB = B[j];
165 __asm__ volatile ("fcpsgn %0, %1, %2":"=f" (FRT):"f"(FRA),
166 "f"(FRB));
167 printf("fcpsgn sign=%f, base=%f => %f\n", FRA, FRB, FRT);
168 }
169 }
170 }
171
172 /* b0 may be non-zero in lwarx/ldarx Power6 instrs */
test_reservation()173 int test_reservation()
174 {
175
176 int RT;
177 int i, j;
178 unsigned long base;
179 unsigned long offset;
180 long arr[4] = { 0xdeadbeef, 0xbad0beef, 0xbeefdead, 0xbeef0bad };
181
182
183 base = (unsigned long) &arr;
184 offset = (unsigned long) &arr[1] - base;
185 __asm__ volatile ("or 20, 0, %0"::"r" (base));
186 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
187 __asm__ volatile ("lwarx %0, 20, 21, 1":"=r" (RT));
188 printf("lwarx => %x\n", RT);
189
190 #ifdef __powerpc64__
191 offset = (unsigned long) &arr[1] - base;
192 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
193 __asm__ volatile ("ldarx %0, 20, 21, 1":"=r" (RT));
194 printf("ldarx => %x\n", RT);
195 #endif
196 return i + j;
197 }
198
main(void)199 int main(void)
200 {
201 (void) test_reservation();
202 test_fcpsgn();
203 (void) test_double_pair_instrs();
204 test_lfiwax();
205 test_parity_instrs();
206 return 0;
207 }
208 #include <stdio.h>
209
210 double foo = -1.0;
211 double FRT1;
212 double FRT2;
base256(int val)213 int base256(int val)
214 {
215 /* interpret the bitstream representing val as a base 256 number for testing
216 * the parity instrs
217 */
218 int sum = 0;
219 int scale = 1;
220 int i;
221
222 for (i = 0; i < 8; i++) {
223 int bit = val & 1;
224 sum = sum + bit * scale;
225 val <<= 1;
226 scale *= 256;
227 }
228 return sum;
229 }
230
test_parity_instrs()231 void test_parity_instrs()
232 {
233 unsigned long long_word;
234 unsigned int word;
235 int i, parity;
236
237 for (i = 0; i < 50; i++) {
238 word = base256(i);
239 long_word = word;
240 __asm__ volatile ("prtyd %0, %1":"=r" (parity):"r"(long_word));
241 printf("prtyd (%x) => parity=%x\n", i, parity);
242 __asm__ volatile ("prtyw %0, %1":"=r" (parity):"r"(word));
243 printf("prtyw (%x) => parity=%x\n", i, parity);
244 }
245 }
246
test_lfiwax()247 void test_lfiwax()
248 {
249 unsigned long base;
250 unsigned long offset;
251
252 typedef struct {
253 unsigned int hi;
254 unsigned int lo;
255 } int_pair_t;
256
257 int_pair_t *ip;
258 foo = -1024.0;
259 base = (unsigned long) &foo;
260 offset = 0;
261 __asm__ volatile ("lfiwax %0, %1, %2":"=f" (FRT1):"r"(base),
262 "r"(offset));
263 ip = (int_pair_t *) & FRT1;
264 printf("lfiwax (%f) => FRT=(%x, %x)\n", foo, ip->hi, ip->lo);
265
266
267 }
268
269
270
271 /* lfdp FPp, DS(RA) : load float double pair
272 ** FPp = leftmost 64 bits stored at DS(RA)
273 ** FPp+1= rightmost 64 bits stored at DS(RA)
274 ** FPp must be an even float register
275 */
test_double_pair_instrs()276 int test_double_pair_instrs()
277 {
278 typedef struct {
279 double hi;
280 double lo;
281 } dbl_pair_t;
282
283 /* the following decls are for alignment */
284 int i;
285 int j;
286 int k;
287 int l;
288 #ifdef __powerpc64__
289 int m;
290 int n;
291 int o;
292 #endif
293 dbl_pair_t dbl_pair[3]; /* must be quad word aligned */
294 unsigned long base;
295 unsigned long offset;
296
297 for (i = 0; i < 3; i++) {
298 dbl_pair[i].hi = -1024.0 + i;
299 dbl_pair[i].lo = 1024.0 + i + 1;
300 }
301
302 __asm__ volatile ("lfdp 10, %0"::"m" (dbl_pair[0]));
303 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
304 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
305 printf("lfdp (%f, %f) => F_hi=%f, F_lo=%f\n",
306 dbl_pair[0].hi, dbl_pair[0].lo, FRT1, FRT2);
307
308
309 FRT1 = 2.2048;
310 FRT2 = -4.1024;
311 __asm__ volatile ("fmr 10, %0"::"f" (FRT1));
312 __asm__ volatile ("fmr 11, %0"::"f" (FRT2));
313 __asm__ volatile ("stfdp 10, %0"::"m" (dbl_pair[1]));
314 printf("stfdp (%f, %f) => F_hi=%f, F_lo=%f\n",
315 FRT1, FRT2, dbl_pair[1].hi, dbl_pair[1].lo);
316
317 FRT1 = 0.0;
318 FRT2 = -1.0;
319 base = (unsigned long) &dbl_pair;
320 offset = (unsigned long) &dbl_pair[1] - base;
321 __asm__ volatile ("or 20, 0, %0"::"r" (base));
322 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
323 __asm__ volatile ("lfdpx 10, 20, 21");
324 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
325 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
326 printf("lfdpx (%f, %f) => F_hi=%f, F_lo=%f\n",
327 dbl_pair[1].hi, dbl_pair[1].lo, FRT1, FRT2);
328
329 FRT1 = 8.2048;
330 FRT2 = -16.1024;
331 base = (unsigned long) &dbl_pair;
332 offset = (unsigned long) &dbl_pair[2] - base;
333 __asm__ volatile ("or 20, 0, %0"::"r" (base));
334 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
335 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
336 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
337 __asm__ volatile ("stfdpx 10, 20, 21");
338 printf("stfdpx (%f, %f) => F_hi=%f, F_lo=%f\n",
339 FRT1, FRT2, dbl_pair[2].hi, dbl_pair[2].lo);
340 #ifdef __powerpc64__
341 return i + j + k + l + m + n + o;
342 #else
343 return i + j + k + l;
344 #endif
345 }
346
347
348 /* The contents of FRB with bit set 0 set to bit 0 of FRA copied into FRT */
test_fcpsgn()349 void test_fcpsgn()
350 {
351 double A[] = {
352 10.101010,
353 -0.0,
354 0.0,
355 -10.101010
356 };
357
358 double B[] = {
359 11.111111,
360 -0.0,
361 0.0,
362 -11.111111
363 };
364
365 double FRT, FRA, FRB;
366 int i, j;
367
368 for (i = 0; i < 4; i++) {
369 FRA = A[i];
370 for (j = 0; j < 4; j++) {
371 FRB = B[j];
372 __asm__ volatile ("fcpsgn %0, %1, %2":"=f" (FRT):"f"(FRA),
373 "f"(FRB));
374 printf("fcpsgn sign=%f, base=%f => %f\n", FRA, FRB, FRT);
375 }
376 }
377 }
378
379 /* b0 may be non-zero in lwarx/ldarx Power6 instrs */
test_reservation()380 int test_reservation()
381 {
382
383 int RT;
384 int i, j;
385 unsigned long base;
386 unsigned long offset;
387 long arr[4] = { 0xdeadbeef, 0xbad0beef, 0xbeefdead, 0xbeef0bad };
388
389
390 base = (unsigned long) &arr;
391 offset = (unsigned long) &arr[1] - base;
392 __asm__ volatile ("or 20, 0, %0"::"r" (base));
393 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
394 __asm__ volatile ("lwarx %0, 20, 21, 1":"=r" (RT));
395 printf("lwarx => %x\n", RT);
396
397 #ifdef __powerpc64__
398 offset = (unsigned long) &arr[1] - base;
399 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
400 __asm__ volatile ("ldarx %0, 20, 21, 1":"=r" (RT));
401 printf("ldarx => %x\n", RT);
402 #endif
403 return i + j;
404 }
405
main(void)406 int main(void)
407 {
408 (void) test_reservation();
409 test_fcpsgn();
410 (void) test_double_pair_instrs();
411 test_lfiwax();
412 test_parity_instrs();
413 return 0;
414 }
415 #include <stdio.h>
416
417 double foo = -1.0;
418 double FRT1;
419 double FRT2;
base256(int val)420 int base256(int val)
421 {
422 /* interpret the bitstream representing val as a base 256 number for testing
423 * the parity instrs
424 */
425 int sum = 0;
426 int scale = 1;
427 int i;
428
429 for (i = 0; i < 8; i++) {
430 int bit = val & 1;
431 sum = sum + bit * scale;
432 val <<= 1;
433 scale *= 256;
434 }
435 return sum;
436 }
437
test_parity_instrs()438 void test_parity_instrs()
439 {
440 unsigned long long_word;
441 unsigned int word;
442 int i, parity;
443
444 for (i = 0; i < 50; i++) {
445 word = base256(i);
446 long_word = word;
447 __asm__ volatile ("prtyd %0, %1":"=r" (parity):"r"(long_word));
448 printf("prtyd (%x) => parity=%x\n", i, parity);
449 __asm__ volatile ("prtyw %0, %1":"=r" (parity):"r"(word));
450 printf("prtyw (%x) => parity=%x\n", i, parity);
451 }
452 }
453
test_lfiwax()454 void test_lfiwax()
455 {
456 unsigned long base;
457 unsigned long offset;
458
459 typedef struct {
460 unsigned int hi;
461 unsigned int lo;
462 } int_pair_t;
463
464 int_pair_t *ip;
465 foo = -1024.0;
466 base = (unsigned long) &foo;
467 offset = 0;
468 __asm__ volatile ("lfiwax %0, %1, %2":"=f" (FRT1):"r"(base),
469 "r"(offset));
470 ip = (int_pair_t *) & FRT1;
471 printf("lfiwax (%f) => FRT=(%x, %x)\n", foo, ip->hi, ip->lo);
472
473
474 }
475
476
477
478 /* lfdp FPp, DS(RA) : load float double pair
479 ** FPp = leftmost 64 bits stored at DS(RA)
480 ** FPp+1= rightmost 64 bits stored at DS(RA)
481 ** FPp must be an even float register
482 */
test_double_pair_instrs()483 int test_double_pair_instrs()
484 {
485 typedef struct {
486 double hi;
487 double lo;
488 } dbl_pair_t;
489
490 /* the following decls are for alignment */
491 int i;
492 int j;
493 int k;
494 int l;
495 #ifdef __powerpc64__
496 int m;
497 int n;
498 int o;
499 #endif
500 dbl_pair_t dbl_pair[3]; /* must be quad word aligned */
501 unsigned long base;
502 unsigned long offset;
503
504 for (i = 0; i < 3; i++) {
505 dbl_pair[i].hi = -1024.0 + i;
506 dbl_pair[i].lo = 1024.0 + i + 1;
507 }
508
509 __asm__ volatile ("lfdp 10, %0"::"m" (dbl_pair[0]));
510 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
511 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
512 printf("lfdp (%f, %f) => F_hi=%f, F_lo=%f\n",
513 dbl_pair[0].hi, dbl_pair[0].lo, FRT1, FRT2);
514
515
516 FRT1 = 2.2048;
517 FRT2 = -4.1024;
518 __asm__ volatile ("fmr 10, %0"::"f" (FRT1));
519 __asm__ volatile ("fmr 11, %0"::"f" (FRT2));
520 __asm__ volatile ("stfdp 10, %0"::"m" (dbl_pair[1]));
521 printf("stfdp (%f, %f) => F_hi=%f, F_lo=%f\n",
522 FRT1, FRT2, dbl_pair[1].hi, dbl_pair[1].lo);
523
524 FRT1 = 0.0;
525 FRT2 = -1.0;
526 base = (unsigned long) &dbl_pair;
527 offset = (unsigned long) &dbl_pair[1] - base;
528 __asm__ volatile ("or 20, 0, %0"::"r" (base));
529 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
530 __asm__ volatile ("lfdpx 10, 20, 21");
531 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
532 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
533 printf("lfdpx (%f, %f) => F_hi=%f, F_lo=%f\n",
534 dbl_pair[1].hi, dbl_pair[1].lo, FRT1, FRT2);
535
536 FRT1 = 8.2048;
537 FRT2 = -16.1024;
538 base = (unsigned long) &dbl_pair;
539 offset = (unsigned long) &dbl_pair[2] - base;
540 __asm__ volatile ("or 20, 0, %0"::"r" (base));
541 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
542 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
543 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
544 __asm__ volatile ("stfdpx 10, 20, 21");
545 printf("stfdpx (%f, %f) => F_hi=%f, F_lo=%f\n",
546 FRT1, FRT2, dbl_pair[2].hi, dbl_pair[2].lo);
547 #ifdef __powerpc64__
548 return i + j + k + l + m + n + o;
549 #else
550 return i + j + k + l;
551 #endif
552 }
553
554
555 /* The contents of FRB with bit set 0 set to bit 0 of FRA copied into FRT */
test_fcpsgn()556 void test_fcpsgn()
557 {
558 double A[] = {
559 10.101010,
560 -0.0,
561 0.0,
562 -10.101010
563 };
564
565 double B[] = {
566 11.111111,
567 -0.0,
568 0.0,
569 -11.111111
570 };
571
572 double FRT, FRA, FRB;
573 int i, j;
574
575 for (i = 0; i < 4; i++) {
576 FRA = A[i];
577 for (j = 0; j < 4; j++) {
578 FRB = B[j];
579 __asm__ volatile ("fcpsgn %0, %1, %2":"=f" (FRT):"f"(FRA),
580 "f"(FRB));
581 printf("fcpsgn sign=%f, base=%f => %f\n", FRA, FRB, FRT);
582 }
583 }
584 }
585
586 /* b0 may be non-zero in lwarx/ldarx Power6 instrs */
test_reservation()587 int test_reservation()
588 {
589
590 int RT;
591 int i, j;
592 unsigned long base;
593 unsigned long offset;
594 long arr[4] = { 0xdeadbeef, 0xbad0beef, 0xbeefdead, 0xbeef0bad };
595
596
597 base = (unsigned long) &arr;
598 offset = (unsigned long) &arr[1] - base;
599 __asm__ volatile ("or 20, 0, %0"::"r" (base));
600 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
601 __asm__ volatile ("lwarx %0, 20, 21, 1":"=r" (RT));
602 printf("lwarx => %x\n", RT);
603
604 #ifdef __powerpc64__
605 offset = (unsigned long) &arr[1] - base;
606 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
607 __asm__ volatile ("ldarx %0, 20, 21, 1":"=r" (RT));
608 printf("ldarx => %x\n", RT);
609 #endif
610 return i + j;
611 }
612
main(void)613 int main(void)
614 {
615 (void) test_reservation();
616 test_fcpsgn();
617 (void) test_double_pair_instrs();
618 test_lfiwax();
619 test_parity_instrs();
620 return 0;
621 }
622 #include <stdio.h>
623
624 double foo = -1.0;
625 double FRT1;
626 double FRT2;
base256(int val)627 int base256(int val)
628 {
629 /* interpret the bitstream representing val as a base 256 number for testing
630 * the parity instrs
631 */
632 int sum = 0;
633 int scale = 1;
634 int i;
635
636 for (i = 0; i < 8; i++) {
637 int bit = val & 1;
638 sum = sum + bit * scale;
639 val <<= 1;
640 scale *= 256;
641 }
642 return sum;
643 }
644
test_parity_instrs()645 void test_parity_instrs()
646 {
647 unsigned long long_word;
648 unsigned int word;
649 int i, parity;
650
651 for (i = 0; i < 50; i++) {
652 word = base256(i);
653 long_word = word;
654 __asm__ volatile ("prtyd %0, %1":"=r" (parity):"r"(long_word));
655 printf("prtyd (%x) => parity=%x\n", i, parity);
656 __asm__ volatile ("prtyw %0, %1":"=r" (parity):"r"(word));
657 printf("prtyw (%x) => parity=%x\n", i, parity);
658 }
659 }
660
test_lfiwax()661 void test_lfiwax()
662 {
663 unsigned long base;
664 unsigned long offset;
665
666 typedef struct {
667 unsigned int hi;
668 unsigned int lo;
669 } int_pair_t;
670
671 int_pair_t *ip;
672 foo = -1024.0;
673 base = (unsigned long) &foo;
674 offset = 0;
675 __asm__ volatile ("lfiwax %0, %1, %2":"=f" (FRT1):"r"(base),
676 "r"(offset));
677 ip = (int_pair_t *) & FRT1;
678 printf("lfiwax (%f) => FRT=(%x, %x)\n", foo, ip->hi, ip->lo);
679
680
681 }
682
683
684
685 /* lfdp FPp, DS(RA) : load float double pair
686 ** FPp = leftmost 64 bits stored at DS(RA)
687 ** FPp+1= rightmost 64 bits stored at DS(RA)
688 ** FPp must be an even float register
689 */
test_double_pair_instrs()690 int test_double_pair_instrs()
691 {
692 typedef struct {
693 double hi;
694 double lo;
695 } dbl_pair_t;
696
697 /* the following decls are for alignment */
698 int i;
699 int j;
700 int k;
701 int l;
702 #ifdef __powerpc64__
703 int m;
704 int n;
705 int o;
706 #endif
707 dbl_pair_t dbl_pair[3]; /* must be quad word aligned */
708 unsigned long base;
709 unsigned long offset;
710
711 for (i = 0; i < 3; i++) {
712 dbl_pair[i].hi = -1024.0 + i;
713 dbl_pair[i].lo = 1024.0 + i + 1;
714 }
715
716 __asm__ volatile ("lfdp 10, %0"::"m" (dbl_pair[0]));
717 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
718 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
719 printf("lfdp (%f, %f) => F_hi=%f, F_lo=%f\n",
720 dbl_pair[0].hi, dbl_pair[0].lo, FRT1, FRT2);
721
722
723 FRT1 = 2.2048;
724 FRT2 = -4.1024;
725 __asm__ volatile ("fmr 10, %0"::"f" (FRT1));
726 __asm__ volatile ("fmr 11, %0"::"f" (FRT2));
727 __asm__ volatile ("stfdp 10, %0"::"m" (dbl_pair[1]));
728 printf("stfdp (%f, %f) => F_hi=%f, F_lo=%f\n",
729 FRT1, FRT2, dbl_pair[1].hi, dbl_pair[1].lo);
730
731 FRT1 = 0.0;
732 FRT2 = -1.0;
733 base = (unsigned long) &dbl_pair;
734 offset = (unsigned long) &dbl_pair[1] - base;
735 __asm__ volatile ("or 20, 0, %0"::"r" (base));
736 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
737 __asm__ volatile ("lfdpx 10, 20, 21");
738 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
739 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
740 printf("lfdpx (%f, %f) => F_hi=%f, F_lo=%f\n",
741 dbl_pair[1].hi, dbl_pair[1].lo, FRT1, FRT2);
742
743 FRT1 = 8.2048;
744 FRT2 = -16.1024;
745 base = (unsigned long) &dbl_pair;
746 offset = (unsigned long) &dbl_pair[2] - base;
747 __asm__ volatile ("or 20, 0, %0"::"r" (base));
748 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
749 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
750 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
751 __asm__ volatile ("stfdpx 10, 20, 21");
752 printf("stfdpx (%f, %f) => F_hi=%f, F_lo=%f\n",
753 FRT1, FRT2, dbl_pair[2].hi, dbl_pair[2].lo);
754 #ifdef __powerpc64__
755 return i + j + k + l + m + n + o;
756 #else
757 return i + j + k + l;
758 #endif
759 }
760
761
762 /* The contents of FRB with bit set 0 set to bit 0 of FRA copied into FRT */
test_fcpsgn()763 void test_fcpsgn()
764 {
765 double A[] = {
766 10.101010,
767 -0.0,
768 0.0,
769 -10.101010
770 };
771
772 double B[] = {
773 11.111111,
774 -0.0,
775 0.0,
776 -11.111111
777 };
778
779 double FRT, FRA, FRB;
780 int i, j;
781
782 for (i = 0; i < 4; i++) {
783 FRA = A[i];
784 for (j = 0; j < 4; j++) {
785 FRB = B[j];
786 __asm__ volatile ("fcpsgn %0, %1, %2":"=f" (FRT):"f"(FRA),
787 "f"(FRB));
788 printf("fcpsgn sign=%f, base=%f => %f\n", FRA, FRB, FRT);
789 }
790 }
791 }
792
793 /* b0 may be non-zero in lwarx/ldarx Power6 instrs */
test_reservation()794 int test_reservation()
795 {
796
797 int RT;
798 int i, j;
799 unsigned long base;
800 unsigned long offset;
801 long arr[4] = { 0xdeadbeef, 0xbad0beef, 0xbeefdead, 0xbeef0bad };
802
803
804 base = (unsigned long) &arr;
805 offset = (unsigned long) &arr[1] - base;
806 __asm__ volatile ("or 20, 0, %0"::"r" (base));
807 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
808 __asm__ volatile ("lwarx %0, 20, 21, 1":"=r" (RT));
809 printf("lwarx => %x\n", RT);
810
811 #ifdef __powerpc64__
812 offset = (unsigned long) &arr[1] - base;
813 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
814 __asm__ volatile ("ldarx %0, 20, 21, 1":"=r" (RT));
815 printf("ldarx => %x\n", RT);
816 #endif
817 return i + j;
818 }
819
main(void)820 int main(void)
821 {
822 (void) test_reservation();
823 test_fcpsgn();
824 (void) test_double_pair_instrs();
825 test_lfiwax();
826 test_parity_instrs();
827 return 0;
828 }
829 #include <stdio.h>
830
831 double foo = -1.0;
832 double FRT1;
833 double FRT2;
base256(int val)834 int base256(int val)
835 {
836 /* interpret the bitstream representing val as a base 256 number for testing
837 * the parity instrs
838 */
839 int sum = 0;
840 int scale = 1;
841 int i;
842
843 for (i = 0; i < 8; i++) {
844 int bit = val & 1;
845 sum = sum + bit * scale;
846 val <<= 1;
847 scale *= 256;
848 }
849 return sum;
850 }
851
test_parity_instrs()852 void test_parity_instrs()
853 {
854 unsigned long long_word;
855 unsigned int word;
856 int i, parity;
857
858 for (i = 0; i < 50; i++) {
859 word = base256(i);
860 long_word = word;
861 __asm__ volatile ("prtyd %0, %1":"=r" (parity):"r"(long_word));
862 printf("prtyd (%x) => parity=%x\n", i, parity);
863 __asm__ volatile ("prtyw %0, %1":"=r" (parity):"r"(word));
864 printf("prtyw (%x) => parity=%x\n", i, parity);
865 }
866 }
867
test_lfiwax()868 void test_lfiwax()
869 {
870 unsigned long base;
871 unsigned long offset;
872
873 typedef struct {
874 unsigned int hi;
875 unsigned int lo;
876 } int_pair_t;
877
878 int_pair_t *ip;
879 foo = -1024.0;
880 base = (unsigned long) &foo;
881 offset = 0;
882 __asm__ volatile ("lfiwax %0, %1, %2":"=f" (FRT1):"r"(base),
883 "r"(offset));
884 ip = (int_pair_t *) & FRT1;
885 printf("lfiwax (%f) => FRT=(%x, %x)\n", foo, ip->hi, ip->lo);
886
887
888 }
889
890
891
892 /* lfdp FPp, DS(RA) : load float double pair
893 ** FPp = leftmost 64 bits stored at DS(RA)
894 ** FPp+1= rightmost 64 bits stored at DS(RA)
895 ** FPp must be an even float register
896 */
test_double_pair_instrs()897 int test_double_pair_instrs()
898 {
899 typedef struct {
900 double hi;
901 double lo;
902 } dbl_pair_t;
903
904 /* the following decls are for alignment */
905 int i;
906 int j;
907 int k;
908 int l;
909 #ifdef __powerpc64__
910 int m;
911 int n;
912 int o;
913 #endif
914 dbl_pair_t dbl_pair[3]; /* must be quad word aligned */
915 unsigned long base;
916 unsigned long offset;
917
918 for (i = 0; i < 3; i++) {
919 dbl_pair[i].hi = -1024.0 + i;
920 dbl_pair[i].lo = 1024.0 + i + 1;
921 }
922
923 __asm__ volatile ("lfdp 10, %0"::"m" (dbl_pair[0]));
924 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
925 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
926 printf("lfdp (%f, %f) => F_hi=%f, F_lo=%f\n",
927 dbl_pair[0].hi, dbl_pair[0].lo, FRT1, FRT2);
928
929
930 FRT1 = 2.2048;
931 FRT2 = -4.1024;
932 __asm__ volatile ("fmr 10, %0"::"f" (FRT1));
933 __asm__ volatile ("fmr 11, %0"::"f" (FRT2));
934 __asm__ volatile ("stfdp 10, %0"::"m" (dbl_pair[1]));
935 printf("stfdp (%f, %f) => F_hi=%f, F_lo=%f\n",
936 FRT1, FRT2, dbl_pair[1].hi, dbl_pair[1].lo);
937
938 FRT1 = 0.0;
939 FRT2 = -1.0;
940 base = (unsigned long) &dbl_pair;
941 offset = (unsigned long) &dbl_pair[1] - base;
942 __asm__ volatile ("or 20, 0, %0"::"r" (base));
943 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
944 __asm__ volatile ("lfdpx 10, 20, 21");
945 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
946 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
947 printf("lfdpx (%f, %f) => F_hi=%f, F_lo=%f\n",
948 dbl_pair[1].hi, dbl_pair[1].lo, FRT1, FRT2);
949
950 FRT1 = 8.2048;
951 FRT2 = -16.1024;
952 base = (unsigned long) &dbl_pair;
953 offset = (unsigned long) &dbl_pair[2] - base;
954 __asm__ volatile ("or 20, 0, %0"::"r" (base));
955 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
956 __asm__ volatile ("fmr %0, 10":"=f" (FRT1));
957 __asm__ volatile ("fmr %0, 11":"=f" (FRT2));
958 __asm__ volatile ("stfdpx 10, 20, 21");
959 printf("stfdpx (%f, %f) => F_hi=%f, F_lo=%f\n",
960 FRT1, FRT2, dbl_pair[2].hi, dbl_pair[2].lo);
961 #ifdef __powerpc64__
962 return i + j + k + l + m + n + o;
963 #else
964 return i + j + k + l;
965 #endif
966 }
967
968
969 /* The contents of FRB with bit set 0 set to bit 0 of FRA copied into FRT */
test_fcpsgn()970 void test_fcpsgn()
971 {
972 double A[] = {
973 10.101010,
974 -0.0,
975 0.0,
976 -10.101010
977 };
978
979 double B[] = {
980 11.111111,
981 -0.0,
982 0.0,
983 -11.111111
984 };
985
986 double FRT, FRA, FRB;
987 int i, j;
988
989 for (i = 0; i < 4; i++) {
990 FRA = A[i];
991 for (j = 0; j < 4; j++) {
992 FRB = B[j];
993 __asm__ volatile ("fcpsgn %0, %1, %2":"=f" (FRT):"f"(FRA),
994 "f"(FRB));
995 printf("fcpsgn sign=%f, base=%f => %f\n", FRA, FRB, FRT);
996 }
997 }
998 }
999
1000 /* b0 may be non-zero in lwarx/ldarx Power6 instrs */
test_reservation()1001 int test_reservation()
1002 {
1003
1004 int RT;
1005 int i, j;
1006 unsigned long base;
1007 unsigned long offset;
1008 long arr[4] = { 0xdeadbeef, 0xbad0beef, 0xbeefdead, 0xbeef0bad };
1009
1010
1011 base = (unsigned long) &arr;
1012 offset = (unsigned long) &arr[1] - base;
1013 __asm__ volatile ("or 20, 0, %0"::"r" (base));
1014 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
1015 __asm__ volatile ("lwarx %0, 20, 21, 1":"=r" (RT));
1016 printf("lwarx => %x\n", RT);
1017
1018 #ifdef __powerpc64__
1019 offset = (unsigned long) &arr[1] - base;
1020 __asm__ volatile ("or 21, 0, %0"::"r" (offset));
1021 __asm__ volatile ("ldarx %0, 20, 21, 1":"=r" (RT));
1022 printf("ldarx => %x\n", RT);
1023 #endif
1024 return i + j;
1025 }
1026
main(void)1027 int main(void)
1028 {
1029 (void) test_reservation();
1030 test_fcpsgn();
1031 (void) test_double_pair_instrs();
1032 test_lfiwax();
1033 test_parity_instrs();
1034 return 0;
1035 }
1036