riscv64-asm: Add lui, auipc
This commit is contained in:
		
							parent
							
								
									e5a898e510
								
							
						
					
					
						commit
						0b1cc489e1
					
				
					 2 changed files with 53 additions and 0 deletions
				
			
		| 
						 | 
				
			
			@ -179,6 +179,49 @@ static void asm_unary_opcode(TCCState *s1, int token)
 | 
			
		|||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static void asm_emit_u(int token, uint32_t opcode, const Operand* rd, const Operand* rs2)
 | 
			
		||||
{
 | 
			
		||||
    if (rd->type != OP_REG) {
 | 
			
		||||
        tcc_error("'%s': Expected destination operand that is a register", get_tok_str(token, NULL));
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
    if (rs2->type != OP_IM12S && rs2->type != OP_IM32) {
 | 
			
		||||
        tcc_error("'%s': Expected second source operand that is an immediate value", get_tok_str(token, NULL));
 | 
			
		||||
        return;
 | 
			
		||||
    } else if (rs2->e.v >= 0x100000) {
 | 
			
		||||
        tcc_error("'%s': Expected second source operand that is an immediate value between 0 and 0xfffff", get_tok_str(token, NULL));
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
    /* U-type instruction:
 | 
			
		||||
	      31...12 imm[31:12]
 | 
			
		||||
	      11...7 rd
 | 
			
		||||
	      6...0 opcode */
 | 
			
		||||
    gen_le32(opcode | ENCODE_RD(rd->reg) | (rs2->e.v << 12));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static void asm_binary_opcode(TCCState* s1, int token)
 | 
			
		||||
{
 | 
			
		||||
    Operand ops[2];
 | 
			
		||||
    parse_operand(s1, &ops[0]);
 | 
			
		||||
    if (tok == ',')
 | 
			
		||||
        next();
 | 
			
		||||
    else
 | 
			
		||||
        expect("','");
 | 
			
		||||
    parse_operand(s1, &ops[1]);
 | 
			
		||||
 | 
			
		||||
    switch (token) {
 | 
			
		||||
    case TOK_ASM_lui:
 | 
			
		||||
        asm_emit_u(token, (0xD << 2) | 3, &ops[0], &ops[1]);
 | 
			
		||||
        return;
 | 
			
		||||
    case TOK_ASM_auipc:
 | 
			
		||||
        asm_emit_u(token, (0x05 << 2) | 3, &ops[0], &ops[1]);
 | 
			
		||||
        return;
 | 
			
		||||
    default:
 | 
			
		||||
        expect("binary instruction");
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
ST_FUNC void asm_opcode(TCCState *s1, int token)
 | 
			
		||||
{
 | 
			
		||||
    switch (token) {
 | 
			
		||||
| 
						 | 
				
			
			@ -204,6 +247,11 @@ ST_FUNC void asm_opcode(TCCState *s1, int token)
 | 
			
		|||
        asm_unary_opcode(s1, token);
 | 
			
		||||
        return;
 | 
			
		||||
 | 
			
		||||
    case TOK_ASM_lui:
 | 
			
		||||
    case TOK_ASM_auipc:
 | 
			
		||||
        asm_binary_opcode(s1, token);
 | 
			
		||||
        return;
 | 
			
		||||
 | 
			
		||||
    default:
 | 
			
		||||
        expect("known instruction");
 | 
			
		||||
    }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -82,6 +82,11 @@
 | 
			
		|||
#define DEF_ASM_WITH_SUFFIX(x, y) \
 | 
			
		||||
  DEF(TOK_ASM_ ## x ## _ ## y, #x #y)
 | 
			
		||||
 | 
			
		||||
/* Arithmetic */
 | 
			
		||||
 | 
			
		||||
 DEF_ASM(lui)
 | 
			
		||||
 DEF_ASM(auipc)
 | 
			
		||||
 | 
			
		||||
/* Sync */
 | 
			
		||||
 | 
			
		||||
 DEF_ASM(fence)
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
	Add table
		
		Reference in a new issue