forked from Mirrors/opensbi
include: Add hard FP access macros and defines
This patch adds hardware floating-point (hard FP) access macros and defines. Signed-off-by: Anup Patel <anup.patel@wdc.com>
This commit is contained in:
@@ -446,6 +446,19 @@
|
||||
#define INSN_MATCH_SD 0x3023
|
||||
#define INSN_MASK_SD 0x707f
|
||||
|
||||
#define INSN_MATCH_FLW 0x2007
|
||||
#define INSN_MASK_FLW 0x707f
|
||||
#define INSN_MATCH_FLD 0x3007
|
||||
#define INSN_MASK_FLD 0x707f
|
||||
#define INSN_MATCH_FLQ 0x4007
|
||||
#define INSN_MASK_FLQ 0x707f
|
||||
#define INSN_MATCH_FSW 0x2027
|
||||
#define INSN_MASK_FSW 0x707f
|
||||
#define INSN_MATCH_FSD 0x3027
|
||||
#define INSN_MASK_FSD 0x707f
|
||||
#define INSN_MATCH_FSQ 0x4027
|
||||
#define INSN_MASK_FSQ 0x707f
|
||||
|
||||
#define INSN_MATCH_C_LD 0x6000
|
||||
#define INSN_MASK_C_LD 0xe003
|
||||
#define INSN_MATCH_C_SD 0xe000
|
||||
|
73
include/sbi/riscv_fp.h
Normal file
73
include/sbi/riscv_fp.h
Normal file
@@ -0,0 +1,73 @@
|
||||
/*
|
||||
* Copyright (c) 2019 Western Digital Corporation or its affiliates.
|
||||
*
|
||||
* Authors:
|
||||
* Anup Patel <anup.patel@wdc.com>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#ifndef __RISCV_FP_H__
|
||||
#define __RISCV_FP_H__
|
||||
|
||||
#include <sbi/riscv_asm.h>
|
||||
#include <sbi/riscv_encoding.h>
|
||||
#include <sbi/sbi_types.h>
|
||||
|
||||
#define GET_PRECISION(insn) (((insn) >> 25) & 3)
|
||||
#define GET_RM(insn) (((insn) >> 12) & 7)
|
||||
#define PRECISION_S 0
|
||||
#define PRECISION_D 1
|
||||
|
||||
#ifdef __riscv_flen
|
||||
|
||||
#define GET_F32_REG(insn, pos, regs) ({ \
|
||||
register s32 value asm("a0") = SHIFT_RIGHT(insn, (pos)-3) & 0xf8; \
|
||||
ulong tmp; \
|
||||
asm ("1: auipc %0, %%pcrel_hi(get_f32_reg); add %0, %0, %1; jalr t0, %0, %%pcrel_lo(1b)" : "=&r"(tmp), "+&r"(value) :: "t0"); \
|
||||
value; })
|
||||
#define SET_F32_REG(insn, pos, regs, val) ({ \
|
||||
register u32 value asm("a0") = (val); \
|
||||
ulong offset = SHIFT_RIGHT(insn, (pos)-3) & 0xf8; \
|
||||
ulong tmp; \
|
||||
asm volatile ("1: auipc %0, %%pcrel_hi(put_f32_reg); add %0, %0, %2; jalr t0, %0, %%pcrel_lo(1b)" : "=&r"(tmp) : "r"(value), "r"(offset) : "t0"); })
|
||||
#define init_fp_reg(i) SET_F32_REG((i) << 3, 3, 0, 0)
|
||||
#define GET_F64_REG(insn, pos, regs) ({ \
|
||||
register ulong value asm("a0") = SHIFT_RIGHT(insn, (pos)-3) & 0xf8; \
|
||||
ulong tmp; \
|
||||
asm ("1: auipc %0, %%pcrel_hi(get_f64_reg); add %0, %0, %1; jalr t0, %0, %%pcrel_lo(1b)" : "=&r"(tmp), "+&r"(value) :: "t0"); \
|
||||
sizeof(ulong) == 4 ? *(int64_t*)value : (int64_t)value; })
|
||||
#define SET_F64_REG(insn, pos, regs, val) ({ \
|
||||
uint64_t __val = (val); \
|
||||
register ulong value asm("a0") = sizeof(ulong) == 4 ? (ulong)&__val : (ulong)__val; \
|
||||
ulong offset = SHIFT_RIGHT(insn, (pos)-3) & 0xf8; \
|
||||
ulong tmp; \
|
||||
asm volatile ("1: auipc %0, %%pcrel_hi(put_f64_reg); add %0, %0, %2; jalr t0, %0, %%pcrel_lo(1b)" : "=&r"(tmp) : "r"(value), "r"(offset) : "t0"); })
|
||||
#define GET_FCSR() csr_read(fcsr)
|
||||
#define SET_FCSR(value) csr_write(fcsr, (value))
|
||||
#define GET_FRM() csr_read(frm)
|
||||
#define SET_FRM(value) csr_write(frm, (value))
|
||||
#define GET_FFLAGS() csr_read(fflags)
|
||||
#define SET_FFLAGS(value) csr_write(fflags, (value))
|
||||
|
||||
#define SET_FS_DIRTY() ((void) 0)
|
||||
|
||||
#else
|
||||
#error "Floating point emulation not supported.\n"
|
||||
#endif
|
||||
|
||||
#define GET_F32_RS1(insn, regs) (GET_F32_REG(insn, 15, regs))
|
||||
#define GET_F32_RS2(insn, regs) (GET_F32_REG(insn, 20, regs))
|
||||
#define GET_F32_RS3(insn, regs) (GET_F32_REG(insn, 27, regs))
|
||||
#define GET_F64_RS1(insn, regs) (GET_F64_REG(insn, 15, regs))
|
||||
#define GET_F64_RS2(insn, regs) (GET_F64_REG(insn, 20, regs))
|
||||
#define GET_F64_RS3(insn, regs) (GET_F64_REG(insn, 27, regs))
|
||||
#define SET_F32_RD(insn, regs, val) (SET_F32_REG(insn, 7, regs, val), SET_FS_DIRTY())
|
||||
#define SET_F64_RD(insn, regs, val) (SET_F64_REG(insn, 7, regs, val), SET_FS_DIRTY())
|
||||
|
||||
#define GET_F32_RS2C(insn, regs) (GET_F32_REG(insn, 2, regs))
|
||||
#define GET_F32_RS2S(insn, regs) (GET_F32_REG(RVC_RS2S(insn), 0, regs))
|
||||
#define GET_F64_RS2C(insn, regs) (GET_F64_REG(insn, 2, regs))
|
||||
#define GET_F64_RS2S(insn, regs) (GET_F64_REG(RVC_RS2S(insn), 0, regs))
|
||||
|
||||
#endif
|
Reference in New Issue
Block a user