Mercurial > hg > index.cgi
annotate lwasm/insn_rel.c @ 577:e49d24f4a9a5
Correct bug in the object file output code leading to stack corruption
It turns out leaving a pointer to a stack allocated temporary in a
persistent data structure is not conducive to correct program operation.
Undo the export check setup in the object file output sequence so a
pointer to stack allocated memory is not left hanging when the function
returns. This seems to correct at least one mysterious crash bug, and
possibly others.
Thanks to Boisy Pitre for reporting the crash bug that led to this
discovery, as well as a previous crash bug that likely has the same
root cause.
Additional thanks to Ciaran Anscomb whose debugger wielding wizardry
revealed the exact location of this particular bit of unbrilliance.
author | William Astle <lost@l-w.ca> |
---|---|
date | Sat, 03 Aug 2024 14:30:06 -0600 |
parents | cad5937314cb |
children |
rev | line source |
---|---|
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
1 /* |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
2 insn_rel.c |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
3 Copyright © 2009 William Astle |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
4 |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
5 This file is part of LWASM. |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
6 |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
7 LWASM is free software: you can redistribute it and/or modify it under the |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
8 terms of the GNU General Public License as published by the Free Software |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
9 Foundation, either version 3 of the License, or (at your option) any later |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
10 version. |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
11 |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
12 This program is distributed in the hope that it will be useful, but WITHOUT |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
13 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
14 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
15 more details. |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
16 |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
17 You should have received a copy of the GNU General Public License along with |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
18 this program. If not, see <http://www.gnu.org/licenses/>. |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
19 */ |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
20 |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
21 /* |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
22 for handling relative mode instructions |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
23 */ |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
24 |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
25 #include <ctype.h> |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
26 #include <stdlib.h> |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
27 #include <stdio.h> |
377
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
28 #include <string.h> |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
29 |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
30 #include <lw_expr.h> |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
31 |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
32 #include "lwasm.h" |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
33 #include "instab.h" |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
34 |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
35 /* |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
36 For generic relative, the first "opcode" is the natural opcode for the |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
37 mneumonic. The second "opcode" is the natural size of the relative offset. |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
38 These will be used when pragma autobranchlength is NOT in effect. |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
39 |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
40 The third "opcode" is the short (8 bit) version of the branch. The final one |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
41 is the long (16 bit) version of the branch. These will be used when pragma |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
42 autobranchlength is in effect. |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
43 |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
44 When autobranchlength is in effect, the branch target can be prefixed with |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
45 either < or > to force a short or long branch. Note that in this mode, |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
46 a > or < on its own still specifies a branch point. |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
47 |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
48 */ |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
49 PARSEFUNC(insn_parse_relgen) |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
50 { |
377
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
51 lw_expr_t t = NULL, e1, e2; |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
52 |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
53 l -> lint = -1; |
211
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
54 l -> maxlen = OPLEN(instab[l -> insn].ops[3]) + 2; |
241
d0e9dbe9afbe
Add new heuristic for resolving instruction sizes.
William Astle <lost@l-w.ca>
parents:
211
diff
changeset
|
55 l -> minlen = OPLEN(instab[l -> insn].ops[2]) + 1; |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
56 if (CURPRAGMA(l, PRAGMA_AUTOBRANCHLENGTH) == 0) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
57 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
58 l -> lint = instab[l -> insn].ops[1]; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
59 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
60 else |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
61 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
62 if (**p == '>' && (((*p)[1]) && !isspace((*p)[1]))) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
63 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
64 (*p)++; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
65 l -> lint = 16; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
66 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
67 else if (**p == '<' && (((*p)[1]) && !isspace((*p)[1]))) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
68 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
69 (*p)++; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
70 l -> lint = 8; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
71 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
72 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
73 |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
74 /* forced sizes handled */ |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
75 |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
76 // sometimes there is a "#", ignore if there |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
77 if (**p == '#') |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
78 (*p)++; |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
79 |
377
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
80 if (CURPRAGMA(l, PRAGMA_QRTS)) |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
81 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
82 // handle ?RTS conditional return |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
83 if (**p == '?') |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
84 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
85 if (strncasecmp(*p, "?RTS", 4) == 0) |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
86 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
87 (*p) += 4; |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
88 |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
89 line_t *cl = l; |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
90 for (cl = cl->prev; cl; cl = cl->prev) |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
91 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
92 if (cl->insn == -1) |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
93 continue; |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
94 |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
95 if (l->addr->value - cl->addr->value > 128) |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
96 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
97 cl = NULL; |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
98 break; |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
99 } |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
100 |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
101 if (cl->conditional_return) |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
102 break; |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
103 |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
104 if (instab[cl->insn].ops[0] == 0x39) |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
105 break; |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
106 } |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
107 |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
108 if (cl) |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
109 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
110 l->lint = -1; |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
111 if (cl->conditional_return) |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
112 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
113 e2 = lw_expr_build(lw_expr_type_special, lwasm_expr_lineaddr, cl); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
114 e1 = lw_expr_build(lw_expr_type_int, 2); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
115 t = lw_expr_build(lw_expr_type_oper, lw_expr_oper_plus, e1, e2); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
116 } |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
117 else |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
118 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
119 t = lw_expr_build(lw_expr_type_special, lwasm_expr_lineaddr, cl); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
120 } |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
121 } |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
122 else |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
123 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
124 l->conditional_return = 1; |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
125 |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
126 // t = * + 1 |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
127 |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
128 e2 = lw_expr_build(lw_expr_type_special, lwasm_expr_lineaddr, l); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
129 e1 = lw_expr_build(lw_expr_type_int, 1); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
130 t = lw_expr_build(lw_expr_type_oper, lw_expr_oper_plus, e1, e2); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
131 |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
132 lw_expr_destroy(e1); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
133 lw_expr_destroy(e2); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
134 } |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
135 } |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
136 } |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
137 } |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
138 |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
139 if (!t) |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
140 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
141 t = lwasm_parse_expr(as, p); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
142 } |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
143 |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
144 if (!t) |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
145 { |
370
8764142b3192
Convert internal error/warning handling framework to a new unified system
William Astle <lost@l-w.ca>
parents:
241
diff
changeset
|
146 lwasm_register_error(as, l, E_OPERAND_BAD); |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
147 return; |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
148 } |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
149 |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
150 // if we know the length of the instruction, set it now |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
151 if (l -> lint == 8) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
152 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
153 l -> len = OPLEN(instab[l -> insn].ops[2]) + 1; |
377
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
154 if (l->conditional_return) l->len++; |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
155 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
156 else if (l -> lint == 16) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
157 { |
122
2be2649841f8
Fixed embarrassing off by one in insn_rel length calculation
lost@l-w.ca
parents:
116
diff
changeset
|
158 l -> len = OPLEN(instab[l -> insn].ops[3]) + 2; |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
159 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
160 |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
161 // the offset calculation here depends on the length of this line! |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
162 // how to calculate requirements? |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
163 // this is the same problem faced by ,pcr indexing |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
164 e2 = lw_expr_build(lw_expr_type_special, lwasm_expr_linelen, l); |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
165 e1 = lw_expr_build(lw_expr_type_oper, lw_expr_oper_minus, t, e2); |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
166 lw_expr_destroy(e2); |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
167 e2 = lw_expr_build(lw_expr_type_oper, lw_expr_oper_minus, e1, l -> addr); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
168 lw_expr_destroy(e1); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
169 lwasm_save_expr(l, 0, e2); |
89 | 170 lw_expr_destroy(t); |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
171 |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
172 if (l -> len == -1) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
173 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
174 e1 = lw_expr_copy(e2); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
175 l -> len = OPLEN(instab[l -> insn].ops[2]) + 1; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
176 lwasm_reduce_expr(as, e1); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
177 l -> len = -1; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
178 if (lw_expr_istype(e1, lw_expr_type_int)) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
179 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
180 int v; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
181 v = lw_expr_intval(e1); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
182 if (v >= -128 && v <= 127) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
183 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
184 l -> lint = 8; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
185 l -> len = OPLEN(instab[l -> insn].ops[2]) + 1; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
186 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
187 else |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
188 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
189 l -> lint = 16; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
190 l -> len = OPLEN(instab[l -> insn].ops[3]) + 2; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
191 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
192 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
193 lw_expr_destroy(e1); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
194 } |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
195 } |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
196 |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
197 RESOLVEFUNC(insn_resolve_relgen) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
198 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
199 lw_expr_t e, e2; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
200 int offs; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
201 |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
202 if (l -> lint == -1) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
203 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
204 e = lwasm_fetch_expr(l, 0); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
205 if (!lw_expr_istype(e, lw_expr_type_int)) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
206 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
207 // temporarily set the instruction length to see if we get a |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
208 // constant for our expression; if so, we can select an instruction |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
209 // size |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
210 e2 = lw_expr_copy(e); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
211 // size of 8-bit opcode + 8 bit offset |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
212 l -> len = OPLEN(instab[l -> insn].ops[2]) + 1; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
213 lwasm_reduce_expr(as, e2); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
214 l -> len = -1; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
215 if (lw_expr_istype(e2, lw_expr_type_int)) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
216 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
217 // it reduced to an integer; is it in 8 bit range? |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
218 offs = lw_expr_intval(e2); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
219 if (offs >= -128 && offs <= 127) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
220 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
221 // fits in 8 bits |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
222 l -> len = OPLEN(instab[l -> insn].ops[2]) + 1; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
223 l -> lint = 8; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
224 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
225 else |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
226 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
227 // requires 16 bits |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
228 l -> len = OPLEN(instab[l -> insn].ops[3]) + 2; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
229 l -> lint = 16; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
230 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
231 } |
211
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
232 // size of 8-bit opcode + 8 bit offset |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
233 l -> len = OPLEN(instab[l -> insn].ops[2]) + 1; |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
234 as -> pretendmax = 1; |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
235 lwasm_reduce_expr(as, e2); |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
236 as -> pretendmax = 0; |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
237 l -> len = -1; |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
238 if (lw_expr_istype(e2, lw_expr_type_int)) |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
239 { |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
240 // it reduced to an integer; is it in 8 bit range? |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
241 offs = lw_expr_intval(e2); |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
242 if (offs >= -128 && offs <= 127) |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
243 { |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
244 // fits in 8 bits with a worst case scenario |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
245 l -> len = OPLEN(instab[l -> insn].ops[2]) + 1; |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
246 l -> lint = 8; |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
247 } |
6f2e18f1fe67
Improve autobranchlength pragma
William Astle <lost@l-w.ca>
parents:
122
diff
changeset
|
248 } |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
249 lw_expr_destroy(e2); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
250 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
251 if (lw_expr_istype(e, lw_expr_type_int)) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
252 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
253 // it reduced to an integer; is it in 8 bit range? |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
254 offs = lw_expr_intval(e); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
255 if (offs >= -128 && offs <= 127) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
256 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
257 // fits in 8 bits |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
258 l -> len = OPLEN(instab[l -> insn].ops[2]) + 1; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
259 l -> lint = 8; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
260 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
261 else |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
262 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
263 // requires 16 bits |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
264 l -> len = OPLEN(instab[l -> insn].ops[3]) + 2; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
265 l -> lint = 16; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
266 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
267 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
268 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
269 if (!force) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
270 return; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
271 |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
272 if (l -> len == -1) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
273 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
274 l -> len = OPLEN(instab[l -> insn].ops[3]) + 2; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
275 l -> lint = 16; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
276 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
277 } |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
278 |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
279 EMITFUNC(insn_emit_relgen) |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
280 { |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
281 lw_expr_t e; |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
282 int offs; |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
283 |
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
284 e = lwasm_fetch_expr(l, 0); |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
285 if (l -> lint == 8) |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
286 { |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
287 if (!lw_expr_istype(e, lw_expr_type_int)) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
288 { |
370
8764142b3192
Convert internal error/warning handling framework to a new unified system
William Astle <lost@l-w.ca>
parents:
241
diff
changeset
|
289 lwasm_register_error(as, l, E_EXPRESSION_NOT_CONST); |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
290 return; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
291 } |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
292 |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
293 offs = lw_expr_intval(e); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
294 if (l -> lint == 8 && (offs < -128 || offs > 127)) |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
295 { |
370
8764142b3192
Convert internal error/warning handling framework to a new unified system
William Astle <lost@l-w.ca>
parents:
241
diff
changeset
|
296 lwasm_register_error(as, l, E_BYTE_OVERFLOW); |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
297 return; |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
298 } |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
299 |
377
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
300 if (l->conditional_return) |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
301 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
302 lwasm_emitop(l, instab[l->insn].ops[2] ^ 1); /* flip branch, add RTS */ |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
303 lwasm_emit(l, 1); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
304 lwasm_emit(l, 0x39); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
305 l->cycle_adj = 3; |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
306 } |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
307 else |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
308 { |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
309 lwasm_emitop(l, instab[l->insn].ops[2]); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
310 lwasm_emit(l, offs); |
67373a053c49
Add ?rts target for branch instructions
William Astle <lost@l-w.ca>
parents:
376
diff
changeset
|
311 } |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
312 } |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
313 else |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
314 { |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
315 lwasm_emitop(l, instab[l -> insn].ops[3]); |
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
316 lwasm_emitexpr(l, e, 2); |
455 | 317 if (CURPRAGMA(l, PRAGMA_OPERANDSIZE) && lw_expr_istype(e, lw_expr_type_int)) |
318 { | |
319 offs = lw_expr_intval(e); | |
320 if (offs >= -128 && offs <= 127) | |
321 { | |
322 lwasm_register_error(as, l, W_OPERAND_SIZE); | |
323 } | |
324 } | |
116
7b0716264251
Pragma autobranchlength implementation completed
lost@l-w.ca
parents:
91
diff
changeset
|
325 } |
0
2c24602be78f
Initial import from lwtools 3.0.1 version, with new hand built build system and file reorganization
lost@l-w.ca
parents:
diff
changeset
|
326 } |