base.hh revision 9754:91fbf7b7e933
1/* 2 * Copyright (c) 2012 ARM Limited 3 * All rights reserved 4 * 5 * The license below extends only to copyright in the software and shall 6 * not be construed as granting a license to any other intellectual 7 * property including but not limited to intellectual property relating 8 * to a hardware implementation of the functionality of the software 9 * licensed hereunder. You may use the software subject to the license 10 * terms below provided that you ensure that this notice is replicated 11 * unmodified and in its entirety in all distributions of the software, 12 * modified or unmodified, in source code or in binary form. 13 * 14 * Redistribution and use in source and binary forms, with or without 15 * modification, are permitted provided that the following conditions are 16 * met: redistributions of source code must retain the above copyright 17 * notice, this list of conditions and the following disclaimer; 18 * redistributions in binary form must reproduce the above copyright 19 * notice, this list of conditions and the following disclaimer in the 20 * documentation and/or other materials provided with the distribution; 21 * neither the name of the copyright holders nor the names of its 22 * contributors may be used to endorse or promote products derived from 23 * this software without specific prior written permission. 24 * 25 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 26 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 27 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 28 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 29 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 30 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 31 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 32 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 33 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 34 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 35 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 36 * 37 * Authors: Andreas Sandberg 38 */ 39 40#ifndef __CPU_KVM_BASE_HH__ 41#define __CPU_KVM_BASE_HH__ 42 43#include <memory> 44#include <csignal> 45 46#include "base/statistics.hh" 47#include "cpu/kvm/perfevent.hh" 48#include "cpu/kvm/timer.hh" 49#include "cpu/kvm/vm.hh" 50#include "cpu/base.hh" 51#include "cpu/simple_thread.hh" 52 53/** Signal to use to trigger time-based exits from KVM */ 54#define KVM_TIMER_SIGNAL SIGRTMIN 55 56// forward declarations 57class ThreadContext; 58struct BaseKvmCPUParams; 59 60/** 61 * Base class for KVM based CPU models 62 * 63 * All architecture specific KVM implementation should inherit from 64 * this class. The most basic CPU models only need to override the 65 * updateKvmState() and updateThreadContext() methods to implement 66 * state synchronization between gem5 and KVM. 67 * 68 * The architecture specific implementation is also responsible for 69 * delivering interrupts into the VM. This is typically done by 70 * overriding tick() and checking the thread context before entering 71 * into the VM. In order to deliver an interrupt, the implementation 72 * then calls KvmVM::setIRQLine() or BaseKvmCPU::kvmInterrupt() 73 * depending on the specifics of the underlying hardware/drivers. 74 */ 75class BaseKvmCPU : public BaseCPU 76{ 77 public: 78 BaseKvmCPU(BaseKvmCPUParams *params); 79 virtual ~BaseKvmCPU(); 80 81 void init(); 82 void startup(); 83 void regStats(); 84 85 void serializeThread(std::ostream &os, ThreadID tid); 86 void unserializeThread(Checkpoint *cp, const std::string §ion, 87 ThreadID tid); 88 89 unsigned int drain(DrainManager *dm); 90 void drainResume(); 91 92 void switchOut(); 93 void takeOverFrom(BaseCPU *cpu); 94 95 void verifyMemoryMode() const; 96 97 MasterPort &getDataPort() { return dataPort; } 98 MasterPort &getInstPort() { return instPort; } 99 100 void wakeup(); 101 void activateContext(ThreadID thread_num, Cycles delay); 102 void suspendContext(ThreadID thread_num); 103 void deallocateContext(ThreadID thread_num); 104 void haltContext(ThreadID thread_num); 105 106 ThreadContext *getContext(int tn); 107 108 Counter totalInsts() const; 109 Counter totalOps() const; 110 111 /** Dump the internal state to the terminal. */ 112 virtual void dump(); 113 114 /** 115 * A cached copy of a thread's state in the form of a SimpleThread 116 * object. 117 * 118 * Normally the actual thread state is stored in the KVM vCPU. If KVM has 119 * been running this copy is will be out of date. If we recently handled 120 * some events within gem5 that required state to be updated this could be 121 * the most up-to-date copy. When getContext() or updateThreadContext() is 122 * called this copy gets updated. The method syncThreadContext can 123 * be used within a KVM CPU to update the thread context if the 124 * KVM state is dirty (i.e., the vCPU has been run since the last 125 * update). 126 */ 127 SimpleThread *thread; 128 129 /** ThreadContext object, provides an interface for external 130 * objects to modify this thread's state. 131 */ 132 ThreadContext *tc; 133 134 KvmVM &vm; 135 136 protected: 137 /** 138 * 139 * @dot 140 * digraph { 141 * Idle; 142 * Running; 143 * RunningService; 144 * RunningServiceCompletion; 145 * 146 * Idle -> Idle; 147 * Idle -> Running [label="activateContext()", URL="\ref activateContext"]; 148 * Running -> Running [label="tick()", URL="\ref tick"]; 149 * Running -> RunningService [label="tick()", URL="\ref tick"]; 150 * Running -> Idle [label="suspendContext()", URL="\ref suspendContext"]; 151 * Running -> Idle [label="drain()", URL="\ref drain"]; 152 * Idle -> Running [label="drainResume()", URL="\ref drainResume"]; 153 * RunningService -> RunningServiceCompletion [label="handleKvmExit()", URL="\ref handleKvmExit"]; 154 * RunningServiceCompletion -> Running [label="tick()", URL="\ref tick"]; 155 * RunningServiceCompletion -> RunningService [label="tick()", URL="\ref tick"]; 156 * } 157 * @enddot 158 */ 159 enum Status { 160 /** Context not scheduled in KVM. 161 * 162 * The CPU generally enters this state when the guest execute 163 * an instruction that halts the CPU (e.g., WFI on ARM or HLT 164 * on X86) if KVM traps this instruction. Ticks are not 165 * scheduled in this state. 166 * 167 * @see suspendContext() 168 */ 169 Idle, 170 /** Running normally. 171 * 172 * This is the normal run state of the CPU. KVM will be 173 * entered next time tick() is called. 174 */ 175 Running, 176 /** Requiring service at the beginning of the next cycle. 177 * 178 * The virtual machine has exited and requires service, tick() 179 * will call handleKvmExit() on the next cycle. The next state 180 * after running service is determined in handleKvmExit() and 181 * depends on what kind of service the guest requested: 182 * <ul> 183 * <li>IO/MMIO: RunningServiceCompletion 184 * <li>Halt: Idle 185 * <li>Others: Running 186 * </ul> 187 */ 188 RunningService, 189 /** Service completion in progress. 190 * 191 * The VM has requested service that requires KVM to be 192 * entered once in order to get to a consistent state. This 193 * happens in handleKvmExit() or one of its friends after IO 194 * exits. After executing tick(), the CPU will transition into 195 * the Running or RunningService state. 196 */ 197 RunningServiceCompletion, 198 }; 199 200 /** CPU run state */ 201 Status _status; 202 203 /** 204 * Execute the CPU until the next event in the main event queue or 205 * until the guest needs service from gem5. 206 */ 207 void tick(); 208 209 /** 210 * Get the value of the hardware cycle counter in the guest. 211 * 212 * This method is supposed to return the total number of cycles 213 * executed in hardware mode relative to some arbitrary point in 214 * the past. It's mainly used when estimating the number of cycles 215 * actually executed by the CPU in kvmRun(). The default behavior 216 * of this method is to use the cycles performance counter, but 217 * some architectures may want to use internal registers instead. 218 * 219 * @return Number of host cycles executed relative to an undefined 220 * point in the past. 221 */ 222 virtual uint64_t getHostCycles() const; 223 224 /** 225 * Request KVM to run the guest for a given number of ticks. The 226 * method returns the approximate number of ticks executed. 227 * 228 * @note The returned number of ticks can be both larger or 229 * smaller than the requested number of ticks. A smaller number 230 * can, for example, occur when the guest executes MMIO. A larger 231 * number is typically due to performance counter inaccuracies. 232 * 233 * @note This method is virtual in order to allow implementations 234 * to check for architecture specific events (e.g., interrupts) 235 * before entering the VM. 236 * 237 * @note It is the response of the caller (normally tick()) to 238 * make sure that the KVM state is synchronized and that the TC is 239 * invalidated after entering KVM. 240 * 241 * @param ticks Number of ticks to execute, set to 0 to exit 242 * immediately after finishing pending operations. 243 * @return Number of ticks executed (see note) 244 */ 245 virtual Tick kvmRun(Tick ticks); 246 247 /** 248 * Request the CPU to run until draining completes. 249 * 250 * This function normally calls kvmRun(0) to make KVM finish 251 * pending MMIO operations. Architecures implementing 252 * archIsDrained() must override this method. 253 * 254 * @see BaseKvmCPU::archIsDrained() 255 * 256 * @return Number of ticks executed 257 */ 258 virtual Tick kvmRunDrain(); 259 260 /** 261 * Get a pointer to the kvm_run structure containing all the input 262 * and output parameters from kvmRun(). 263 */ 264 struct kvm_run *getKvmRunState() { return _kvmRun; }; 265 266 /** 267 * Retrieve a pointer to guest data stored at the end of the 268 * kvm_run structure. This is mainly used for PIO operations 269 * (KVM_EXIT_IO). 270 * 271 * @param offset Offset as specified by the kvm_run structure 272 * @return Pointer to guest data 273 */ 274 uint8_t *getGuestData(uint64_t offset) const { 275 return (uint8_t *)_kvmRun + offset; 276 }; 277 278 /** 279 * @addtogroup KvmInterrupts 280 * @{ 281 */ 282 /** 283 * Send a non-maskable interrupt to the guest 284 * 285 * @note The presence of this call depends on Kvm::capUserNMI(). 286 */ 287 void kvmNonMaskableInterrupt(); 288 289 /** 290 * Send a normal interrupt to the guest 291 * 292 * @note Make sure that ready_for_interrupt_injection in kvm_run 293 * is set prior to calling this function. If not, an interrupt 294 * window must be requested by setting request_interrupt_window in 295 * kvm_run to 1 and restarting the guest. 296 * 297 * @param interrupt Structure describing the interrupt to send 298 */ 299 void kvmInterrupt(const struct kvm_interrupt &interrupt); 300 301 /** @} */ 302 303 /** @{ */ 304 /** 305 * Get/Set the register state of the guest vCPU 306 * 307 * KVM has two different interfaces for accessing the state of the 308 * guest CPU. One interface updates 'normal' registers and one 309 * updates 'special' registers. The distinction between special 310 * and normal registers isn't very clear and is architecture 311 * dependent. 312 */ 313 void getRegisters(struct kvm_regs ®s) const; 314 void setRegisters(const struct kvm_regs ®s); 315 void getSpecialRegisters(struct kvm_sregs ®s) const; 316 void setSpecialRegisters(const struct kvm_sregs ®s); 317 /** @} */ 318 319 /** @{ */ 320 /** 321 * Get/Set the guest FPU/vector state 322 */ 323 void getFPUState(struct kvm_fpu &state) const; 324 void setFPUState(const struct kvm_fpu &state); 325 /** @} */ 326 327 /** @{ */ 328 /** 329 * Get/Set single register using the KVM_(SET|GET)_ONE_REG API. 330 * 331 * @note The presence of this call depends on Kvm::capOneReg(). 332 */ 333 void setOneReg(uint64_t id, const void *addr); 334 void setOneReg(uint64_t id, uint64_t value) { setOneReg(id, &value); } 335 void setOneReg(uint64_t id, uint32_t value) { setOneReg(id, &value); } 336 void getOneReg(uint64_t id, void *addr) const; 337 uint64_t getOneRegU64(uint64_t id) const { 338 uint64_t value; 339 getOneReg(id, &value); 340 return value; 341 } 342 uint32_t getOneRegU32(uint64_t id) const { 343 uint32_t value; 344 getOneReg(id, &value); 345 return value; 346 } 347 /** @} */ 348 349 /** 350 * Get and format one register for printout. 351 * 352 * This function call getOneReg() to retrieve the contents of one 353 * register and automatically formats it for printing. 354 * 355 * @note The presence of this call depends on Kvm::capOneReg(). 356 */ 357 std::string getAndFormatOneReg(uint64_t id) const; 358 359 /** @{ */ 360 /** 361 * Update the KVM state from the current thread context 362 * 363 * The base CPU calls this method before starting the guest CPU 364 * when the contextDirty flag is set. The architecture dependent 365 * CPU implementation is expected to update all guest state 366 * (registers, special registers, and FPU state). 367 */ 368 virtual void updateKvmState() = 0; 369 370 /** 371 * Update the current thread context with the KVM state 372 * 373 * The base CPU after the guest updates any of the KVM state. In 374 * practice, this happens after kvmRun is called. The architecture 375 * dependent code is expected to read the state of the guest CPU 376 * and update gem5's thread state. 377 */ 378 virtual void updateThreadContext() = 0; 379 380 /** 381 * Update a thread context if the KVM state is dirty with respect 382 * to the cached thread context. 383 */ 384 void syncThreadContext(); 385 386 /** 387 * Update the KVM if the thread context is dirty. 388 */ 389 void syncKvmState(); 390 /** @} */ 391 392 /** @{ */ 393 /** 394 * Main kvmRun exit handler, calls the relevant handleKvmExit* 395 * depending on exit type. 396 * 397 * @return Number of ticks spent servicing the exit request 398 */ 399 virtual Tick handleKvmExit(); 400 401 /** 402 * The guest performed a legacy IO request (out/inp on x86) 403 * 404 * @return Number of ticks spent servicing the IO request 405 */ 406 virtual Tick handleKvmExitIO(); 407 408 /** 409 * The guest requested a monitor service using a hypercall 410 * 411 * @return Number of ticks spent servicing the hypercall 412 */ 413 virtual Tick handleKvmExitHypercall(); 414 415 /** 416 * The guest exited because an interrupt window was requested 417 * 418 * The guest exited because an interrupt window was requested 419 * (request_interrupt_window in the kvm_run structure was set to 1 420 * before calling kvmRun) and it is now ready to receive 421 * 422 * @return Number of ticks spent servicing the IRQ 423 */ 424 virtual Tick handleKvmExitIRQWindowOpen(); 425 426 /** 427 * An unknown architecture dependent error occurred when starting 428 * the vCPU 429 * 430 * The kvm_run data structure contains the hardware error 431 * code. The defaults behavior of this method just prints the HW 432 * error code and panics. Architecture dependent implementations 433 * may want to override this method to provide better, 434 * hardware-aware, error messages. 435 * 436 * @return Number of ticks delay the next CPU tick 437 */ 438 virtual Tick handleKvmExitUnknown(); 439 440 /** 441 * An unhandled virtualization exception occured 442 * 443 * Some KVM virtualization drivers return unhandled exceptions to 444 * the user-space monitor. This interface is currently only used 445 * by the Intel VMX KVM driver. 446 * 447 * @return Number of ticks delay the next CPU tick 448 */ 449 virtual Tick handleKvmExitException(); 450 451 /** 452 * KVM failed to start the virtualized CPU 453 * 454 * The kvm_run data structure contains the hardware-specific error 455 * code. 456 * 457 * @return Number of ticks delay the next CPU tick 458 */ 459 virtual Tick handleKvmExitFailEntry(); 460 /** @} */ 461 462 /** 463 * Is the architecture specific code in a state that prevents 464 * draining? 465 * 466 * This method should return false if there are any pending events 467 * in the guest vCPU that won't be carried over to the gem5 state 468 * and thus will prevent correct checkpointing or CPU handover. It 469 * might, for example, check for pending interrupts that have been 470 * passed to the vCPU but not acknowledged by the OS. Architecures 471 * implementing this method <i>must</i> override 472 * kvmRunDrain(). 473 * 474 * @see BaseKvmCPU::kvmRunDrain() 475 * 476 * @return true if the vCPU is drained, false otherwise. 477 */ 478 virtual bool archIsDrained() const { return true; } 479 480 /** 481 * Inject a memory mapped IO request into gem5 482 * 483 * @param paddr Physical address 484 * @param data Pointer to the source/destination buffer 485 * @param size Memory access size 486 * @param write True if write, False if read 487 * @return Number of ticks spent servicing the memory access 488 */ 489 Tick doMMIOAccess(Addr paddr, void *data, int size, bool write); 490 491 /** @{ */ 492 /** 493 * Set the signal mask used in kvmRun() 494 * 495 * This method allows the signal mask of the thread executing 496 * kvmRun() to be overridden inside the actual system call. This 497 * allows us to mask timer signals used to force KVM exits while 498 * in gem5. 499 * 500 * The signal mask can be disabled by setting it to NULL. 501 * 502 * @param mask Signals to mask 503 */ 504 void setSignalMask(const sigset_t *mask); 505 /** @} */ 506 507 /** 508 * @addtogroup KvmIoctl 509 * @{ 510 */ 511 /** 512 * vCPU ioctl interface. 513 * 514 * @param request KVM vCPU request 515 * @param p1 Optional request parameter 516 * 517 * @return -1 on error (error number in errno), ioctl dependent 518 * value otherwise. 519 */ 520 int ioctl(int request, long p1) const; 521 int ioctl(int request, void *p1) const { 522 return ioctl(request, (long)p1); 523 } 524 int ioctl(int request) const { 525 return ioctl(request, 0L); 526 } 527 /** @} */ 528 529 530 /** 531 * KVM memory port. Uses the default MasterPort behavior, but 532 * panics on timing accesses. 533 */ 534 class KVMCpuPort : public MasterPort 535 { 536 537 public: 538 KVMCpuPort(const std::string &_name, BaseKvmCPU *_cpu) 539 : MasterPort(_name, _cpu) 540 { } 541 542 protected: 543 bool recvTimingResp(PacketPtr pkt) 544 { 545 panic("The KVM CPU doesn't expect recvTimingResp!\n"); 546 return true; 547 } 548 549 void recvRetry() 550 { 551 panic("The KVM CPU doesn't expect recvRetry!\n"); 552 } 553 554 }; 555 556 /** Port for data requests */ 557 KVMCpuPort dataPort; 558 559 /** Unused dummy port for the instruction interface */ 560 KVMCpuPort instPort; 561 562 /** Pre-allocated MMIO memory request */ 563 Request mmio_req; 564 565 /** 566 * Is the gem5 context dirty? Set to true to force an update of 567 * the KVM vCPU state upon the next call to kvmRun(). 568 */ 569 bool threadContextDirty; 570 571 /** 572 * Is the KVM state dirty? Set to true to force an update of 573 * the KVM vCPU state upon the next call to kvmRun(). 574 */ 575 bool kvmStateDirty; 576 577 /** KVM internal ID of the vCPU */ 578 const long vcpuID; 579 580 private: 581 struct TickEvent : public Event 582 { 583 BaseKvmCPU &cpu; 584 585 TickEvent(BaseKvmCPU &c) 586 : Event(CPU_Tick_Pri), cpu(c) {} 587 588 void process() { cpu.tick(); } 589 590 const char *description() const { 591 return "BaseKvmCPU tick"; 592 } 593 }; 594 595 /** 596 * Service MMIO requests in the mmioRing. 597 * 598 * 599 * @return Number of ticks spent servicing the MMIO requests in 600 * the MMIO ring buffer 601 */ 602 Tick flushCoalescedMMIO(); 603 604 /** 605 * Setup a signal handler to catch the timer signal used to 606 * switch back to the monitor. 607 */ 608 void setupSignalHandler(); 609 610 /** 611 * Discard a (potentially) pending signal. 612 * 613 * @param signum Signal to discard 614 * @return true if the signal was pending, false otherwise. 615 */ 616 bool discardPendingSignal(int signum) const; 617 618 /** Setup hardware performance counters */ 619 void setupCounters(); 620 621 /** Try to drain the CPU if a drain is pending */ 622 bool tryDrain(); 623 624 /** Execute the KVM_RUN ioctl */ 625 void ioctlRun(); 626 627 /** KVM vCPU file descriptor */ 628 int vcpuFD; 629 /** Size of MMAPed kvm_run area */ 630 int vcpuMMapSize; 631 /** 632 * Pointer to the kvm_run structure used to communicate parameters 633 * with KVM. 634 * 635 * @note This is the base pointer of the MMAPed KVM region. The 636 * first page contains the kvm_run structure. Subsequent pages may 637 * contain other data such as the MMIO ring buffer. 638 */ 639 struct kvm_run *_kvmRun; 640 /** 641 * Coalesced MMIO ring buffer. NULL if coalesced MMIO is not 642 * supported. 643 */ 644 struct kvm_coalesced_mmio_ring *mmioRing; 645 /** Cached page size of the host */ 646 const long pageSize; 647 648 TickEvent tickEvent; 649 650 /** @{ */ 651 /** Guest performance counters */ 652 PerfKvmCounter hwCycles; 653 PerfKvmCounter hwInstructions; 654 /** @} */ 655 656 /** 657 * Does the runTimer control the performance counters? 658 * 659 * The run timer will automatically enable and disable performance 660 * counters if a PerfEvent-based timer is used to control KVM 661 * exits. 662 */ 663 bool perfControlledByTimer; 664 665 /** 666 * Timer used to force execution into the monitor after a 667 * specified number of simulation tick equivalents have executed 668 * in the guest. This counter generates the signal specified by 669 * KVM_TIMER_SIGNAL. 670 */ 671 std::unique_ptr<BaseKvmTimer> runTimer; 672 673 /** Host frequency */ 674 Tick hostFreq; 675 676 /** Host factor as specified in the configuration */ 677 float hostFactor; 678 679 /** 680 * Drain manager to use when signaling drain completion 681 * 682 * This pointer is non-NULL when draining and NULL otherwise. 683 */ 684 DrainManager *drainManager; 685 686 public: 687 /* @{ */ 688 Stats::Scalar numInsts; 689 Stats::Scalar numVMExits; 690 Stats::Scalar numMMIO; 691 Stats::Scalar numCoalescedMMIO; 692 Stats::Scalar numIO; 693 Stats::Scalar numHalt; 694 Stats::Scalar numInterrupts; 695 Stats::Scalar numHypercalls; 696 /* @} */ 697 698 /** Number of instructions executed by the CPU */ 699 Counter ctrInsts; 700}; 701 702#endif 703