mem.isa revision 7291
19793Sakash.bagdia@arm.com// -*- mode:c++ -*-
27586SAli.Saidi@arm.com
37586SAli.Saidi@arm.com// Copyright (c) 2010 ARM Limited
47586SAli.Saidi@arm.com// All rights reserved
57586SAli.Saidi@arm.com//
67586SAli.Saidi@arm.com// The license below extends only to copyright in the software and shall
77586SAli.Saidi@arm.com// not be construed as granting a license to any other intellectual
87586SAli.Saidi@arm.com// property including but not limited to intellectual property relating
97586SAli.Saidi@arm.com// to a hardware implementation of the functionality of the software
107586SAli.Saidi@arm.com// licensed hereunder.  You may use the software subject to the license
117586SAli.Saidi@arm.com// terms below provided that you ensure that this notice is replicated
127586SAli.Saidi@arm.com// unmodified and in its entirety in all distributions of the software,
133970Sgblack@eecs.umich.edu// modified or unmodified, in source code or in binary form.
143005Sstever@eecs.umich.edu//
153005Sstever@eecs.umich.edu// Copyright (c) 2007-2008 The Florida State University
163005Sstever@eecs.umich.edu// All rights reserved.
173005Sstever@eecs.umich.edu//
183005Sstever@eecs.umich.edu// Redistribution and use in source and binary forms, with or without
193005Sstever@eecs.umich.edu// modification, are permitted provided that the following conditions are
203005Sstever@eecs.umich.edu// met: redistributions of source code must retain the above copyright
213005Sstever@eecs.umich.edu// notice, this list of conditions and the following disclaimer;
223005Sstever@eecs.umich.edu// redistributions in binary form must reproduce the above copyright
233005Sstever@eecs.umich.edu// notice, this list of conditions and the following disclaimer in the
243005Sstever@eecs.umich.edu// documentation and/or other materials provided with the distribution;
253005Sstever@eecs.umich.edu// neither the name of the copyright holders nor the names of its
263005Sstever@eecs.umich.edu// contributors may be used to endorse or promote products derived from
273005Sstever@eecs.umich.edu// this software without specific prior written permission.
283005Sstever@eecs.umich.edu//
293005Sstever@eecs.umich.edu// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
303005Sstever@eecs.umich.edu// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
313005Sstever@eecs.umich.edu// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
323005Sstever@eecs.umich.edu// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
333005Sstever@eecs.umich.edu// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
343005Sstever@eecs.umich.edu// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
353005Sstever@eecs.umich.edu// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
363005Sstever@eecs.umich.edu// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
373005Sstever@eecs.umich.edu// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
383005Sstever@eecs.umich.edu// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
393005Sstever@eecs.umich.edu// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
403005Sstever@eecs.umich.edu//
416654Snate@binkert.org// Authors: Stephen Hines
426654Snate@binkert.org
432889SN/A
442710SN/Adef template SwapExecute {{
456654Snate@binkert.org    Fault %(class_name)s::execute(%(CPU_exec_context)s *xc,
466654Snate@binkert.org                                  Trace::InstRecord *traceData) const
476654Snate@binkert.org    {
485457Ssaidi@eecs.umich.edu        Addr EA;
496654Snate@binkert.org        Fault fault = NoFault;
506654Snate@binkert.org
512934SN/A        %(op_decl)s;
522549SN/A        uint64_t memData = 0;
532995SN/A        %(op_rd)s;
543395Shsul@eecs.umich.edu        %(ea_code)s;
556981SLisa.Hsu@amd.com
563448Shsul@eecs.umich.edu        if (%(predicate_test)s)
578920Snilay@cs.wisc.edu        {
583444Sktlim@umich.edu            %(preacc_code)s;
592889SN/A
608920Snilay@cs.wisc.edu            if (fault == NoFault) {
618920Snilay@cs.wisc.edu                fault = xc->write((uint%(mem_acc_size)d_t&)Mem,
623322Shsul@eecs.umich.edu                        EA, memAccessFlags, &memData);
632710SN/A            }
642710SN/A
652710SN/A            if (fault == NoFault) {
662710SN/A                %(postacc_code)s;
672710SN/A            }
682710SN/A
693322Shsul@eecs.umich.edu            if (fault == NoFault) {
703304Sstever@eecs.umich.edu                %(op_wb)s;
713322Shsul@eecs.umich.edu            }
723322Shsul@eecs.umich.edu        }
733304Sstever@eecs.umich.edu
749653SAndreas.Sandberg@ARM.com        return fault;
759653SAndreas.Sandberg@ARM.com    }
769653SAndreas.Sandberg@ARM.com}};
779653SAndreas.Sandberg@ARM.com
789653SAndreas.Sandberg@ARM.comdef template SwapInitiateAcc {{
799653SAndreas.Sandberg@ARM.com    Fault %(class_name)s::initiateAcc(%(CPU_exec_context)s *xc,
809653SAndreas.Sandberg@ARM.com                                      Trace::InstRecord *traceData) const
813481Shsul@eecs.umich.edu    {
823481Shsul@eecs.umich.edu        Addr EA;
832566SN/A        Fault fault = NoFault;
849665Sandreas.hansson@arm.com
859665Sandreas.hansson@arm.com        %(op_decl)s;
869665Sandreas.hansson@arm.com        uint64_t memData = 0;
879665Sandreas.hansson@arm.com        %(op_rd)s;
889665Sandreas.hansson@arm.com        %(ea_code)s;
892995SN/A
903304Sstever@eecs.umich.edu        if (%(predicate_test)s)
913304Sstever@eecs.umich.edu        {
923304Sstever@eecs.umich.edu            %(preacc_code)s;
932995SN/A
942995SN/A            if (fault == NoFault) {
952995SN/A                fault = xc->write((uint%(mem_acc_size)d_t&)Mem, EA,
962917SN/A                                  memAccessFlags, &memData);
972995SN/A            }
988956Sjayneel@cs.wisc.edu
992995SN/A            if (fault == NoFault) {
1008956Sjayneel@cs.wisc.edu                %(op_wb)s;
1013304Sstever@eecs.umich.edu            }
1026135Sgblack@eecs.umich.edu        }
1036135Sgblack@eecs.umich.edu
1046654Snate@binkert.org        return fault;
1059826Sandreas.hansson@arm.com    }
1066654Snate@binkert.org}};
1079826Sandreas.hansson@arm.com
1086654Snate@binkert.orgdef template SwapCompleteAcc {{
1099826Sandreas.hansson@arm.com    Fault %(class_name)s::completeAcc(PacketPtr pkt,
1106654Snate@binkert.org                                      %(CPU_exec_context)s *xc,
1119826Sandreas.hansson@arm.com                                      Trace::InstRecord *traceData) const
1127586SAli.Saidi@arm.com    {
1139826Sandreas.hansson@arm.com        Fault fault = NoFault;
1149826Sandreas.hansson@arm.com
1159665Sandreas.hansson@arm.com        %(op_decl)s;
1163819Shsul@eecs.umich.edu        %(op_rd)s;
1179059Snilay@cs.wisc.edu
1183819Shsul@eecs.umich.edu        if (%(predicate_test)s)
1199827Sakash.bagdia@arm.com        {
1209827Sakash.bagdia@arm.com            // ARM instructions will not have a pkt if the predicate is false
1219827Sakash.bagdia@arm.com            uint64_t memData = pkt->get<typeof(Mem)>();
1229793Sakash.bagdia@arm.com
1239827Sakash.bagdia@arm.com            %(postacc_code)s;
1249827Sakash.bagdia@arm.com
1259827Sakash.bagdia@arm.com            if (fault == NoFault) {
1269827Sakash.bagdia@arm.com                %(op_wb)s;
1279827Sakash.bagdia@arm.com            }
1289793Sakash.bagdia@arm.com        }
1299793Sakash.bagdia@arm.com
1309827Sakash.bagdia@arm.com        return fault;
1319827Sakash.bagdia@arm.com    }
1329827Sakash.bagdia@arm.com}};
1339790Sakash.bagdia@arm.com
1343873Sbinkertn@umich.edudef template LoadExecute {{
1353873Sbinkertn@umich.edu    Fault %(class_name)s::execute(%(CPU_exec_context)s *xc,
1363873Sbinkertn@umich.edu                                  Trace::InstRecord *traceData) const
1373873Sbinkertn@umich.edu    {
1383873Sbinkertn@umich.edu        Addr EA;
1393873Sbinkertn@umich.edu        Fault fault = NoFault;
1408659SAli.Saidi@ARM.com
1418659SAli.Saidi@ARM.com        %(op_decl)s;
1429793Sakash.bagdia@arm.com        %(op_rd)s;
1439793Sakash.bagdia@arm.com        %(ea_code)s;
1449793Sakash.bagdia@arm.com
1453668Srdreslin@umich.edu        if (%(predicate_test)s)
1469653SAndreas.Sandberg@ARM.com        {
1479653SAndreas.Sandberg@ARM.com            if (fault == NoFault) {
1489653SAndreas.Sandberg@ARM.com                fault = xc->read(EA, (uint%(mem_acc_size)d_t&)Mem, memAccessFlags);
1496636Ssteve.reinhardt@amd.com                %(memacc_code)s;
1509788Sakash.bagdia@arm.com            }
1519788Sakash.bagdia@arm.com
1528839Sandreas.hansson@arm.com            if (fault == NoFault) {
1538839Sandreas.hansson@arm.com                %(op_wb)s;
1548713Sandreas.hansson@arm.com            }
1559408Sandreas.hansson@arm.com        }
1568839Sandreas.hansson@arm.com
1578839Sandreas.hansson@arm.com        return fault;
1585142Ssaidi@eecs.umich.edu    }
1598926Sandreas.hansson@arm.com}};
1609317Sandreas.hansson@arm.com
1619317Sandreas.hansson@arm.comdef template StoreExecute {{
1629317Sandreas.hansson@arm.com    Fault %(class_name)s::execute(%(CPU_exec_context)s *xc,
1639317Sandreas.hansson@arm.com                                  Trace::InstRecord *traceData) const
1649317Sandreas.hansson@arm.com    {
1658926Sandreas.hansson@arm.com        Addr EA;
1663312Sstever@eecs.umich.edu        Fault fault = NoFault;
1674968Sacolyte@umich.edu
1688926Sandreas.hansson@arm.com        %(op_decl)s;
1698887Sgeoffrey.blake@arm.com        %(op_rd)s;
1708887Sgeoffrey.blake@arm.com        %(ea_code)s;
1719384SAndreas.Sandberg@arm.com
1728887Sgeoffrey.blake@arm.com        if (%(predicate_test)s)
1738887Sgeoffrey.blake@arm.com        {
1744968Sacolyte@umich.edu            if (fault == NoFault) {
1759826Sandreas.hansson@arm.com                %(memacc_code)s;
1769826Sandreas.hansson@arm.com            }
1779826Sandreas.hansson@arm.com
1789826Sandreas.hansson@arm.com            if (fault == NoFault) {
1799826Sandreas.hansson@arm.com                fault = xc->write((uint%(mem_acc_size)d_t&)Mem, EA,
1809826Sandreas.hansson@arm.com                                  memAccessFlags, NULL);
1819826Sandreas.hansson@arm.com                if (traceData) { traceData->setData(Mem); }
1823005Sstever@eecs.umich.edu            }
1836654Snate@binkert.org
1849826Sandreas.hansson@arm.com            if (fault == NoFault) {
1856654Snate@binkert.org                %(op_wb)s;
1869826Sandreas.hansson@arm.com            }
1876654Snate@binkert.org        }
1889826Sandreas.hansson@arm.com
1896654Snate@binkert.org        return fault;
1909826Sandreas.hansson@arm.com    }
1917586SAli.Saidi@arm.com}};
1929826Sandreas.hansson@arm.com
1938661SAli.Saidi@ARM.comdef template StoreInitiateAcc {{
1949827Sakash.bagdia@arm.com    Fault %(class_name)s::initiateAcc(%(CPU_exec_context)s *xc,
1959827Sakash.bagdia@arm.com                                      Trace::InstRecord *traceData) const
1969827Sakash.bagdia@arm.com    {
1979793Sakash.bagdia@arm.com        Addr EA;
1989793Sakash.bagdia@arm.com        Fault fault = NoFault;
1999790Sakash.bagdia@arm.com
2009827Sakash.bagdia@arm.com        %(op_decl)s;
2019827Sakash.bagdia@arm.com        %(op_rd)s;
2029827Sakash.bagdia@arm.com        %(ea_code)s;
2039793Sakash.bagdia@arm.com
2049827Sakash.bagdia@arm.com        if (%(predicate_test)s)
2059827Sakash.bagdia@arm.com        {
2069827Sakash.bagdia@arm.com            if (fault == NoFault) {
2079793Sakash.bagdia@arm.com                %(memacc_code)s;
2089793Sakash.bagdia@arm.com            }
2099793Sakash.bagdia@arm.com
2109384SAndreas.Sandberg@arm.com            if (fault == NoFault) {
2118863Snilay@cs.wisc.edu                fault = xc->write((uint%(mem_acc_size)d_t&)Mem, EA,
2127876Sgblack@eecs.umich.edu                                  memAccessFlags, NULL);
2134968Sacolyte@umich.edu                if (traceData) { traceData->setData(Mem); }
2148926Sandreas.hansson@arm.com            }
2154837Ssaidi@eecs.umich.edu
2164837Ssaidi@eecs.umich.edu            // Need to write back any potential address register update
2179408Sandreas.hansson@arm.com            if (fault == NoFault) {
2189653SAndreas.Sandberg@ARM.com                %(op_wb)s;
2199653SAndreas.Sandberg@ARM.com            }
2209653SAndreas.Sandberg@ARM.com        }
2219164Sandreas.hansson@arm.com
2229408Sandreas.hansson@arm.com        return fault;
2238845Sandreas.hansson@arm.com    }
2248845Sandreas.hansson@arm.com}};
2254837Ssaidi@eecs.umich.edu
2269826Sandreas.hansson@arm.comdef template LoadInitiateAcc {{
2279826Sandreas.hansson@arm.com    Fault %(class_name)s::initiateAcc(%(CPU_exec_context)s *xc,
2289826Sandreas.hansson@arm.com                                      Trace::InstRecord *traceData) const
2299826Sandreas.hansson@arm.com    {
2309826Sandreas.hansson@arm.com        Addr EA;
2319826Sandreas.hansson@arm.com        Fault fault = NoFault;
2329826Sandreas.hansson@arm.com
2338659SAli.Saidi@ARM.com        %(op_src_decl)s;
2348801Sgblack@eecs.umich.edu        %(op_rd)s;
2353005Sstever@eecs.umich.edu        %(ea_code)s;
2368801Sgblack@eecs.umich.edu
2373005Sstever@eecs.umich.edu        if (%(predicate_test)s)
2383005Sstever@eecs.umich.edu        {
2393005Sstever@eecs.umich.edu            if (fault == NoFault) {
2402566SN/A                fault = xc->read(EA, (uint%(mem_acc_size)d_t &)Mem, memAccessFlags);
2417861Sgblack@eecs.umich.edu            }
2427861Sgblack@eecs.umich.edu        }
2437861Sgblack@eecs.umich.edu
2448635Schris.emmons@arm.com        return fault;
2458635Schris.emmons@arm.com    }
2468635Schris.emmons@arm.com}};
2479061Snilay@cs.wisc.edu
2483481Shsul@eecs.umich.edudef template LoadCompleteAcc {{
249    Fault %(class_name)s::completeAcc(PacketPtr pkt,
250                                      %(CPU_exec_context)s *xc,
251                                      Trace::InstRecord *traceData) const
252    {
253        Fault fault = NoFault;
254
255        %(op_decl)s;
256        %(op_rd)s;
257
258        if (%(predicate_test)s)
259        {
260            // ARM instructions will not have a pkt if the predicate is false
261            Mem = pkt->get<typeof(Mem)>();
262
263            if (fault == NoFault) {
264                %(memacc_code)s;
265            }
266
267            if (fault == NoFault) {
268                %(op_wb)s;
269            }
270        }
271
272        return fault;
273    }
274}};
275
276def template StoreCompleteAcc {{
277    Fault %(class_name)s::completeAcc(PacketPtr pkt,
278                                      %(CPU_exec_context)s *xc,
279                                      Trace::InstRecord *traceData) const
280    {
281        Fault fault = NoFault;
282
283        %(op_decl)s;
284        %(op_rd)s;
285
286        if (%(predicate_test)s)
287        {
288            if (fault == NoFault) {
289                %(op_wb)s;
290            }
291        }
292
293        return fault;
294    }
295}};
296
297def template RfeDeclare {{
298    /**
299     * Static instruction class for "%(mnemonic)s".
300     */
301    class %(class_name)s : public %(base_class)s
302    {
303      public:
304
305        /// Constructor.
306        %(class_name)s(ExtMachInst machInst,
307                uint32_t _base, int _mode, bool _wb);
308
309        %(BasicExecDeclare)s
310
311        %(InitiateAccDeclare)s
312
313        %(CompleteAccDeclare)s
314    };
315}};
316
317def template SwapDeclare {{
318    /**
319     * Static instruction class for "%(mnemonic)s".
320     */
321    class %(class_name)s : public %(base_class)s
322    {
323      public:
324
325        /// Constructor.
326        %(class_name)s(ExtMachInst machInst,
327                uint32_t _dest, uint32_t _op1, uint32_t _base);
328
329        %(BasicExecDeclare)s
330
331        %(InitiateAccDeclare)s
332
333        %(CompleteAccDeclare)s
334    };
335}};
336
337def template LoadStoreDImmDeclare {{
338    /**
339     * Static instruction class for "%(mnemonic)s".
340     */
341    class %(class_name)s : public %(base_class)s
342    {
343      public:
344
345        /// Constructor.
346        %(class_name)s(ExtMachInst machInst,
347                uint32_t _dest, uint32_t _dest2,
348                uint32_t _base, bool _add, int32_t _imm);
349
350        %(BasicExecDeclare)s
351
352        %(InitiateAccDeclare)s
353
354        %(CompleteAccDeclare)s
355    };
356}};
357
358def template LoadStoreImmDeclare {{
359    /**
360     * Static instruction class for "%(mnemonic)s".
361     */
362    class %(class_name)s : public %(base_class)s
363    {
364      public:
365
366        /// Constructor.
367        %(class_name)s(ExtMachInst machInst,
368                uint32_t _dest, uint32_t _base, bool _add, int32_t _imm);
369
370        %(BasicExecDeclare)s
371
372        %(InitiateAccDeclare)s
373
374        %(CompleteAccDeclare)s
375    };
376}};
377
378def template LoadStoreDRegDeclare {{
379    /**
380     * Static instruction class for "%(mnemonic)s".
381     */
382    class %(class_name)s : public %(base_class)s
383    {
384      public:
385
386        /// Constructor.
387        %(class_name)s(ExtMachInst machInst,
388                uint32_t _dest, uint32_t _dest2,
389                uint32_t _base, bool _add,
390                int32_t _shiftAmt, uint32_t _shiftType,
391                uint32_t _index);
392
393        %(BasicExecDeclare)s
394
395        %(InitiateAccDeclare)s
396
397        %(CompleteAccDeclare)s
398    };
399}};
400
401def template LoadStoreRegDeclare {{
402    /**
403     * Static instruction class for "%(mnemonic)s".
404     */
405    class %(class_name)s : public %(base_class)s
406    {
407      public:
408
409        /// Constructor.
410        %(class_name)s(ExtMachInst machInst,
411                uint32_t _dest, uint32_t _base, bool _add,
412                int32_t _shiftAmt, uint32_t _shiftType,
413                uint32_t _index);
414
415        %(BasicExecDeclare)s
416
417        %(InitiateAccDeclare)s
418
419        %(CompleteAccDeclare)s
420    };
421}};
422
423def template InitiateAccDeclare {{
424    Fault initiateAcc(%(CPU_exec_context)s *, Trace::InstRecord *) const;
425}};
426
427def template CompleteAccDeclare {{
428    Fault completeAcc(PacketPtr,  %(CPU_exec_context)s *, Trace::InstRecord *) const;
429}};
430
431def template RfeConstructor {{
432    inline %(class_name)s::%(class_name)s(ExtMachInst machInst,
433            uint32_t _base, int _mode, bool _wb)
434         : %(base_class)s("%(mnemonic)s", machInst, %(op_class)s,
435                 (IntRegIndex)_base, (AddrMode)_mode, _wb)
436    {
437        %(constructor)s;
438    }
439}};
440
441def template SwapConstructor {{
442    inline %(class_name)s::%(class_name)s(ExtMachInst machInst,
443            uint32_t _dest, uint32_t _op1, uint32_t _base)
444         : %(base_class)s("%(mnemonic)s", machInst, %(op_class)s,
445                 (IntRegIndex)_dest, (IntRegIndex)_op1, (IntRegIndex)_base)
446    {
447        %(constructor)s;
448    }
449}};
450
451def template LoadStoreDImmConstructor {{
452    inline %(class_name)s::%(class_name)s(ExtMachInst machInst,
453            uint32_t _dest, uint32_t _dest2,
454            uint32_t _base, bool _add, int32_t _imm)
455         : %(base_class)s("%(mnemonic)s", machInst, %(op_class)s,
456                 (IntRegIndex)_dest, (IntRegIndex)_dest2,
457                 (IntRegIndex)_base, _add, _imm)
458    {
459        %(constructor)s;
460    }
461}};
462
463def template LoadStoreImmConstructor {{
464    inline %(class_name)s::%(class_name)s(ExtMachInst machInst,
465            uint32_t _dest, uint32_t _base, bool _add, int32_t _imm)
466         : %(base_class)s("%(mnemonic)s", machInst, %(op_class)s,
467                 (IntRegIndex)_dest, (IntRegIndex)_base, _add, _imm)
468    {
469        %(constructor)s;
470    }
471}};
472
473def template LoadStoreDRegConstructor {{
474    inline %(class_name)s::%(class_name)s(ExtMachInst machInst,
475            uint32_t _dest, uint32_t _dest2, uint32_t _base, bool _add,
476            int32_t _shiftAmt, uint32_t _shiftType, uint32_t _index)
477         : %(base_class)s("%(mnemonic)s", machInst, %(op_class)s,
478                 (IntRegIndex)_dest, (IntRegIndex)_dest2,
479                 (IntRegIndex)_base, _add,
480                 _shiftAmt, (ArmShiftType)_shiftType,
481                 (IntRegIndex)_index)
482    {
483        %(constructor)s;
484    }
485}};
486
487def template LoadStoreRegConstructor {{
488    inline %(class_name)s::%(class_name)s(ExtMachInst machInst,
489            uint32_t _dest, uint32_t _base, bool _add,
490            int32_t _shiftAmt, uint32_t _shiftType, uint32_t _index)
491         : %(base_class)s("%(mnemonic)s", machInst, %(op_class)s,
492                 (IntRegIndex)_dest, (IntRegIndex)_base, _add,
493                 _shiftAmt, (ArmShiftType)_shiftType,
494                 (IntRegIndex)_index)
495    {
496        %(constructor)s;
497    }
498}};
499