isa.cc revision 9375:ecfd5607d5e9
1/*
2 * Copyright (c) 2009 The Regents of The University of Michigan
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are
7 * met: redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer;
9 * redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution;
12 * neither the name of the copyright holders nor the names of its
13 * contributors may be used to endorse or promote products derived from
14 * this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
18 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
19 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
20 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 *
28 * Authors: Gabe Black
29 */
30
31#include "arch/sparc/asi.hh"
32#include "arch/sparc/isa.hh"
33#include "base/bitfield.hh"
34#include "base/trace.hh"
35#include "cpu/base.hh"
36#include "cpu/thread_context.hh"
37#include "debug/MiscRegs.hh"
38#include "debug/Timer.hh"
39
40namespace SparcISA
41{
42
43static PSTATE
44buildPstateMask()
45{
46    PSTATE mask = 0;
47    mask.ie = 1;
48    mask.priv = 1;
49    mask.am = 1;
50    mask.pef = 1;
51    mask.mm = 3;
52    mask.tle = 1;
53    mask.cle = 1;
54    mask.pid1 = 1;
55    return mask;
56}
57
58static const PSTATE PstateMask = buildPstateMask();
59
60void
61ISA::reloadRegMap()
62{
63    installGlobals(gl, CurrentGlobalsOffset);
64    installWindow(cwp, CurrentWindowOffset);
65    // Microcode registers.
66    for (int i = 0; i < NumMicroIntRegs; i++)
67        intRegMap[MicroIntOffset + i] = i + TotalGlobals + NWindows * 16;
68    installGlobals(gl, NextGlobalsOffset);
69    installWindow(cwp - 1, NextWindowOffset);
70    installGlobals(gl, PreviousGlobalsOffset);
71    installWindow(cwp + 1, PreviousWindowOffset);
72}
73
74void
75ISA::installWindow(int cwp, int offset)
76{
77    assert(offset >= 0 && offset + NumWindowedRegs <= NumIntRegs);
78    RegIndex *mapChunk = intRegMap + offset;
79    for (int i = 0; i < NumWindowedRegs; i++)
80        mapChunk[i] = TotalGlobals +
81            ((i - cwp * RegsPerWindow + TotalWindowed) % (TotalWindowed));
82}
83
84void
85ISA::installGlobals(int gl, int offset)
86{
87    assert(offset >= 0 && offset + NumGlobalRegs <= NumIntRegs);
88    RegIndex *mapChunk = intRegMap + offset;
89    mapChunk[0] = 0;
90    for (int i = 1; i < NumGlobalRegs; i++)
91        mapChunk[i] = i + gl * NumGlobalRegs;
92}
93
94void
95ISA::clear()
96{
97    cwp = 0;
98    gl = 0;
99    reloadRegMap();
100
101    // y = 0;
102    // ccr = 0;
103    asi = 0;
104    tick = ULL(1) << 63;
105    fprs = 0;
106    gsr = 0;
107    softint = 0;
108    tick_cmpr = 0;
109    stick = 0;
110    stick_cmpr = 0;
111    memset(tpc, 0, sizeof(tpc));
112    memset(tnpc, 0, sizeof(tnpc));
113    memset(tstate, 0, sizeof(tstate));
114    memset(tt, 0, sizeof(tt));
115    tba = 0;
116    pstate = 0;
117    tl = 0;
118    pil = 0;
119    // cansave = 0;
120    // canrestore = 0;
121    // cleanwin = 0;
122    // otherwin = 0;
123    // wstate = 0;
124    // In a T1, bit 11 is apparently always 1
125    hpstate = 0;
126    hpstate.id = 1;
127    memset(htstate, 0, sizeof(htstate));
128    hintp = 0;
129    htba = 0;
130    hstick_cmpr = 0;
131    // This is set this way in Legion for some reason
132    strandStatusReg = 0x50000;
133    fsr = 0;
134
135    priContext = 0;
136    secContext = 0;
137    partId = 0;
138    lsuCtrlReg = 0;
139
140    memset(scratchPad, 0, sizeof(scratchPad));
141
142    cpu_mondo_head = 0;
143    cpu_mondo_tail = 0;
144    dev_mondo_head = 0;
145    dev_mondo_tail = 0;
146    res_error_head = 0;
147    res_error_tail = 0;
148    nres_error_head = 0;
149    nres_error_tail = 0;
150
151    // If one of these events is active, it's not obvious to me how to get
152    // rid of it cleanly. For now we'll just assert that they're not.
153    if (tickCompare != NULL && sTickCompare != NULL && hSTickCompare != NULL)
154        panic("Tick comparison event active when clearing the ISA object.\n");
155}
156
157MiscReg
158ISA::readMiscRegNoEffect(int miscReg)
159{
160
161  // The three miscRegs are moved up from the switch statement
162  // due to more frequent calls.
163
164  if (miscReg == MISCREG_GL)
165    return gl;
166  if (miscReg == MISCREG_CWP)
167    return cwp;
168  if (miscReg == MISCREG_TLB_DATA) {
169    /* Package up all the data for the tlb:
170     * 6666555555555544444444443333333333222222222211111111110000000000
171     * 3210987654321098765432109876543210987654321098765432109876543210
172     *   secContext   | priContext    |             |tl|partid|  |||||^hpriv
173     *                                                           ||||^red
174     *                                                           |||^priv
175     *                                                           ||^am
176     *                                                           |^lsuim
177     *                                                           ^lsudm
178     */
179    return      (uint64_t)hpstate.hpriv |
180                (uint64_t)hpstate.red << 1 |
181                (uint64_t)pstate.priv << 2 |
182                (uint64_t)pstate.am << 3 |
183           bits((uint64_t)lsuCtrlReg,3,2) << 4 |
184           bits((uint64_t)partId,7,0) << 8 |
185           bits((uint64_t)tl,2,0) << 16 |
186                (uint64_t)priContext << 32 |
187                (uint64_t)secContext << 48;
188  }
189
190    switch (miscReg) {
191      // case MISCREG_TLB_DATA:
192      //  [original contents see above]
193      // case MISCREG_Y:
194      //  return y;
195      // case MISCREG_CCR:
196      //  return ccr;
197      case MISCREG_ASI:
198        return asi;
199      case MISCREG_FPRS:
200        return fprs;
201      case MISCREG_TICK:
202        return tick;
203      case MISCREG_PCR:
204        panic("PCR not implemented\n");
205      case MISCREG_PIC:
206        panic("PIC not implemented\n");
207      case MISCREG_GSR:
208        return gsr;
209      case MISCREG_SOFTINT:
210        return softint;
211      case MISCREG_TICK_CMPR:
212        return tick_cmpr;
213      case MISCREG_STICK:
214        return stick;
215      case MISCREG_STICK_CMPR:
216        return stick_cmpr;
217
218        /** Privilged Registers */
219      case MISCREG_TPC:
220        return tpc[tl-1];
221      case MISCREG_TNPC:
222        return tnpc[tl-1];
223      case MISCREG_TSTATE:
224        return tstate[tl-1];
225      case MISCREG_TT:
226        return tt[tl-1];
227      case MISCREG_PRIVTICK:
228        panic("Priviliged access to tick registers not implemented\n");
229      case MISCREG_TBA:
230        return tba;
231      case MISCREG_PSTATE:
232        return (MiscReg)pstate;
233      case MISCREG_TL:
234        return tl;
235      case MISCREG_PIL:
236        return pil;
237      // CWP, GL moved
238      // case MISCREG_CWP:
239      //   return cwp;
240      // case MISCREG_CANSAVE:
241      //   return cansave;
242      // case MISCREG_CANRESTORE:
243      //   return canrestore;
244      // case MISCREG_CLEANWIN:
245      //   return cleanwin;
246      // case MISCREG_OTHERWIN:
247      //   return otherwin;
248      // case MISCREG_WSTATE:
249      //   return wstate;
250      // case MISCREG_GL:
251      //   return gl;
252
253        /** Hyper privileged registers */
254      case MISCREG_HPSTATE:
255        return (MiscReg)hpstate;
256      case MISCREG_HTSTATE:
257        return htstate[tl-1];
258      case MISCREG_HINTP:
259        return hintp;
260      case MISCREG_HTBA:
261        return htba;
262      case MISCREG_STRAND_STS_REG:
263        return strandStatusReg;
264      case MISCREG_HSTICK_CMPR:
265        return hstick_cmpr;
266
267        /** Floating Point Status Register */
268      case MISCREG_FSR:
269        DPRINTF(MiscRegs, "FSR read as: %#x\n", fsr);
270        return fsr;
271
272      case MISCREG_MMU_P_CONTEXT:
273        return priContext;
274      case MISCREG_MMU_S_CONTEXT:
275        return secContext;
276      case MISCREG_MMU_PART_ID:
277        return partId;
278      case MISCREG_MMU_LSU_CTRL:
279        return lsuCtrlReg;
280
281      case MISCREG_SCRATCHPAD_R0:
282        return scratchPad[0];
283      case MISCREG_SCRATCHPAD_R1:
284        return scratchPad[1];
285      case MISCREG_SCRATCHPAD_R2:
286        return scratchPad[2];
287      case MISCREG_SCRATCHPAD_R3:
288        return scratchPad[3];
289      case MISCREG_SCRATCHPAD_R4:
290        return scratchPad[4];
291      case MISCREG_SCRATCHPAD_R5:
292        return scratchPad[5];
293      case MISCREG_SCRATCHPAD_R6:
294        return scratchPad[6];
295      case MISCREG_SCRATCHPAD_R7:
296        return scratchPad[7];
297      case MISCREG_QUEUE_CPU_MONDO_HEAD:
298        return cpu_mondo_head;
299      case MISCREG_QUEUE_CPU_MONDO_TAIL:
300        return cpu_mondo_tail;
301      case MISCREG_QUEUE_DEV_MONDO_HEAD:
302        return dev_mondo_head;
303      case MISCREG_QUEUE_DEV_MONDO_TAIL:
304        return dev_mondo_tail;
305      case MISCREG_QUEUE_RES_ERROR_HEAD:
306        return res_error_head;
307      case MISCREG_QUEUE_RES_ERROR_TAIL:
308        return res_error_tail;
309      case MISCREG_QUEUE_NRES_ERROR_HEAD:
310        return nres_error_head;
311      case MISCREG_QUEUE_NRES_ERROR_TAIL:
312        return nres_error_tail;
313      default:
314        panic("Miscellaneous register %d not implemented\n", miscReg);
315    }
316}
317
318MiscReg
319ISA::readMiscReg(int miscReg, ThreadContext * tc)
320{
321    switch (miscReg) {
322        // tick and stick are aliased to each other in niagra
323        // well store the tick data in stick and the interrupt bit in tick
324      case MISCREG_STICK:
325      case MISCREG_TICK:
326      case MISCREG_PRIVTICK:
327        // I'm not sure why legion ignores the lowest two bits, but we'll go
328        // with it
329        // change from curCycle() to instCount() until we're done with legion
330        DPRINTF(Timer, "Instruction Count when TICK read: %#X stick=%#X\n",
331                tc->getCpuPtr()->instCount(), stick);
332        return mbits(tc->getCpuPtr()->instCount() + (int64_t)stick,62,2) |
333               mbits(tick,63,63);
334      case MISCREG_FPRS:
335        // in legion if fp is enabled du and dl are set
336        return fprs | 0x3;
337      case MISCREG_PCR:
338      case MISCREG_PIC:
339        panic("Performance Instrumentation not impl\n");
340      case MISCREG_SOFTINT_CLR:
341      case MISCREG_SOFTINT_SET:
342        panic("Can read from softint clr/set\n");
343      case MISCREG_SOFTINT:
344      case MISCREG_TICK_CMPR:
345      case MISCREG_STICK_CMPR:
346      case MISCREG_HINTP:
347      case MISCREG_HTSTATE:
348      case MISCREG_HTBA:
349      case MISCREG_HVER:
350      case MISCREG_STRAND_STS_REG:
351      case MISCREG_HSTICK_CMPR:
352      case MISCREG_QUEUE_CPU_MONDO_HEAD:
353      case MISCREG_QUEUE_CPU_MONDO_TAIL:
354      case MISCREG_QUEUE_DEV_MONDO_HEAD:
355      case MISCREG_QUEUE_DEV_MONDO_TAIL:
356      case MISCREG_QUEUE_RES_ERROR_HEAD:
357      case MISCREG_QUEUE_RES_ERROR_TAIL:
358      case MISCREG_QUEUE_NRES_ERROR_HEAD:
359      case MISCREG_QUEUE_NRES_ERROR_TAIL:
360      case MISCREG_HPSTATE:
361        return readFSReg(miscReg, tc);
362    }
363    return readMiscRegNoEffect(miscReg);
364}
365
366void
367ISA::setMiscRegNoEffect(int miscReg, MiscReg val)
368{
369    switch (miscReg) {
370//      case MISCREG_Y:
371//        y = val;
372//        break;
373//      case MISCREG_CCR:
374//        ccr = val;
375//        break;
376      case MISCREG_ASI:
377        asi = val;
378        break;
379      case MISCREG_FPRS:
380        fprs = val;
381        break;
382      case MISCREG_TICK:
383        tick = val;
384        break;
385      case MISCREG_PCR:
386        panic("PCR not implemented\n");
387      case MISCREG_PIC:
388        panic("PIC not implemented\n");
389      case MISCREG_GSR:
390        gsr = val;
391        break;
392      case MISCREG_SOFTINT:
393        softint = val;
394        break;
395      case MISCREG_TICK_CMPR:
396        tick_cmpr = val;
397        break;
398      case MISCREG_STICK:
399        stick = val;
400        break;
401      case MISCREG_STICK_CMPR:
402        stick_cmpr = val;
403        break;
404
405        /** Privilged Registers */
406      case MISCREG_TPC:
407        tpc[tl-1] = val;
408        break;
409      case MISCREG_TNPC:
410        tnpc[tl-1] = val;
411        break;
412      case MISCREG_TSTATE:
413        tstate[tl-1] = val;
414        break;
415      case MISCREG_TT:
416        tt[tl-1] = val;
417        break;
418      case MISCREG_PRIVTICK:
419        panic("Priviliged access to tick regesiters not implemented\n");
420      case MISCREG_TBA:
421        // clear lower 7 bits on writes.
422        tba = val & ULL(~0x7FFF);
423        break;
424      case MISCREG_PSTATE:
425        pstate = (val & PstateMask);
426        break;
427      case MISCREG_TL:
428        tl = val;
429        break;
430      case MISCREG_PIL:
431        pil = val;
432        break;
433      case MISCREG_CWP:
434        cwp = val;
435        break;
436//      case MISCREG_CANSAVE:
437//        cansave = val;
438//        break;
439//      case MISCREG_CANRESTORE:
440//        canrestore = val;
441//        break;
442//      case MISCREG_CLEANWIN:
443//        cleanwin = val;
444//        break;
445//      case MISCREG_OTHERWIN:
446//        otherwin = val;
447//        break;
448//      case MISCREG_WSTATE:
449//        wstate = val;
450//        break;
451      case MISCREG_GL:
452        gl = val;
453        break;
454
455        /** Hyper privileged registers */
456      case MISCREG_HPSTATE:
457        hpstate = val;
458        break;
459      case MISCREG_HTSTATE:
460        htstate[tl-1] = val;
461        break;
462      case MISCREG_HINTP:
463        hintp = val;
464      case MISCREG_HTBA:
465        htba = val;
466        break;
467      case MISCREG_STRAND_STS_REG:
468        strandStatusReg = val;
469        break;
470      case MISCREG_HSTICK_CMPR:
471        hstick_cmpr = val;
472        break;
473
474        /** Floating Point Status Register */
475      case MISCREG_FSR:
476        fsr = val;
477        DPRINTF(MiscRegs, "FSR written with: %#x\n", fsr);
478        break;
479
480      case MISCREG_MMU_P_CONTEXT:
481        priContext = val;
482        break;
483      case MISCREG_MMU_S_CONTEXT:
484        secContext = val;
485        break;
486      case MISCREG_MMU_PART_ID:
487        partId = val;
488        break;
489      case MISCREG_MMU_LSU_CTRL:
490        lsuCtrlReg = val;
491        break;
492
493      case MISCREG_SCRATCHPAD_R0:
494        scratchPad[0] = val;
495        break;
496      case MISCREG_SCRATCHPAD_R1:
497        scratchPad[1] = val;
498        break;
499      case MISCREG_SCRATCHPAD_R2:
500        scratchPad[2] = val;
501        break;
502      case MISCREG_SCRATCHPAD_R3:
503        scratchPad[3] = val;
504        break;
505      case MISCREG_SCRATCHPAD_R4:
506        scratchPad[4] = val;
507        break;
508      case MISCREG_SCRATCHPAD_R5:
509        scratchPad[5] = val;
510        break;
511      case MISCREG_SCRATCHPAD_R6:
512        scratchPad[6] = val;
513        break;
514      case MISCREG_SCRATCHPAD_R7:
515        scratchPad[7] = val;
516        break;
517      case MISCREG_QUEUE_CPU_MONDO_HEAD:
518        cpu_mondo_head = val;
519        break;
520      case MISCREG_QUEUE_CPU_MONDO_TAIL:
521        cpu_mondo_tail = val;
522        break;
523      case MISCREG_QUEUE_DEV_MONDO_HEAD:
524        dev_mondo_head = val;
525        break;
526      case MISCREG_QUEUE_DEV_MONDO_TAIL:
527        dev_mondo_tail = val;
528        break;
529      case MISCREG_QUEUE_RES_ERROR_HEAD:
530        res_error_head = val;
531        break;
532      case MISCREG_QUEUE_RES_ERROR_TAIL:
533        res_error_tail = val;
534        break;
535      case MISCREG_QUEUE_NRES_ERROR_HEAD:
536        nres_error_head = val;
537        break;
538      case MISCREG_QUEUE_NRES_ERROR_TAIL:
539        nres_error_tail = val;
540        break;
541      default:
542        panic("Miscellaneous register %d not implemented\n", miscReg);
543    }
544}
545
546void
547ISA::setMiscReg(int miscReg, MiscReg val, ThreadContext * tc)
548{
549    MiscReg new_val = val;
550
551    switch (miscReg) {
552      case MISCREG_ASI:
553        tc->getDecodePtr()->setContext(val);
554        break;
555      case MISCREG_STICK:
556      case MISCREG_TICK:
557        // stick and tick are same thing on niagra
558        // use stick for offset and tick for holding intrrupt bit
559        stick = mbits(val,62,0) - tc->getCpuPtr()->instCount();
560        tick = mbits(val,63,63);
561        DPRINTF(Timer, "Writing TICK=%#X\n", val);
562        break;
563      case MISCREG_FPRS:
564        // Configure the fpu based on the fprs
565        break;
566      case MISCREG_PCR:
567        // Set up performance counting based on pcr value
568        break;
569      case MISCREG_PSTATE:
570        pstate = val & PstateMask;
571        return;
572      case MISCREG_TL:
573        {
574            tl = val;
575            if (hpstate.tlz && tl == 0 && !hpstate.hpriv)
576                tc->getCpuPtr()->postInterrupt(IT_TRAP_LEVEL_ZERO, 0);
577            else
578                tc->getCpuPtr()->clearInterrupt(IT_TRAP_LEVEL_ZERO, 0);
579            return;
580        }
581      case MISCREG_CWP:
582        new_val = val >= NWindows ? NWindows - 1 : val;
583        if (val >= NWindows)
584            new_val = NWindows - 1;
585
586        installWindow(new_val, CurrentWindowOffset);
587        installWindow(new_val - 1, NextWindowOffset);
588        installWindow(new_val + 1, PreviousWindowOffset);
589        break;
590      case MISCREG_GL:
591        installGlobals(val, CurrentGlobalsOffset);
592        installGlobals(val, NextGlobalsOffset);
593        installGlobals(val, PreviousGlobalsOffset);
594        break;
595      case MISCREG_PIL:
596      case MISCREG_SOFTINT:
597      case MISCREG_SOFTINT_SET:
598      case MISCREG_SOFTINT_CLR:
599      case MISCREG_TICK_CMPR:
600      case MISCREG_STICK_CMPR:
601      case MISCREG_HINTP:
602      case MISCREG_HTSTATE:
603      case MISCREG_HTBA:
604      case MISCREG_HVER:
605      case MISCREG_STRAND_STS_REG:
606      case MISCREG_HSTICK_CMPR:
607      case MISCREG_QUEUE_CPU_MONDO_HEAD:
608      case MISCREG_QUEUE_CPU_MONDO_TAIL:
609      case MISCREG_QUEUE_DEV_MONDO_HEAD:
610      case MISCREG_QUEUE_DEV_MONDO_TAIL:
611      case MISCREG_QUEUE_RES_ERROR_HEAD:
612      case MISCREG_QUEUE_RES_ERROR_TAIL:
613      case MISCREG_QUEUE_NRES_ERROR_HEAD:
614      case MISCREG_QUEUE_NRES_ERROR_TAIL:
615      case MISCREG_HPSTATE:
616        setFSReg(miscReg, val, tc);
617        return;
618    }
619    setMiscRegNoEffect(miscReg, new_val);
620}
621
622void
623ISA::serialize(EventManager *em, std::ostream &os)
624{
625    SERIALIZE_SCALAR(asi);
626    SERIALIZE_SCALAR(tick);
627    SERIALIZE_SCALAR(fprs);
628    SERIALIZE_SCALAR(gsr);
629    SERIALIZE_SCALAR(softint);
630    SERIALIZE_SCALAR(tick_cmpr);
631    SERIALIZE_SCALAR(stick);
632    SERIALIZE_SCALAR(stick_cmpr);
633    SERIALIZE_ARRAY(tpc,MaxTL);
634    SERIALIZE_ARRAY(tnpc,MaxTL);
635    SERIALIZE_ARRAY(tstate,MaxTL);
636    SERIALIZE_ARRAY(tt,MaxTL);
637    SERIALIZE_SCALAR(tba);
638    SERIALIZE_SCALAR((uint16_t)pstate);
639    SERIALIZE_SCALAR(tl);
640    SERIALIZE_SCALAR(pil);
641    SERIALIZE_SCALAR(cwp);
642    SERIALIZE_SCALAR(gl);
643    SERIALIZE_SCALAR((uint64_t)hpstate);
644    SERIALIZE_ARRAY(htstate,MaxTL);
645    SERIALIZE_SCALAR(hintp);
646    SERIALIZE_SCALAR(htba);
647    SERIALIZE_SCALAR(hstick_cmpr);
648    SERIALIZE_SCALAR(strandStatusReg);
649    SERIALIZE_SCALAR(fsr);
650    SERIALIZE_SCALAR(priContext);
651    SERIALIZE_SCALAR(secContext);
652    SERIALIZE_SCALAR(partId);
653    SERIALIZE_SCALAR(lsuCtrlReg);
654    SERIALIZE_ARRAY(scratchPad,8);
655    SERIALIZE_SCALAR(cpu_mondo_head);
656    SERIALIZE_SCALAR(cpu_mondo_tail);
657    SERIALIZE_SCALAR(dev_mondo_head);
658    SERIALIZE_SCALAR(dev_mondo_tail);
659    SERIALIZE_SCALAR(res_error_head);
660    SERIALIZE_SCALAR(res_error_tail);
661    SERIALIZE_SCALAR(nres_error_head);
662    SERIALIZE_SCALAR(nres_error_tail);
663    Tick tick_cmp = 0, stick_cmp = 0, hstick_cmp = 0;
664    ThreadContext *tc = NULL;
665    BaseCPU *cpu = NULL;
666    int tc_num = 0;
667    bool tick_intr_sched = true;
668
669    if (tickCompare)
670        tc = tickCompare->getTC();
671    else if (sTickCompare)
672        tc = sTickCompare->getTC();
673    else if (hSTickCompare)
674        tc = hSTickCompare->getTC();
675    else
676        tick_intr_sched = false;
677
678    SERIALIZE_SCALAR(tick_intr_sched);
679
680    if (tc) {
681        cpu = tc->getCpuPtr();
682        tc_num = cpu->findContext(tc);
683        if (tickCompare && tickCompare->scheduled())
684            tick_cmp = tickCompare->when();
685        if (sTickCompare && sTickCompare->scheduled())
686            stick_cmp = sTickCompare->when();
687        if (hSTickCompare && hSTickCompare->scheduled())
688            hstick_cmp = hSTickCompare->when();
689
690        SERIALIZE_OBJPTR(cpu);
691        SERIALIZE_SCALAR(tc_num);
692        SERIALIZE_SCALAR(tick_cmp);
693        SERIALIZE_SCALAR(stick_cmp);
694        SERIALIZE_SCALAR(hstick_cmp);
695    }
696}
697
698void
699ISA::unserialize(EventManager *em, Checkpoint *cp, const std::string &section)
700{
701    UNSERIALIZE_SCALAR(asi);
702    UNSERIALIZE_SCALAR(tick);
703    UNSERIALIZE_SCALAR(fprs);
704    UNSERIALIZE_SCALAR(gsr);
705    UNSERIALIZE_SCALAR(softint);
706    UNSERIALIZE_SCALAR(tick_cmpr);
707    UNSERIALIZE_SCALAR(stick);
708    UNSERIALIZE_SCALAR(stick_cmpr);
709    UNSERIALIZE_ARRAY(tpc,MaxTL);
710    UNSERIALIZE_ARRAY(tnpc,MaxTL);
711    UNSERIALIZE_ARRAY(tstate,MaxTL);
712    UNSERIALIZE_ARRAY(tt,MaxTL);
713    UNSERIALIZE_SCALAR(tba);
714    {
715        uint16_t pstate;
716        UNSERIALIZE_SCALAR(pstate);
717        this->pstate = pstate;
718    }
719    UNSERIALIZE_SCALAR(tl);
720    UNSERIALIZE_SCALAR(pil);
721    UNSERIALIZE_SCALAR(cwp);
722    UNSERIALIZE_SCALAR(gl);
723    reloadRegMap();
724    {
725        uint64_t hpstate;
726        UNSERIALIZE_SCALAR(hpstate);
727        this->hpstate = hpstate;
728    }
729    UNSERIALIZE_ARRAY(htstate,MaxTL);
730    UNSERIALIZE_SCALAR(hintp);
731    UNSERIALIZE_SCALAR(htba);
732    UNSERIALIZE_SCALAR(hstick_cmpr);
733    UNSERIALIZE_SCALAR(strandStatusReg);
734    UNSERIALIZE_SCALAR(fsr);
735    UNSERIALIZE_SCALAR(priContext);
736    UNSERIALIZE_SCALAR(secContext);
737    UNSERIALIZE_SCALAR(partId);
738    UNSERIALIZE_SCALAR(lsuCtrlReg);
739    UNSERIALIZE_ARRAY(scratchPad,8);
740    UNSERIALIZE_SCALAR(cpu_mondo_head);
741    UNSERIALIZE_SCALAR(cpu_mondo_tail);
742    UNSERIALIZE_SCALAR(dev_mondo_head);
743    UNSERIALIZE_SCALAR(dev_mondo_tail);
744    UNSERIALIZE_SCALAR(res_error_head);
745    UNSERIALIZE_SCALAR(res_error_tail);
746    UNSERIALIZE_SCALAR(nres_error_head);
747    UNSERIALIZE_SCALAR(nres_error_tail);
748
749    Tick tick_cmp = 0, stick_cmp = 0, hstick_cmp = 0;
750    ThreadContext *tc = NULL;
751    BaseCPU *cpu = NULL;
752    int tc_num;
753    bool tick_intr_sched;
754    UNSERIALIZE_SCALAR(tick_intr_sched);
755    if (tick_intr_sched) {
756        UNSERIALIZE_OBJPTR(cpu);
757        if (cpu) {
758            UNSERIALIZE_SCALAR(tc_num);
759            UNSERIALIZE_SCALAR(tick_cmp);
760            UNSERIALIZE_SCALAR(stick_cmp);
761            UNSERIALIZE_SCALAR(hstick_cmp);
762            tc = cpu->getContext(tc_num);
763
764            if (tick_cmp) {
765                tickCompare = new TickCompareEvent(this, tc);
766                em->schedule(tickCompare, tick_cmp);
767            }
768            if (stick_cmp)  {
769                sTickCompare = new STickCompareEvent(this, tc);
770                em->schedule(sTickCompare, stick_cmp);
771            }
772            if (hstick_cmp)  {
773                hSTickCompare = new HSTickCompareEvent(this, tc);
774                em->schedule(hSTickCompare, hstick_cmp);
775            }
776        }
777    }
778
779}
780
781}
782