romutil.py (5853:606b9525071d) | romutil.py (5856:f770af5600c9) |
---|---|
1# Copyright (c) 2008 The Regents of The University of Michigan 2# All rights reserved. 3# 4# Redistribution and use in source and binary forms, with or without 5# modification, are permitted provided that the following conditions are 6# met: redistributions of source code must retain the above copyright 7# notice, this list of conditions and the following disclaimer; 8# redistributions in binary form must reproduce the above copyright --- 12 unchanged lines hidden (view full) --- 21# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 22# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 23# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 24# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 25# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26# 27# Authors: Gabe Black 28 | 1# Copyright (c) 2008 The Regents of The University of Michigan 2# All rights reserved. 3# 4# Redistribution and use in source and binary forms, with or without 5# modification, are permitted provided that the following conditions are 6# met: redistributions of source code must retain the above copyright 7# notice, this list of conditions and the following disclaimer; 8# redistributions in binary form must reproduce the above copyright --- 12 unchanged lines hidden (view full) --- 21# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 22# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 23# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 24# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 25# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26# 27# Authors: Gabe Black 28 |
29microcode = ''' | 29intCodeTemplate = ''' |
30def rom 31{ 32 # This vectors the CPU into an interrupt handler in long mode. 33 # On entry, t1 is set to the vector of the interrupt and t7 is the current 34 # ip. We need that because rdip returns the next ip. | 30def rom 31{ 32 # This vectors the CPU into an interrupt handler in long mode. 33 # On entry, t1 is set to the vector of the interrupt and t7 is the current 34 # ip. We need that because rdip returns the next ip. |
35 extern longModeInterrupt: | 35 extern %(startLabel)s: |
36 37 # 38 # Get the 64 bit interrupt or trap gate descriptor from the IDT 39 # 40 41 # Load the gate descriptor from the IDT 42 slli t4, t1, 4, dataSize=8 43 ld t2, idtr, [1, t0, t4], 8, dataSize=8, addressSize=8 44 ld t4, idtr, [1, t0, t4], dataSize=8, addressSize=8 45 46 # Make sure the descriptor is a legal gate. | 36 37 # 38 # Get the 64 bit interrupt or trap gate descriptor from the IDT 39 # 40 41 # Load the gate descriptor from the IDT 42 slli t4, t1, 4, dataSize=8 43 ld t2, idtr, [1, t0, t4], 8, dataSize=8, addressSize=8 44 ld t4, idtr, [1, t0, t4], dataSize=8, addressSize=8 45 46 # Make sure the descriptor is a legal gate. |
47 chks t1, t4, IntGateCheck | 47 chks t1, t4, %(gateCheckType)s |
48 49 # 50 # Get the target CS descriptor using the selector in the gate 51 # descriptor. 52 # 53 srli t10, t4, 16, dataSize=8 54 andi t5, t10, 0xF8, dataSize=8 55 andi t0, t10, 0x4, flags=(EZF,), dataSize=2 | 48 49 # 50 # Get the target CS descriptor using the selector in the gate 51 # descriptor. 52 # 53 srli t10, t4, 16, dataSize=8 54 andi t5, t10, 0xF8, dataSize=8 55 andi t0, t10, 0x4, flags=(EZF,), dataSize=2 |
56 br rom_local_label("globalDescriptor"), flags=(CEZF,) | 56 br rom_local_label("%(startLabel)s_globalDescriptor"), flags=(CEZF,) |
57 ld t3, tsl, [1, t0, t5], dataSize=8, addressSize=8 | 57 ld t3, tsl, [1, t0, t5], dataSize=8, addressSize=8 |
58 br rom_local_label("processDescriptor") 59globalDescriptor: | 58 br rom_local_label("%(startLabel)s_processDescriptor") 59%(startLabel)s_globalDescriptor: |
60 ld t3, tsg, [1, t0, t5], dataSize=8, addressSize=8 | 60 ld t3, tsg, [1, t0, t5], dataSize=8, addressSize=8 |
61processDescriptor: | 61%(startLabel)s_processDescriptor: |
62 chks t10, t3, IntCSCheck, dataSize=8 63 wrdl hs, t3, t10, dataSize=8 64 65 # Stick the target offset in t9. 66 wrdh t9, t4, t2, dataSize=8 67 68 69 # --- 15 unchanged lines hidden (view full) --- 85 # We're going to change priviledge, so zero out the stack selector. We 86 # need to let the IST have priority so we don't branch yet. 87 wrsel t11, t0, flags=(nCEZF,) 88 89 # Check the IST field of the gate descriptor 90 srli t10, t4, 32, dataSize=8 91 andi t10, t10, 0x7, dataSize=8 92 subi t0, t10, 1, flags=(ECF,), dataSize=8 | 62 chks t10, t3, IntCSCheck, dataSize=8 63 wrdl hs, t3, t10, dataSize=8 64 65 # Stick the target offset in t9. 66 wrdh t9, t4, t2, dataSize=8 67 68 69 # --- 15 unchanged lines hidden (view full) --- 85 # We're going to change priviledge, so zero out the stack selector. We 86 # need to let the IST have priority so we don't branch yet. 87 wrsel t11, t0, flags=(nCEZF,) 88 89 # Check the IST field of the gate descriptor 90 srli t10, t4, 32, dataSize=8 91 andi t10, t10, 0x7, dataSize=8 92 subi t0, t10, 1, flags=(ECF,), dataSize=8 |
93 br rom_local_label("istStackSwitch"), flags=(nCECF,) 94 br rom_local_label("cplStackSwitch"), flags=(nCEZF,) | 93 br rom_local_label("%(startLabel)s_istStackSwitch"), flags=(nCECF,) 94 br rom_local_label("%(startLabel)s_cplStackSwitch"), flags=(nCEZF,) |
95 96 # If we're here, it's because the stack isn't being switched. | 95 96 # If we're here, it's because the stack isn't being switched. |
97 # Set t6 to the new rsp. 98 subi t6, rsp, 40, dataSize=8 99 100 # Align the stack | 97 # Set t6 to the new aligned rsp. 98 mov t6, rsp, dataSize=8 |
101 andi t6, t6, 0xF0, dataSize=1 | 99 andi t6, t6, 0xF0, dataSize=1 |
100 subi t6, t6, 40 + %(errorCodeSize)d, dataSize=8 |
|
102 103 # Check that we can access everything we need to on the stack 104 ldst t0, hs, [1, t0, t6], dataSize=8, addressSize=8 | 101 102 # Check that we can access everything we need to on the stack 103 ldst t0, hs, [1, t0, t6], dataSize=8, addressSize=8 |
105 ldst t0, hs, [1, t0, t6], 32, dataSize=8, addressSize=8 106 br rom_local_label("stackSwitched") | 104 ldst t0, hs, [1, t0, t6], \ 105 32 + %(errorCodeSize)d, dataSize=8, addressSize=8 106 br rom_local_label("%(startLabel)s_stackSwitched") |
107 | 107 |
108istStackSwitch: | 108%(startLabel)s_istStackSwitch: |
109 panic "IST based stack switching isn't implemented" | 109 panic "IST based stack switching isn't implemented" |
110 br rom_local_label("stackSwitched") | 110 br rom_local_label("%(startLabel)s_stackSwitched") |
111 | 111 |
112cplStackSwitch: | 112%(startLabel)s_cplStackSwitch: |
113 panic "CPL change initiated stack switching isn't implemented" 114 | 113 panic "CPL change initiated stack switching isn't implemented" 114 |
115stackSwitched: | 115%(startLabel)s_stackSwitched: |
116 117 118 ## 119 ## Point of no return. 120 ## We're now going to irrevocably modify visible state. 121 ## Anything bad that's going to happen should have happened by now or will 122 ## happen right now. 123 ## 124 wrip t0, t9, dataSize=8 125 126 127 # 128 # Build up the interrupt stack frame 129 # 130 131 132 # Write out the contents of memory | 116 117 118 ## 119 ## Point of no return. 120 ## We're now going to irrevocably modify visible state. 121 ## Anything bad that's going to happen should have happened by now or will 122 ## happen right now. 123 ## 124 wrip t0, t9, dataSize=8 125 126 127 # 128 # Build up the interrupt stack frame 129 # 130 131 132 # Write out the contents of memory |
133 st t7, hs, [1, t0, t6], dataSize=8 | 133 %(errorCodeCode)s 134 st t7, hs, [1, t0, t6], %(errorCodeSize)d, dataSize=8, addressSize=8 |
134 limm t5, 0, dataSize=8 135 rdsel t5, cs, dataSize=2 | 135 limm t5, 0, dataSize=8 136 rdsel t5, cs, dataSize=2 |
136 st t5, hs, [1, t0, t6], 8, dataSize=8 | 137 st t5, hs, [1, t0, t6], 8 + %(errorCodeSize)d, dataSize=8, addressSize=8 |
137 rflags t10, dataSize=8 | 138 rflags t10, dataSize=8 |
138 st t10, hs, [1, t0, t6], 16, dataSize=8 139 st rsp, hs, [1, t0, t6], 24, dataSize=8 | 139 st t10, hs, [1, t0, t6], 16 + %(errorCodeSize)d, dataSize=8, addressSize=8 140 st rsp, hs, [1, t0, t6], 24 + %(errorCodeSize)d, dataSize=8, addressSize=8 |
140 rdsel t5, ss, dataSize=2 | 141 rdsel t5, ss, dataSize=2 |
141 st t5, hs, [1, t0, t6], 32, dataSize=8 | 142 st t5, hs, [1, t0, t6], 32 + %(errorCodeSize)d, dataSize=8, addressSize=8 |
142 143 # Set the stack segment 144 mov rsp, rsp, t6, dataSize=8 145 wrsel ss, t11, dataSize=2 146 147 # 148 # Set up the target code segment 149 # --- 19 unchanged lines hidden (view full) --- 169 slli t5, t5, 9, dataSize=8 170 or t6, t5, t6, dataSize=8 171 172 # Put the results into rflags 173 wrflags t6, t10 174 175 eret 176}; | 143 144 # Set the stack segment 145 mov rsp, rsp, t6, dataSize=8 146 wrsel ss, t11, dataSize=2 147 148 # 149 # Set up the target code segment 150 # --- 19 unchanged lines hidden (view full) --- 170 slli t5, t5, 9, dataSize=8 171 or t6, t5, t6, dataSize=8 172 173 # Put the results into rflags 174 wrflags t6, t10 175 176 eret 177}; |
178''' |
|
177 | 179 |
180microcode = \ 181intCodeTemplate % {\ 182 "startLabel" : "longModeInterrupt", 183 "gateCheckType" : "IntGateCheck", 184 "errorCodeSize" : 0, 185 "errorCodeCode" : "" 186} + \ 187intCodeTemplate % {\ 188 "startLabel" : "longModeSoftInterrupt", 189 "gateCheckType" : "SoftIntGateCheck", 190 "errorCodeSize" : 0, 191 "errorCodeCode" : "" 192} + \ 193intCodeTemplate % {\ 194 "startLabel" : "longModeInterruptWithError", 195 "gateCheckType" : "IntGateCheck", 196 "errorCodeSize" : 8, 197 "errorCodeCode" : ''' 198 st t15, hs, [1, t0, t6], dataSize=8, addressSize=8 199 ''' 200} + \ 201''' |
|
178def rom 179{ 180 # This vectors the CPU into an interrupt handler in legacy mode. 181 extern legacyModeInterrupt: 182 panic "Legacy mode interrupts not implemented (in microcode)" 183 eret 184}; 185''' | 202def rom 203{ 204 # This vectors the CPU into an interrupt handler in legacy mode. 205 extern legacyModeInterrupt: 206 panic "Legacy mode interrupts not implemented (in microcode)" 207 eret 208}; 209''' |