summaryrefslogtreecommitdiff
path: root/src/arch/x86/tlb.hh
diff options
context:
space:
mode:
authorGabe Black <gblack@eecs.umich.edu>2007-11-12 14:38:31 -0800
committerGabe Black <gblack@eecs.umich.edu>2007-11-12 14:38:31 -0800
commitfce45baf178b43c2ea1476967fba3766e9b2ea9d (patch)
tree1aa3ba357950f9a18e2d7a7e6fd4be8c8d0e5d91 /src/arch/x86/tlb.hh
parentf17f3d20be08d25f176138691a29897df54e5cc0 (diff)
downloadgem5-fce45baf178b43c2ea1476967fba3766e9b2ea9d.tar.xz
X86: Work on the page table walker, TLB, and related faults.
--HG-- extra : convert_revision : 9edde958b7e571c07072785f18f9109f73b8059f
Diffstat (limited to 'src/arch/x86/tlb.hh')
-rw-r--r--src/arch/x86/tlb.hh114
1 files changed, 52 insertions, 62 deletions
diff --git a/src/arch/x86/tlb.hh b/src/arch/x86/tlb.hh
index 726c25374..d45f94520 100644
--- a/src/arch/x86/tlb.hh
+++ b/src/arch/x86/tlb.hh
@@ -59,6 +59,7 @@
#define __ARCH_X86_TLB_HH__
#include <list>
+#include <vector>
#include <string>
#include "arch/x86/pagetable.hh"
@@ -88,6 +89,8 @@ namespace X86ISA
System * sys;
+ bool allowNX;
+
public:
typedef X86TLBParams Params;
TLB(const Params *p);
@@ -116,65 +119,55 @@ namespace X86ISA
PTE
};
- // Act on the current state and determine what to do next. If the
- // walker has finished updating the TLB, this will return false.
- bool doNext(PacketPtr read, PacketPtr &write);
-
- // This does an actual load to feed the walker. If we're in
- // atomic mode, this will drive the state machine itself until
- // the TLB is filled. If we're in timing mode, the port getting
- // a reply will drive the machine using this function which will
- // return after starting the memory operation.
- void doMemory(Addr addr);
+ // Act on the current state and determine what to do next. read
+ // should be the packet that just came back from a read and write
+ // should be NULL. When the function returns, read is either NULL
+ // if the machine is finished, or points to a packet to initiate
+ // the next read. If any write is required to update an "accessed"
+ // bit, write will point to a packet to do the write. Otherwise it
+ // will be NULL.
+ void doNext(PacketPtr &read, PacketPtr &write);
// Kick off the state machine.
- void start(bool _uncachable, Addr _vaddr, Addr cr3, State next)
- {
- assert(state == Ready);
- state = Waiting;
- nextState = next;
- // If PAE isn't being used, entries are 4 bytes. Otherwise
- // they're 8.
- if (next == PSEPD || next == PD || next == PTE)
- size = 4;
- else
- size = 8;
- vaddr = _vaddr;
- uncachable = _uncacheable;
- buildPacket(cr3);
- if (state == Enums::timing) {
- port->sendTiming(&packet);
- } else if (state == Enums::atomic) {
- port->sendAtomic(&packet);
- Addr addr;
- while(doNext(packet.get<uint64_t>(), addr)) {
- buildPacket(addr);
- port->sendAtomic(&packet);
- }
- } else {
- panic("Unrecognized memory system mode.\n");
- }
- };
+ void start(ThreadContext * _tc, Addr vaddr);
protected:
friend class TLB;
+ /*
+ * State having to do with sending packets.
+ */
+ PacketPtr read;
+ std::vector<PacketPtr> writes;
+
+ // How many memory operations are in flight.
+ unsigned inflight;
+
+ bool retrying;
+
+ /*
+ * Functions for dealing with packets.
+ */
+ bool recvTiming(PacketPtr pkt);
+ void recvRetry();
+
+ void sendPackets();
+
+ /*
+ * Port for accessing memory
+ */
class WalkerPort : public Port
{
public:
WalkerPort(const std::string &_name, Walker * _walker) :
Port(_name, _walker->tlb), walker(_walker),
- packet(NULL), snoopRangeSent(false), retrying(false)
+ snoopRangeSent(false)
{}
protected:
Walker * walker;
- PacketPtr packet;
- vector<PacketPtr> writes;
-
bool snoopRangeSent;
- bool retrying;
bool recvTiming(PacketPtr pkt);
Tick recvAtomic(PacketPtr pkt);
@@ -187,46 +180,41 @@ namespace X86ISA
resp.clear();
snoop = true;
}
-
- public:
- bool sendTiming(PacketPtr pkt)
- {
- retrying = !Port::sendTiming(pkt);
- return !retrying;
- }
-
- bool blocked() { return retrying; }
};
friend class WalkerPort;
WalkerPort port;
- Packet packet;
- Request request;
-
+ // The TLB we're supposed to load.
TLB * tlb;
+ /*
+ * State machine state.
+ */
+ ThreadContext * tc;
State state;
State nextState;
int size;
-
- Addr vaddr;
+ bool enableNX;
+ TlbEntry entry;
public:
Walker(const std::string &_name, TLB * _tlb) :
+ read(NULL), inflight(0), retrying(false),
port(_name + "-walker_port", this),
- packet(&request, ReadExReq, Broadcast),
- tlb(_tlb), state(Ready), nextState(Ready)
+ tlb(_tlb),
+ tc(NULL), state(Ready), nextState(Ready)
{
}
-
-
};
Walker walker;
+
#endif
+ Port *getPort(const std::string &if_name, int idx = -1);
+
protected:
int size;
@@ -236,8 +224,6 @@ namespace X86ISA
EntryList freeList;
EntryList entryList;
- Port *getPort(const std::string &if_name, int idx = -1);
-
void insert(Addr vpn, TlbEntry &entry);
void invalidateAll();
@@ -262,6 +248,8 @@ namespace X86ISA
typedef X86ITBParams Params;
ITB(const Params *p) : TLB(p)
{
+ sys = p->system;
+ allowNX = false;
}
Fault translate(RequestPtr &req, ThreadContext *tc);
@@ -275,6 +263,8 @@ namespace X86ISA
typedef X86DTBParams Params;
DTB(const Params *p) : TLB(p)
{
+ sys = p->system;
+ allowNX = true;
}
Fault translate(RequestPtr &req, ThreadContext *tc, bool write);
#if FULL_SYSTEM