1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
|
#include <stdio.h>
#include <string.h>
#include <libmcpu.h>
#include "../utils/mcpu-asm.h"
#define CHECK(c,m) do { if(!(c)) { fprintf(stderr,"FAIL: %s\n",m); return 1; } } while(0)
static int
rejected( const char *src, const char *needle )
{
cpu_asm_image im;
char err[512];
int rc = cpu_assemble_text( src, &im, err, sizeof( err ) );
if( rc == 0 )
{
cpu_asm_image_free( &im );
return( 0 );
}
return( strstr( err, needle ) != 0 );
}
int
main( void )
{
cpu_asm_image im;
char err[512];
static const char *prec = "3.14243987129849274029174912694696912849214e-286";
char src[4096];
__cpu_init();
CHECK( cpu_assemble_text( ".text\nLDR r32@0x00000, -17.0\nHALT\n", &im, err, sizeof( err ) ) == 0,
"exact real32 LDR accepted");
cpu_asm_image_free( &im );
CHECK( cpu_assemble_text( ".text\nLDR r4096@0x00000, 2.0\nHALT\n", &im, err, sizeof( err ) ) == 0,
"exact real64 immediate widened to real4096 accepted");
cpu_asm_image_free( &im );
CHECK( rejected( ".text\nLDR r32@0x00000, 0.1\nHALT\n",
"LDR immediate is not exactly representable as real32;"),
"inexact real32 immediate rejected");
CHECK( rejected( ".text\nLDR r64@0x00000, 0.1\nHALT\n",
"LDR immediate is not exactly representable as real64;"),
"inexact real64 immediate rejected");
snprintf( src, sizeof( src ), ".text\nLDR r64@0x00000, %s\nHALT\n", prec );
CHECK( rejected( src, "LDR immediate is not exactly representable as real64;" ),
"inexact real64 immediate rejected");
snprintf( src, sizeof( src ), ".text\nLDR r4096@0x00000, %s\nHALT\n", prec );
CHECK( rejected( src, "LDR immediate is not exactly representable as real64;" ),
"wide LDR cannot hide binary64 precision loss");
CHECK( cpu_assemble_text( ".text\nLDC c64@0x00000, -17.0r0+32.0j0\nHALT\n", &im, err, sizeof( err ) ) == 0,
"exact complex64 immediate accepted");
cpu_asm_image_free( &im );
CHECK( rejected( ".text\nLDC c128@0x00000, 0.1r0+32.0j0\nHALT\n",
"LDC immediate component is not exactly representable as real32;"),
"inexact complex immediate component rejected");
CHECK( rejected( ".text\nLDC c32@0x00000, 1.0r0+2.0j0\nHALT\n",
"bad LDC destination"),
"complex destination below 64 bits rejected");
CHECK( rejected( ".text\nLDI r128@0x00000, 9223372036854775808\nHALT\n",
"LDI immediate is not exactly representable as integer64;"),
"integer wider than signed IMM64 rejected");
CHECK( rejected( ".text\nLDI r8@0x00000, 255\nHALT\n",
"LDI immediate is not exactly representable as integer8;"),
"narrow integer immediate that changes value rejected");
CHECK( cpu_assemble_text( ".text\nLDI r8@0x00000, -1\nHALT\n", &im, err, sizeof( err ) ) == 0,
"exact signed integer8 immediate accepted");
cpu_asm_image_free( &im );
snprintf( src, sizeof( src ),
".data\n"
".align 16\n"
"wide_real:\n"
" .real 4096, %s\n"
"wide_int:\n"
" .integer 128, 9223372036854775808\n"
"wide_complex:\n"
" .complex 4096, %s, -%s\n"
".text\n"
" LOAD r4096@0x00000, wide_real\n"
" LOAD r128@0x00200, wide_int\n"
" LOAD c4096@0x00400, wide_complex\n"
" HALT\n", prec, prec, prec);
CHECK( cpu_assemble_text( src, &im, err, sizeof( err ) ) == 0,
"DATA fallback with .real/.integer/.complex and LOAD accepted");
cpu_asm_image_free( &im );
__cpu_free_context();
puts( "libcpu immediate exactness regression: PASS" );
return( 0 );
}
|