14 for ( ; *m != '\0'; m++)
20 process_operand( str, op)
22 register struct t_operand *op;
24 char *glob_lbl(), *strindex();
29 case '#' : op->type = IS_IMMEDIATE;
32 if ( *(op->expr) != '$') { /* #1 */
33 op->val = atoi( str+1);
34 if ( 1 <= op->val && op->val <= 8 ) {
40 if ( arg_type( str+1) == STRING) { /* #$1+$2 */
49 case '(' : if ( strindex( str+1, ',') == NULL)
50 if ( is_reg( str+1)) {
51 op->reg = reg_val( str+1);
53 if ( *(str+4) == '+') /* (sp)+ */
56 op->type = IS_IND_REG;
59 op->type = IS_IND_MEM;
61 for ( str++; *++str != ')';)
65 if ( *(op->expr) == '$')
66 if ( arg_type( op->expr) == STRING) {
69 if ( strlen( op->lbl) == 2)
78 else if ( isdigit( *(op->expr))) /* (1) */
81 op->lbl = glob_lbl( op->expr);
86 if ( *(str+1) == '[') {
87 op->type = IS_IND_IND;
89 for ( str += 2; *++str != ',';)
92 for ( ; *str == ' '; str++)
94 op->reg = reg_val( str);
96 for ( ; *str++ != ']';)
98 if ( *str == ')') /* ([$1, a6]) */
100 else { /* ([8,a6],8) */
101 for ( ; *str++ != ',';)
103 for ( ; *str == ' '; str++)
105 op->expr2 = atoi( str);
110 for ( str++; *++str != ',';)
113 for ( ; *str == ' '; str++)
115 op->reg = reg_val( str);
116 if ( *(str+2) == ')') { /* (4, a0) */
117 int i = atoi(op->expr);
118 if ((*(op->expr) == '-' ||
119 isdigit(*(op->expr))) &&
120 i <= 32767 && i >= -32768) {
121 op->type = IS_IND_REG_DISPL;
123 else op->type = IS_IND_REG_EDISPL;
125 else { /* (0, sp, d0.l*1) */
127 for ( str++; *++str != ',';)
129 for ( ; *str == ' '; str++)
131 op->reg2 = reg_val( str);
133 for ( ; *str++ != '*';)
135 op->scale = atoi( str);
140 case '-' : op->type = IS_DECR; /* -(sp) */
141 op->reg = reg_val( str+2);
144 case '$' : op->type = IS_GLOB_LBL; /* $1 */
149 default : if ( is_reg( str)) {
150 op->reg = reg_val( str);
151 if ( *(str+2) == ':') { /* d2:d1 */
152 op->type = IS_REG_PAIR;
153 op->reg2 = reg_val( str+3);
156 op->type = ( *str == 'd' ? IS_D_REG : IS_A_REG);
158 else if ( isdigit( *str)) { /* 1f */
159 op->type = IS_LOC_LBL;
165 op->type = IS_GLOB_LBL;
166 op->lbl = glob_lbl( str);
177 return( *reg == 's' ? 7 : atoi( reg+1));
185 case 'd' : return( isdigit( *(str+1)));
187 case 's' : return( *(str+1) == 'p');
189 default : return( 0);
199 gl = Malloc( strlen( lbl) + 3);
200 sprintf( gl, "\"%s\"", lbl);
205 /******************************************************************************/
209 register struct t_operand *eaddr;
211 switch ( eaddr->type) {
212 case IS_A_REG : return( 0x08 | eaddr->reg);
214 case IS_D_REG : return( 0x00 | eaddr->reg);
216 case IS_IND_REG : return( 0x10 | eaddr->reg);
218 case IS_INCR : return( 0x18 | eaddr->reg);
220 case IS_DECR : return( 0x20 | eaddr->reg);
222 case IS_IND_MEM : return( 0x39);
224 case IS_IND_IND : return( 0x30 | eaddr->reg);
226 case IS_IND_REG_DISPL : return( 0x28 | eaddr->reg);
228 case IS_IND_REG_EDISPL: return( 0x30 | eaddr->reg);
230 case IS_GLOB_LBL : return( 0x39);
232 case IS_3_OPS : if ( isdigit( *(eaddr->expr)) &&
233 atoi( eaddr->expr) < 128)
234 return( 0x30 | eaddr->reg);
236 fprintf( stderr, "FOUT in IS_3_OPS\n");
240 case IS_IMMEDIATE : return( 0x3c);
242 default : fprintf( stderr,
243 "mode_reg(), wrong operand %d\n",
251 code_extension( eaddr)
252 register struct t_operand *eaddr;
255 switch ( eaddr->type) {
256 case IS_IND_MEM : if ( eaddr->lbl == NULL)
257 @text4( %$( eaddr->expr));
259 @reloc4( %$( eaddr->lbl),
264 case IS_IND_IND : if ( eaddr->expr2 == 0) {
266 @text2( %$(eaddr->expr));
270 @text2( %$(eaddr->expr));
271 @text2( %d(eaddr->expr2));
275 case IS_IND_REG_DISPL : @text2( %$( eaddr->expr));
278 case IS_IND_REG_EDISPL :@text2(0x0170);
279 @text4( %$( eaddr->expr));
282 case IS_GLOB_LBL : @reloc4( %$(eaddr->lbl),
287 case IS_3_OPS : if ( isdigit( *(eaddr->expr)) &&
288 atoi( eaddr->expr) < 128) {
291 ( eaddr->reg2 << 12) |
292 ( two_log( eaddr->scale)<<9) |
293 atoi( eaddr->expr)));
296 fprintf( stderr, "FOUT in IS_3_OPS\n");
300 case IS_IMMEDIATE : if ( eaddr->lbl != NULL)
301 @reloc4( %$(eaddr->lbl),
305 @text4( %$(eaddr->expr));
311 struct t_operand *eaddr;
315 mr = mode_reg( eaddr);
316 return( ((mr & 0x7) << 3) | ((mr & 0x38) >> 3));
320 code_opcode( opcode, field1, field2, eaddr)
321 int opcode, field1, field2;
322 struct t_operand *eaddr;
324 @text2( %d(((opcode & 0xf) << 12) | ((field1 & 0x7) << 9) |
325 ((field2 & 0x7) << 6) | (mode_reg(eaddr) & 0x3f)));
329 /* The attempts to optimize the instruction size when it cannot be done
330 at code-expander generation time is actually quite dangerous, because
331 it may not happen between references to and definitions of (corresponding)
332 local labels. The reason for this is that these offsets are computed
333 at code-expander generation time. Unfortunately, no warning is given,
334 so this has to be checked by hand.
336 code_instr( opcode, field1, field2, eaddr)
337 int opcode, field1, field2;
338 struct t_operand *eaddr;
340 if (eaddr->type == IS_IND_REG_EDISPL) {
341 @__instr_code(%d(((opcode & 0xf) << 12) | ((field1 & 0x7) << 9) |
342 ((field2 & 0x7) << 6)),
343 %d(eaddr->reg), %$(eaddr->expr));
346 code_opcode( opcode, field1, field2, eaddr);
347 code_extension( eaddr);
352 code_move( size, src, dst)
354 struct t_operand *src, *dst;
356 if (src->type == IS_IND_REG_EDISPL) {
357 if (dst->type == IS_IND_REG_EDISPL) {
358 @__moveXX(%d( ((size & 0x3) << 12)),
359 %d(dst->reg), %$(dst->expr),
360 %d(src->reg), %$(src->expr));
363 @__instr_code(%d( ((size & 0x3) << 12)|((reg_mode( dst) & 0x3f) << 6)),
364 %d(src->reg), %$(src->expr));
367 else if (dst->type == IS_IND_REG_EDISPL) {
368 @__move_X(%d( ((size & 0x3) << 12) | (mode_reg( src) & 0x3f)),
369 %d(dst->reg), %$(dst->expr));
372 @text2( %d( ((size & 0x3) << 12) | ((reg_mode( dst) & 0x3f) << 6) |
373 (mode_reg( src) & 0x3f)));
374 code_extension( src);
375 code_extension( dst);
381 struct t_operand *dst;
383 @reloc4( %$(dst->lbl), %$(dst->expr) + 4, PC_REL);
392 for ( log = 0; nr >= 2; nr >>= 1)