gem5/src/arch/mips/isa/operands.isa
Gabe Black d3ed32b989 MIPS: Create an artificial control register to hold the thread pointer.
In Linux, the set_thread_area system call stores the address of the thread
local storage area into a field of the current thread_info structure. Later,
to access that value, the program uses the rdhwr instruction to read a
"hardware register" with index 29. The 64 bit MIPS manual, volume II, says
that index 29 is reserved for a future ABI extension and should cause a
"Reserved Instruction Exception". In Linux (and potentially other ISAs) that
exception is trapped and emulated to return the value stored by
set_thread_area as if that were actually stored by a physical register.

The tp_value address (as named in the Linux kernel) is ironically stored as a
control register so that it goes with a particular ThreadContext. Syscall
emulation will use that to emulate storing to the OS's thread info structure,
and rdhwr will emulate faulting and returning that value from software by
returning the value itself, as if it was in hardware. In other words, we fake
faking the register in SE mode. In an FS mode implementation it should
work as specified in the manual.
2009-12-31 15:30:50 -05:00

156 lines
6.9 KiB
C++

// -*- mode:c++ -*-
// Copyright (c) 2007 MIPS Technologies, Inc.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met: redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer;
// redistributions in binary form must reproduce the above copyright
// notice, this list of conditions and the following disclaimer in the
// documentation and/or other materials provided with the distribution;
// neither the name of the copyright holders nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
//
// Authors: Korey Sewell
// Jaidev Patwardhan
def operand_types {{
'sb' : ('signed int', 8),
'ub' : ('unsigned int', 8),
'sh' : ('signed int', 16),
'uh' : ('unsigned int', 16),
'sw' : ('signed int', 32),
'uw' : ('unsigned int', 32),
'sd' : ('signed int', 64),
'ud' : ('unsigned int', 64),
'sf' : ('float', 32),
'df' : ('float', 64),
}};
def operands {{
#General Purpose Integer Reg Operands
'Rd': ('IntReg', 'uw', 'RD', 'IsInteger', 1),
'Rs': ('IntReg', 'uw', 'RS', 'IsInteger', 2),
'Rt': ('IntReg', 'uw', 'RT', 'IsInteger', 3),
#Immediate Value operand
'IntImm': ('IntReg', 'uw', 'INTIMM', 'IsInteger', 3),
#Operands used for Link or Syscall Insts
'R31': ('IntReg', 'uw','31','IsInteger', 4),
'R2': ('IntReg', 'uw','2', 'IsInteger', 5),
#Special Integer Reg operands
'LO0': ('IntReg', 'uw','INTREG_LO', 'IsInteger', 6),
'HI0': ('IntReg', 'uw','INTREG_HI', 'IsInteger', 7),
#Bitfield-dependent HI/LO Register Access
'LO_RD_SEL': ('IntReg','uw','INTREG_DSP_LO0 + ACDST*3', None, 6),
'HI_RD_SEL': ('IntReg','uw','INTREG_DSP_HI0 + ACDST*3', None, 7),
'LO_RS_SEL': ('IntReg','uw','INTREG_DSP_LO0 + ACSRC*3', None, 6),
'HI_RS_SEL': ('IntReg','uw','INTREG_DSP_HI0 + ACSRC*3', None, 7),
#DSP Special Purpose Integer Operands
'DSPControl': ('IntReg', 'uw', 'INTREG_DSP_CONTROL', None, 8),
'DSPLo0': ('IntReg', 'uw', 'INTREG_LO', None, 1),
'DSPHi0': ('IntReg', 'uw', 'INTREG_HI', None, 1),
'DSPACX0': ('IntReg', 'uw', 'INTREG_DSP_ACX0', None, 1),
'DSPLo1': ('IntReg', 'uw', 'INTREG_DSP_LO1', None, 1),
'DSPHi1': ('IntReg', 'uw', 'INTREG_DSP_HI1', None, 1),
'DSPACX1': ('IntReg', 'uw', 'INTREG_DSP_ACX1', None, 1),
'DSPLo2': ('IntReg', 'uw', 'INTREG_DSP_LO2', None, 1),
'DSPHi2': ('IntReg', 'uw', 'INTREG_DSP_HI2', None, 1),
'DSPACX2': ('IntReg', 'uw', 'INTREG_DSP_ACX2', None, 1),
'DSPLo3': ('IntReg', 'uw', 'INTREG_DSP_LO3', None, 1),
'DSPHi3': ('IntReg', 'uw', 'INTREG_DSP_HI3', None, 1),
'DSPACX3': ('IntReg', 'uw', 'INTREG_DSP_ACX3', None, 1),
#Floating Point Reg Operands
'Fd': ('FloatReg', 'sf', 'FD', 'IsFloating', 1),
'Fs': ('FloatReg', 'sf', 'FS', 'IsFloating', 2),
'Ft': ('FloatReg', 'sf', 'FT', 'IsFloating', 3),
'Fr': ('FloatReg', 'sf', 'FR', 'IsFloating', 3),
#Special Purpose Floating Point Control Reg Operands
'FIR': ('FloatReg', 'uw', 'FLOATREG_FIR', 'IsFloating', 1),
'FCCR': ('FloatReg', 'uw', 'FLOATREG_FCCR', 'IsFloating', 2),
'FEXR': ('FloatReg', 'uw', 'FLOATREG_FEXR', 'IsFloating', 3),
'FENR': ('FloatReg', 'uw', 'FLOATREG_FENR', 'IsFloating', 3),
'FCSR': ('FloatReg', 'uw', 'FLOATREG_FCSR', 'IsFloating', 3),
#Operands For Paired Singles FP Operations
'Fd1': ('FloatReg', 'sf', 'FD', 'IsFloating', 4),
'Fd2': ('FloatReg', 'sf', 'FD+1', 'IsFloating', 4),
'Fs1': ('FloatReg', 'sf', 'FS', 'IsFloating', 5),
'Fs2': ('FloatReg', 'sf', 'FS+1', 'IsFloating', 5),
'Ft1': ('FloatReg', 'sf', 'FT', 'IsFloating', 6),
'Ft2': ('FloatReg', 'sf', 'FT+1', 'IsFloating', 6),
'Fr1': ('FloatReg', 'sf', 'FR', 'IsFloating', 7),
'Fr2': ('FloatReg', 'sf', 'FR+1', 'IsFloating', 7),
#Status Control Reg
'Status': ('ControlReg', 'uw', 'MISCREG_STATUS', None, 1),
#LL Flag
'LLFlag': ('ControlReg', 'uw', 'MISCREG_LLFLAG', None, 1),
#Thread pointer value for SE mode
'TpValue': ('ControlReg', 'ud', 'MISCREG_TP_VALUE', None, 1),
# Index Register
'Index': ('ControlReg','uw','MISCREG_INDEX',None,1),
'CP0_RD_SEL': ('ControlReg', 'uw', '(RD << 3 | SEL)', None, 1),
#MT Control Regs
'MVPConf0': ('ControlReg', 'uw', 'MISCREG_MVP_CONF0', None, 1),
'MVPControl': ('ControlReg', 'uw', 'MISCREG_MVP_CONTROL', None, 1),
'TCBind': ('ControlReg', 'uw', 'MISCREG_TC_BIND', None, 1),
'TCStatus': ('ControlReg', 'uw', 'MISCREG_TC_STATUS', None, 1),
'TCRestart': ('ControlReg', 'uw', 'MISCREG_TC_RESTART', None, 1),
'VPEConf0': ('ControlReg', 'uw', 'MISCREG_VPE_CONF0', None, 1),
'VPEControl': ('ControlReg', 'uw', 'MISCREG_VPE_CONTROL', None, 1),
'YQMask': ('ControlReg', 'uw', 'MISCREG_YQMASK', None, 1),
#CP0 Control Regs
'EntryHi': ('ControlReg','uw', 'MISCREG_ENTRYHI',None,1),
'EntryLo0': ('ControlReg','uw', 'MISCREG_ENTRYLO0',None,1),
'EntryLo1': ('ControlReg','uw', 'MISCREG_ENTRYLO1',None,1),
'PageMask': ('ControlReg','uw', 'MISCREG_PAGEMASK',None,1),
'Random': ('ControlReg','uw', 'MISCREG_CP0_RANDOM',None,1),
'ErrorEPC': ('ControlReg','uw', 'MISCREG_ERROR_EPC',None,1),
'EPC': ('ControlReg','uw', 'MISCREG_EPC',None,1),
'DEPC': ('ControlReg','uw', 'MISCREG_DEPC',None,1),
'IntCtl': ('ControlReg','uw', 'MISCREG_INTCTL',None,1),
'SRSCtl': ('ControlReg','uw', 'MISCREG_SRSCTL',None,1),
'Config': ('ControlReg','uw', 'MISCREG_CONFIG',None,1),
'Config3': ('ControlReg','uw', 'MISCREG_CONFIG3',None,1),
'Config1': ('ControlReg','uw', 'MISCREG_CONFIG1',None,1),
'Config2': ('ControlReg','uw', 'MISCREG_CONFIG2',None,1),
'PageGrain': ('ControlReg','uw', 'MISCREG_PAGEGRAIN',None,1),
'Debug': ('ControlReg','uw', 'MISCREG_DEBUG',None,1),
'Cause': ('ControlReg','uw', 'MISCREG_CAUSE',None,1),
#Memory Operand
'Mem': ('Mem', 'uw', None, ('IsMemRef', 'IsLoad', 'IsStore'), 4),
#Program Counter Operands
'NPC': ('NPC', 'uw', None, 'IsControl', 4),
'NNPC':('NNPC', 'uw', None, 'IsControl', 4)
}};