sh-dis/c/state.h

91 lines
2.6 KiB
C

#pragma once
#include <assert.h>
#include <stdint.h>
#include <stdbool.h>
#include "status_bits.h"
#define SR__RB (1 << 29)
#define SR__MD (1 << 30)
#define BANK(sr) (((sr) & SR__RB) && ((sr) & SR__MD))
#define REGN(sr, x) (((x) & (1 << 3)) ? (x) : ((x) ^ (BANK(sr) << 4)))
#define REG(state, x) ((state)->general_register[REGN((state)->sr.value, (x))])
#define REGN_BANK(sr, x) (((x) & (1 << 3)) ? (x) : ((x) ^ ((!BANK(sr)) << 4)))
#define REG_BANK(state, x) ((state)->general_register[REGN_BANK((state)->sr.value, (x))])
static_assert(REGN(0, 0 ) == 0 );
static_assert(REGN(0, 7 ) == 7 );
static_assert(REGN(0, 8 ) == 8 );
static_assert(REGN(0, 15) == 15);
static_assert(REGN(SR__MD | SR__RB, 0 ) == 16);
static_assert(REGN(SR__MD | SR__RB, 7 ) == 23);
static_assert(REGN(SR__MD | SR__RB, 8 ) == 8 );
static_assert(REGN(SR__MD | SR__RB, 15) == 15);
static_assert(REGN_BANK(0, 0 ) == 16);
static_assert(REGN_BANK(0, 7 ) == 23);
static_assert(REGN_BANK(0, 8 ) == 8 );
static_assert(REGN_BANK(0, 15) == 15);
static_assert(REGN_BANK(SR__MD | SR__RB, 0 ) == 0 );
static_assert(REGN_BANK(SR__MD | SR__RB, 7 ) == 7 );
static_assert(REGN_BANK(SR__MD | SR__RB, 8 ) == 8 );
static_assert(REGN_BANK(SR__MD | SR__RB, 15) == 15);
union floating_point_registers {
uint32_t fr[32];
uint64_t dr[16];
uint32_t fv[8][4];
uint32_t fm[2][16];
};
static_assert((sizeof (union floating_point_registers)) == 32 * 4);
#define FR_N(state, x) ((x) ^ ((state)->fpscr.bits.fr << 4))
#define FR_(state, x) ((state)->floating_point_register.fr[FR_N(state, x)])
#define DR2_N(state, x) ((x) ^ ((state)->fpscr.bits.fr << 3))
#define DR2_(state, x) ((state)->floating_point_register.dr[DR2_N(state, x)])
#define FP2_ DR2_
#define XD2_N(state, x) ((x) ^ ((!(state)->fpscr.bits.fr) << 3))
#define XD2_(state, x) ((state)->floating_point_register.dr[XD2_N(state, x)])
#define FV4_N(state, x) ((x) ^ ((state)->fpscr.bits.fr << 2))
#define FV4_(state, x) ((state)->floating_point_register.dr[FV4_N(state, x)])
#define XMTRX_N(state) (!(state)->fpscr.fr)
#define XMTRX(state) ((state)->floating_point_register.fm[XMTRX_N(state)])
struct architectural_state {
uint32_t general_register[24];
// system_register
uint32_t mach;
uint32_t macl;
uint32_t pr[3];
uint32_t pc[3];
union {
struct fpscr_bits bits;
uint32_t value;
} fpscr;
uint32_t fpul;
//
// control_register
union {
struct sr_bits bits;
uint32_t value;
} sr;
uint32_t ssr;
uint32_t spc;
uint32_t gbr;
uint32_t vbr;
uint32_t sgr;
uint32_t dbr;
//
union floating_point_registers floating_point_register;
bool is_delay_slot;
};
//