ldstop.isa (4587:2c9a2534a489) ldstop.isa (4601:38c989d15fef)
1// Copyright (c) 2007 The Hewlett-Packard Development Company
2// All rights reserved.
3//
4// Redistribution and use of this software in source and binary forms,
5// with or without modification, are permitted provided that the
6// following conditions are met:
7//
8// The software must be used only for Non-Commercial Use which means any
9// use which is NOT directed to receiving any direct monetary
10// compensation for, or commercial advantage from such use. Illustrative
11// examples of non-commercial use are academic research, personal study,
12// teaching, education and corporate research & development.
13// Illustrative examples of commercial use are distributing products for
14// commercial advantage and providing services using the software for
15// commercial advantage.
16//
17// If you wish to use this software or functionality therein that may be
18// covered by patents for commercial use, please contact:
19// Director of Intellectual Property Licensing
20// Office of Strategy and Technology
21// Hewlett-Packard Company
22// 1501 Page Mill Road
23// Palo Alto, California 94304
24//
25// Redistributions of source code must retain the above copyright notice,
26// this list of conditions and the following disclaimer. Redistributions
27// in binary form must reproduce the above copyright notice, this list of
28// conditions and the following disclaimer in the documentation and/or
29// other materials provided with the distribution. Neither the name of
30// the COPYRIGHT HOLDER(s), HEWLETT-PACKARD COMPANY, nor the names of its
31// contributors may be used to endorse or promote products derived from
32// this software without specific prior written permission. No right of
33// sublicense is granted herewith. Derivatives of the software and
34// output created using the software may be prepared, but only for
35// Non-Commercial Uses. Derivatives of the software may be shared with
36// others provided: (i) the others agree to abide by the list of
37// conditions herein which includes the Non-Commercial Use restrictions;
38// and (ii) such Derivatives of the software include the above copyright
39// notice to acknowledge the contribution from this software where
40// applicable, this list of conditions and the disclaimer below.
41//
42// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
43// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
44// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
45// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
46// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
47// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
48// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
49// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
50// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
51// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
52// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
53//
54// Authors: Gabe Black
55
56//////////////////////////////////////////////////////////////////////////
57//
58// LdStOp Microop templates
59//
60//////////////////////////////////////////////////////////////////////////
61
1// Copyright (c) 2007 The Hewlett-Packard Development Company
2// All rights reserved.
3//
4// Redistribution and use of this software in source and binary forms,
5// with or without modification, are permitted provided that the
6// following conditions are met:
7//
8// The software must be used only for Non-Commercial Use which means any
9// use which is NOT directed to receiving any direct monetary
10// compensation for, or commercial advantage from such use. Illustrative
11// examples of non-commercial use are academic research, personal study,
12// teaching, education and corporate research & development.
13// Illustrative examples of commercial use are distributing products for
14// commercial advantage and providing services using the software for
15// commercial advantage.
16//
17// If you wish to use this software or functionality therein that may be
18// covered by patents for commercial use, please contact:
19// Director of Intellectual Property Licensing
20// Office of Strategy and Technology
21// Hewlett-Packard Company
22// 1501 Page Mill Road
23// Palo Alto, California 94304
24//
25// Redistributions of source code must retain the above copyright notice,
26// this list of conditions and the following disclaimer. Redistributions
27// in binary form must reproduce the above copyright notice, this list of
28// conditions and the following disclaimer in the documentation and/or
29// other materials provided with the distribution. Neither the name of
30// the COPYRIGHT HOLDER(s), HEWLETT-PACKARD COMPANY, nor the names of its
31// contributors may be used to endorse or promote products derived from
32// this software without specific prior written permission. No right of
33// sublicense is granted herewith. Derivatives of the software and
34// output created using the software may be prepared, but only for
35// Non-Commercial Uses. Derivatives of the software may be shared with
36// others provided: (i) the others agree to abide by the list of
37// conditions herein which includes the Non-Commercial Use restrictions;
38// and (ii) such Derivatives of the software include the above copyright
39// notice to acknowledge the contribution from this software where
40// applicable, this list of conditions and the disclaimer below.
41//
42// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
43// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
44// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
45// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
46// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
47// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
48// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
49// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
50// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
51// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
52// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
53//
54// Authors: Gabe Black
55
56//////////////////////////////////////////////////////////////////////////
57//
58// LdStOp Microop templates
59//
60//////////////////////////////////////////////////////////////////////////
61
62
63// Load templates
64
65output header {{
66 /**
67 * Base class for load and store ops
68 */
69 class LdStOp : public X86MicroopBase
70 {
71 protected:
72 const uint8_t scale;
73 const RegIndex index;
74 const RegIndex base;
75 const uint64_t disp;
76 const uint8_t segment;
77 const RegIndex data;
78 const uint8_t dataSize;
79 const uint8_t addressSize;
80
81 //Constructor
82 LdStOp(ExtMachInst _machInst,
83 const char * mnem, const char * _instMnem,
84 bool isMicro, bool isDelayed, bool isFirst, bool isLast,
85 uint8_t _scale, RegIndex _index, RegIndex _base,
86 uint64_t _disp, uint8_t _segment,
87 RegIndex _data,
88 uint8_t _dataSize, uint8_t _addressSize,
89 OpClass __opClass) :
90 X86MicroopBase(machInst, mnem, _instMnem,
91 isMicro, isDelayed, isFirst, isLast, __opClass),
92 scale(_scale), index(_index), base(_base),
93 disp(_disp), segment(_segment),
94 data(_data),
95 dataSize(_dataSize), addressSize(_addressSize)
96 {}
97
98 std::string generateDisassembly(Addr pc,
99 const SymbolTable *symtab) const;
100 };
101}};
102
103output decoder {{
104 std::string LdStOp::generateDisassembly(Addr pc,
105 const SymbolTable *symtab) const
106 {
107 std::stringstream response;
108
109 printMnemonic(response, instMnem, mnemonic);
110 printReg(response, data);
111 response << ", ";
112 printSegment(response, segment);
113 ccprintf(response, ":[%d*", scale);
114 printReg(response, index);
115 response << " + ";
116 printReg(response, base);
117 ccprintf(response, " + %#x]", disp);
118 return response.str();
119 }
120}};
121
62output header {{
63 /**
64 * Base class for load and store ops
65 */
66 class LdStOp : public X86MicroopBase
67 {
68 protected:
69 const uint8_t scale;
70 const RegIndex index;
71 const RegIndex base;
72 const uint64_t disp;
73 const uint8_t segment;
74 const RegIndex data;
75 const uint8_t dataSize;
76 const uint8_t addressSize;
77
78 //Constructor
79 LdStOp(ExtMachInst _machInst,
80 const char * mnem, const char * _instMnem,
81 bool isMicro, bool isDelayed, bool isFirst, bool isLast,
82 uint8_t _scale, RegIndex _index, RegIndex _base,
83 uint64_t _disp, uint8_t _segment,
84 RegIndex _data,
85 uint8_t _dataSize, uint8_t _addressSize,
86 OpClass __opClass) :
87 X86MicroopBase(machInst, mnem, _instMnem,
88 isMicro, isDelayed, isFirst, isLast, __opClass),
89 scale(_scale), index(_index), base(_base),
90 disp(_disp), segment(_segment),
91 data(_data),
92 dataSize(_dataSize), addressSize(_addressSize)
93 {}
94
95 std::string generateDisassembly(Addr pc,
96 const SymbolTable *symtab) const;
97 };
98}};
99
100output decoder {{
101 std::string LdStOp::generateDisassembly(Addr pc,
102 const SymbolTable *symtab) const
103 {
104 std::stringstream response;
105
106 printMnemonic(response, instMnem, mnemonic);
107 printReg(response, data);
108 response << ", ";
109 printSegment(response, segment);
110 ccprintf(response, ":[%d*", scale);
111 printReg(response, index);
112 response << " + ";
113 printReg(response, base);
114 ccprintf(response, " + %#x]", disp);
115 return response.str();
116 }
117}};
118
119// LEA template
120
121def template MicroLeaExecute {{
122 Fault %(class_name)s::execute(%(CPU_exec_context)s *xc,
123 Trace::InstRecord *traceData) const
124 {
125 Fault fault = NoFault;
126 Addr EA;
127
128 %(op_decl)s;
129 %(op_rd)s;
130 %(ea_code)s;
131 DPRINTF(X86, "%s : %s: The address is %#x\n", instMnem, mnemonic, EA);
132
133 %(code)s;
134 if(fault == NoFault)
135 {
136 %(op_wb)s;
137 }
138
139 return fault;
140 }
141}};
142
143def template MicroLeaDeclare {{
144 class %(class_name)s : public %(base_class)s
145 {
146 protected:
147 void buildMe();
148
149 public:
150 %(class_name)s(ExtMachInst _machInst,
151 const char * instMnem,
152 bool isMicro, bool isDelayed, bool isFirst, bool isLast,
153 uint8_t _scale, RegIndex _index, RegIndex _base,
154 uint64_t _disp, uint8_t _segment,
155 RegIndex _data,
156 uint8_t _dataSize, uint8_t _addressSize);
157
158 %(class_name)s(ExtMachInst _machInst,
159 const char * instMnem,
160 uint8_t _scale, RegIndex _index, RegIndex _base,
161 uint64_t _disp, uint8_t _segment,
162 RegIndex _data,
163 uint8_t _dataSize, uint8_t _addressSize);
164
165 %(BasicExecDeclare)s
166 };
167}};
168
169// Load templates
170
122def template MicroLoadExecute {{
123 Fault %(class_name)s::execute(%(CPU_exec_context)s *xc,
124 Trace::InstRecord *traceData) const
125 {
126 Fault fault = NoFault;
127 Addr EA;
128
129 %(op_decl)s;
130 %(op_rd)s;
131 %(ea_code)s;
132 DPRINTF(X86, "%s : %s: The address is %#x\n", instMnem, mnemonic, EA);
133
134 fault = xc->read(EA, (%(mem_acc_type)s%(mem_acc_size)s_t&)Mem, 0);
135 if(fault == NoFault)
136 {
137 %(code)s;
138 }
139 if(fault == NoFault)
140 {
141 %(op_wb)s;
142 }
143
144 return fault;
145 }
146}};
147
148def template MicroLoadInitiateAcc {{
149 Fault %(class_name)s::initiateAcc(%(CPU_exec_context)s * xc,
150 Trace::InstRecord * traceData) const
151 {
152 Fault fault = NoFault;
153 Addr EA;
154
155 %(op_decl)s;
156 %(op_rd)s;
157 %(ea_code)s;
158 DPRINTF(X86, "%s : %s: The address is %#x\n", instMnem, mnemonic, EA);
159
160 fault = xc->read(EA, (%(mem_acc_type)s%(mem_acc_size)s_t&)Mem, 0);
161
162 return fault;
163 }
164}};
165
166def template MicroLoadCompleteAcc {{
167 Fault %(class_name)s::completeAcc(PacketPtr pkt,
168 %(CPU_exec_context)s * xc,
169 Trace::InstRecord * traceData) const
170 {
171 Fault fault = NoFault;
172
173 %(op_decl)s;
174 %(op_rd)s;
175
176 Mem = pkt->get<typeof(Mem)>();
177 %(code)s;
178
179 if(fault == NoFault)
180 {
181 %(op_wb)s;
182 }
183
184 return fault;
185 }
186}};
187
188// Store templates
189
190def template MicroStoreExecute {{
191 Fault %(class_name)s::execute(%(CPU_exec_context)s * xc,
192 Trace::InstRecord *traceData) const
193 {
194 Fault fault = NoFault;
195
196 Addr EA;
197 %(op_decl)s;
198 %(op_rd)s;
199 %(ea_code)s;
200 DPRINTF(X86, "%s : %s: The address is %#x\n", instMnem, mnemonic, EA);
201
202 %(code)s;
203
204 if(fault == NoFault)
205 {
206 fault = xc->write((%(mem_acc_type)s%(mem_acc_size)s_t)Mem,
207 EA, 0, 0);
208 }
209 if(fault == NoFault)
210 {
211 %(op_wb)s;
212 }
213
214 return fault;
215 }
216}};
217
218def template MicroStoreInitiateAcc {{
219 Fault %(class_name)s::initiateAcc(%(CPU_exec_context)s * xc,
220 Trace::InstRecord * traceData) const
221 {
222 Fault fault = NoFault;
223
224 Addr EA;
225 %(op_decl)s;
226 %(op_rd)s;
227 %(ea_code)s;
228 DPRINTF(X86, "%s : %s: The address is %#x\n", instMnem, mnemonic, EA);
229
230 %(code)s;
231
232 if(fault == NoFault)
233 {
234 fault = xc->write((%(mem_acc_type)s%(mem_acc_size)s_t)Mem,
235 EA, 0, 0);
236 }
237 if(fault == NoFault)
238 {
239 %(op_wb)s;
240 }
241 return fault;
242 }
243}};
244
245def template MicroStoreCompleteAcc {{
246 Fault %(class_name)s::completeAcc(PacketPtr, %(CPU_exec_context)s * xc,
247 Trace::InstRecord * traceData) const
248 {
249 return NoFault;
250 }
251}};
252
253// Common templates
254
255//This delcares the initiateAcc function in memory operations
256def template InitiateAccDeclare {{
257 Fault initiateAcc(%(CPU_exec_context)s *, Trace::InstRecord *) const;
258}};
259
260//This declares the completeAcc function in memory operations
261def template CompleteAccDeclare {{
262 Fault completeAcc(PacketPtr, %(CPU_exec_context)s *, Trace::InstRecord *) const;
263}};
264
265def template MicroLdStOpDeclare {{
266 class %(class_name)s : public %(base_class)s
267 {
268 protected:
269 void buildMe();
270
271 public:
272 %(class_name)s(ExtMachInst _machInst,
273 const char * instMnem,
274 bool isMicro, bool isDelayed, bool isFirst, bool isLast,
275 uint8_t _scale, RegIndex _index, RegIndex _base,
276 uint64_t _disp, uint8_t _segment,
277 RegIndex _data,
278 uint8_t _dataSize, uint8_t _addressSize);
279
280 %(class_name)s(ExtMachInst _machInst,
281 const char * instMnem,
282 uint8_t _scale, RegIndex _index, RegIndex _base,
283 uint64_t _disp, uint8_t _segment,
284 RegIndex _data,
285 uint8_t _dataSize, uint8_t _addressSize);
286
287 %(BasicExecDeclare)s
288
289 %(InitiateAccDeclare)s
290
291 %(CompleteAccDeclare)s
292 };
293}};
294
295def template MicroLdStOpConstructor {{
296
297 inline void %(class_name)s::buildMe()
298 {
299 %(constructor)s;
300 }
301
302 inline %(class_name)s::%(class_name)s(
303 ExtMachInst machInst, const char * instMnem,
304 uint8_t _scale, RegIndex _index, RegIndex _base,
305 uint64_t _disp, uint8_t _segment,
306 RegIndex _data,
307 uint8_t _dataSize, uint8_t _addressSize) :
308 %(base_class)s(machInst, "%(mnemonic)s", instMnem,
309 false, false, false, false,
310 _scale, _index, _base,
311 _disp, _segment, _data,
312 _dataSize, _addressSize, %(op_class)s)
313 {
314 buildMe();
315 }
316
317 inline %(class_name)s::%(class_name)s(
318 ExtMachInst machInst, const char * instMnem,
319 bool isMicro, bool isDelayed, bool isFirst, bool isLast,
320 uint8_t _scale, RegIndex _index, RegIndex _base,
321 uint64_t _disp, uint8_t _segment,
322 RegIndex _data,
323 uint8_t _dataSize, uint8_t _addressSize) :
324 %(base_class)s(machInst, "%(mnemonic)s", instMnem,
325 isMicro, isDelayed, isFirst, isLast,
326 _scale, _index, _base,
327 _disp, _segment, _data,
328 _dataSize, _addressSize, %(op_class)s)
329 {
330 buildMe();
331 }
332}};
333
334let {{
335 class LdStOp(X86Microop):
336 def __init__(self, data, segment, addr, disp):
337 self.data = data
338 [self.scale, self.index, self.base] = addr
339 self.disp = disp
340 self.segment = segment
341 self.dataSize = "env.dataSize"
342 self.addressSize = "env.addressSize"
343
344 def getAllocator(self, *microFlags):
345 allocator = '''new %(class_name)s(machInst, mnemonic
346 %(flags)s, %(scale)s, %(index)s, %(base)s,
347 %(disp)s, %(segment)s, %(data)s,
348 %(dataSize)s, %(addressSize)s)''' % {
349 "class_name" : self.className,
350 "flags" : self.microFlagsText(microFlags),
351 "scale" : self.scale, "index" : self.index,
352 "base" : self.base,
353 "disp" : self.disp,
354 "segment" : self.segment, "data" : self.data,
355 "dataSize" : self.dataSize, "addressSize" : self.addressSize}
356 return allocator
357}};
358
359let {{
360
361 # Make these empty strings so that concatenating onto
362 # them will always work.
363 header_output = ""
364 decoder_output = ""
365 exec_output = ""
366
367 calculateEA = "EA = scale * Index + Base + disp;"
368
369 def defineMicroLoadOp(mnemonic, code):
370 global header_output
371 global decoder_output
372 global exec_output
373 global microopClasses
374 Name = mnemonic
375 name = mnemonic.lower()
376
377 # Build up the all register version of this micro op
378 iop = InstObjParams(name, Name, 'LdStOp',
379 {"code": code, "ea_code": calculateEA})
380 header_output += MicroLdStOpDeclare.subst(iop)
381 decoder_output += MicroLdStOpConstructor.subst(iop)
382 exec_output += MicroLoadExecute.subst(iop)
383 exec_output += MicroLoadInitiateAcc.subst(iop)
384 exec_output += MicroLoadCompleteAcc.subst(iop)
385
386 class LoadOp(LdStOp):
387 def __init__(self, data, segment, addr, disp = 0):
388 super(LoadOp, self).__init__(data, segment, addr, disp)
389 self.className = Name
390 self.mnemonic = name
391
392 microopClasses[name] = LoadOp
393
394 defineMicroLoadOp('Ld', 'Data = merge(Data, Mem, dataSize);')
395
396 def defineMicroStoreOp(mnemonic, code):
397 global header_output
398 global decoder_output
399 global exec_output
400 global microopClasses
401 Name = mnemonic
402 name = mnemonic.lower()
403
404 # Build up the all register version of this micro op
405 iop = InstObjParams(name, Name, 'LdStOp',
406 {"code": code, "ea_code": calculateEA})
407 header_output += MicroLdStOpDeclare.subst(iop)
408 decoder_output += MicroLdStOpConstructor.subst(iop)
409 exec_output += MicroStoreExecute.subst(iop)
410 exec_output += MicroStoreInitiateAcc.subst(iop)
411 exec_output += MicroStoreCompleteAcc.subst(iop)
412
413 class StoreOp(LdStOp):
171def template MicroLoadExecute {{
172 Fault %(class_name)s::execute(%(CPU_exec_context)s *xc,
173 Trace::InstRecord *traceData) const
174 {
175 Fault fault = NoFault;
176 Addr EA;
177
178 %(op_decl)s;
179 %(op_rd)s;
180 %(ea_code)s;
181 DPRINTF(X86, "%s : %s: The address is %#x\n", instMnem, mnemonic, EA);
182
183 fault = xc->read(EA, (%(mem_acc_type)s%(mem_acc_size)s_t&)Mem, 0);
184 if(fault == NoFault)
185 {
186 %(code)s;
187 }
188 if(fault == NoFault)
189 {
190 %(op_wb)s;
191 }
192
193 return fault;
194 }
195}};
196
197def template MicroLoadInitiateAcc {{
198 Fault %(class_name)s::initiateAcc(%(CPU_exec_context)s * xc,
199 Trace::InstRecord * traceData) const
200 {
201 Fault fault = NoFault;
202 Addr EA;
203
204 %(op_decl)s;
205 %(op_rd)s;
206 %(ea_code)s;
207 DPRINTF(X86, "%s : %s: The address is %#x\n", instMnem, mnemonic, EA);
208
209 fault = xc->read(EA, (%(mem_acc_type)s%(mem_acc_size)s_t&)Mem, 0);
210
211 return fault;
212 }
213}};
214
215def template MicroLoadCompleteAcc {{
216 Fault %(class_name)s::completeAcc(PacketPtr pkt,
217 %(CPU_exec_context)s * xc,
218 Trace::InstRecord * traceData) const
219 {
220 Fault fault = NoFault;
221
222 %(op_decl)s;
223 %(op_rd)s;
224
225 Mem = pkt->get<typeof(Mem)>();
226 %(code)s;
227
228 if(fault == NoFault)
229 {
230 %(op_wb)s;
231 }
232
233 return fault;
234 }
235}};
236
237// Store templates
238
239def template MicroStoreExecute {{
240 Fault %(class_name)s::execute(%(CPU_exec_context)s * xc,
241 Trace::InstRecord *traceData) const
242 {
243 Fault fault = NoFault;
244
245 Addr EA;
246 %(op_decl)s;
247 %(op_rd)s;
248 %(ea_code)s;
249 DPRINTF(X86, "%s : %s: The address is %#x\n", instMnem, mnemonic, EA);
250
251 %(code)s;
252
253 if(fault == NoFault)
254 {
255 fault = xc->write((%(mem_acc_type)s%(mem_acc_size)s_t)Mem,
256 EA, 0, 0);
257 }
258 if(fault == NoFault)
259 {
260 %(op_wb)s;
261 }
262
263 return fault;
264 }
265}};
266
267def template MicroStoreInitiateAcc {{
268 Fault %(class_name)s::initiateAcc(%(CPU_exec_context)s * xc,
269 Trace::InstRecord * traceData) const
270 {
271 Fault fault = NoFault;
272
273 Addr EA;
274 %(op_decl)s;
275 %(op_rd)s;
276 %(ea_code)s;
277 DPRINTF(X86, "%s : %s: The address is %#x\n", instMnem, mnemonic, EA);
278
279 %(code)s;
280
281 if(fault == NoFault)
282 {
283 fault = xc->write((%(mem_acc_type)s%(mem_acc_size)s_t)Mem,
284 EA, 0, 0);
285 }
286 if(fault == NoFault)
287 {
288 %(op_wb)s;
289 }
290 return fault;
291 }
292}};
293
294def template MicroStoreCompleteAcc {{
295 Fault %(class_name)s::completeAcc(PacketPtr, %(CPU_exec_context)s * xc,
296 Trace::InstRecord * traceData) const
297 {
298 return NoFault;
299 }
300}};
301
302// Common templates
303
304//This delcares the initiateAcc function in memory operations
305def template InitiateAccDeclare {{
306 Fault initiateAcc(%(CPU_exec_context)s *, Trace::InstRecord *) const;
307}};
308
309//This declares the completeAcc function in memory operations
310def template CompleteAccDeclare {{
311 Fault completeAcc(PacketPtr, %(CPU_exec_context)s *, Trace::InstRecord *) const;
312}};
313
314def template MicroLdStOpDeclare {{
315 class %(class_name)s : public %(base_class)s
316 {
317 protected:
318 void buildMe();
319
320 public:
321 %(class_name)s(ExtMachInst _machInst,
322 const char * instMnem,
323 bool isMicro, bool isDelayed, bool isFirst, bool isLast,
324 uint8_t _scale, RegIndex _index, RegIndex _base,
325 uint64_t _disp, uint8_t _segment,
326 RegIndex _data,
327 uint8_t _dataSize, uint8_t _addressSize);
328
329 %(class_name)s(ExtMachInst _machInst,
330 const char * instMnem,
331 uint8_t _scale, RegIndex _index, RegIndex _base,
332 uint64_t _disp, uint8_t _segment,
333 RegIndex _data,
334 uint8_t _dataSize, uint8_t _addressSize);
335
336 %(BasicExecDeclare)s
337
338 %(InitiateAccDeclare)s
339
340 %(CompleteAccDeclare)s
341 };
342}};
343
344def template MicroLdStOpConstructor {{
345
346 inline void %(class_name)s::buildMe()
347 {
348 %(constructor)s;
349 }
350
351 inline %(class_name)s::%(class_name)s(
352 ExtMachInst machInst, const char * instMnem,
353 uint8_t _scale, RegIndex _index, RegIndex _base,
354 uint64_t _disp, uint8_t _segment,
355 RegIndex _data,
356 uint8_t _dataSize, uint8_t _addressSize) :
357 %(base_class)s(machInst, "%(mnemonic)s", instMnem,
358 false, false, false, false,
359 _scale, _index, _base,
360 _disp, _segment, _data,
361 _dataSize, _addressSize, %(op_class)s)
362 {
363 buildMe();
364 }
365
366 inline %(class_name)s::%(class_name)s(
367 ExtMachInst machInst, const char * instMnem,
368 bool isMicro, bool isDelayed, bool isFirst, bool isLast,
369 uint8_t _scale, RegIndex _index, RegIndex _base,
370 uint64_t _disp, uint8_t _segment,
371 RegIndex _data,
372 uint8_t _dataSize, uint8_t _addressSize) :
373 %(base_class)s(machInst, "%(mnemonic)s", instMnem,
374 isMicro, isDelayed, isFirst, isLast,
375 _scale, _index, _base,
376 _disp, _segment, _data,
377 _dataSize, _addressSize, %(op_class)s)
378 {
379 buildMe();
380 }
381}};
382
383let {{
384 class LdStOp(X86Microop):
385 def __init__(self, data, segment, addr, disp):
386 self.data = data
387 [self.scale, self.index, self.base] = addr
388 self.disp = disp
389 self.segment = segment
390 self.dataSize = "env.dataSize"
391 self.addressSize = "env.addressSize"
392
393 def getAllocator(self, *microFlags):
394 allocator = '''new %(class_name)s(machInst, mnemonic
395 %(flags)s, %(scale)s, %(index)s, %(base)s,
396 %(disp)s, %(segment)s, %(data)s,
397 %(dataSize)s, %(addressSize)s)''' % {
398 "class_name" : self.className,
399 "flags" : self.microFlagsText(microFlags),
400 "scale" : self.scale, "index" : self.index,
401 "base" : self.base,
402 "disp" : self.disp,
403 "segment" : self.segment, "data" : self.data,
404 "dataSize" : self.dataSize, "addressSize" : self.addressSize}
405 return allocator
406}};
407
408let {{
409
410 # Make these empty strings so that concatenating onto
411 # them will always work.
412 header_output = ""
413 decoder_output = ""
414 exec_output = ""
415
416 calculateEA = "EA = scale * Index + Base + disp;"
417
418 def defineMicroLoadOp(mnemonic, code):
419 global header_output
420 global decoder_output
421 global exec_output
422 global microopClasses
423 Name = mnemonic
424 name = mnemonic.lower()
425
426 # Build up the all register version of this micro op
427 iop = InstObjParams(name, Name, 'LdStOp',
428 {"code": code, "ea_code": calculateEA})
429 header_output += MicroLdStOpDeclare.subst(iop)
430 decoder_output += MicroLdStOpConstructor.subst(iop)
431 exec_output += MicroLoadExecute.subst(iop)
432 exec_output += MicroLoadInitiateAcc.subst(iop)
433 exec_output += MicroLoadCompleteAcc.subst(iop)
434
435 class LoadOp(LdStOp):
436 def __init__(self, data, segment, addr, disp = 0):
437 super(LoadOp, self).__init__(data, segment, addr, disp)
438 self.className = Name
439 self.mnemonic = name
440
441 microopClasses[name] = LoadOp
442
443 defineMicroLoadOp('Ld', 'Data = merge(Data, Mem, dataSize);')
444
445 def defineMicroStoreOp(mnemonic, code):
446 global header_output
447 global decoder_output
448 global exec_output
449 global microopClasses
450 Name = mnemonic
451 name = mnemonic.lower()
452
453 # Build up the all register version of this micro op
454 iop = InstObjParams(name, Name, 'LdStOp',
455 {"code": code, "ea_code": calculateEA})
456 header_output += MicroLdStOpDeclare.subst(iop)
457 decoder_output += MicroLdStOpConstructor.subst(iop)
458 exec_output += MicroStoreExecute.subst(iop)
459 exec_output += MicroStoreInitiateAcc.subst(iop)
460 exec_output += MicroStoreCompleteAcc.subst(iop)
461
462 class StoreOp(LdStOp):
414 def __init__(self, data, addr, segment):
415 super(LoadOp, self).__init__(data, addr, segment)
463 def __init__(self, data, segment, addr, disp = 0):
464 super(LoadOp, self).__init__(data, segment, addr, disp)
416 self.className = Name
417 self.mnemonic = name
418
419 microopClasses[name] = StoreOp
420
421 defineMicroLoadOp('St', 'Mem = Data;')
465 self.className = Name
466 self.mnemonic = name
467
468 microopClasses[name] = StoreOp
469
470 defineMicroLoadOp('St', 'Mem = Data;')
471
472 iop = InstObjParams("lea", "Lea", 'LdStOp',
473 {"code": "Data = merge(Data, EA, dataSize);", "ea_code": calculateEA})
474 header_output += MicroLeaDeclare.subst(iop)
475 decoder_output += MicroLdStOpConstructor.subst(iop)
476 exec_output += MicroLeaExecute.subst(iop)
477
478 class LeaOp(LdStOp):
479 def __init__(self, data, segment, addr, disp = 0):
480 super(LeaOp, self).__init__(data, segment, addr, disp)
481 self.className = "Lea"
482 self.mnemonic = "lea"
483
484 microopClasses["lea"] = LeaOp
422}};
423
485}};
486