diff --git a/wally-pipelined/src/lsu/lsu.sv b/wally-pipelined/src/lsu/lsu.sv
index d138a933a..df3d32f28 100644
--- a/wally-pipelined/src/lsu/lsu.sv
+++ b/wally-pipelined/src/lsu/lsu.sv
@@ -123,6 +123,9 @@ module lsu
   logic 		       HPTWStall;  
   logic [`XLEN-1:0] 	       HPTWPAdrE;
   logic [`XLEN-1:0] 	       HPTWPAdrM;  
+  logic [`XLEN-1:0] TranslationVAdr;
+  logic [`PA_BITS-1:0] TranslationPAdr;
+  logic            UseTranslationVAdr;
   logic 		       HPTWRead;
   logic [1:0] 		       MemRWMtoDCache;
   logic [2:0] 		       Funct3MtoDCache;
@@ -162,15 +165,22 @@ module lsu
 				  .DTLBWriteM(DTLBWriteM),
 				  .HPTWReadPTE(HPTWReadPTE),
 				  .HPTWStall(HPTWStall),
-				  .HPTWPAdrE(HPTWPAdrE),
-				  .HPTWPAdrM(HPTWPAdrM),				  
+          .TranslationVAdr,
+          .TranslationPAdr,			  
+          .UseTranslationVAdr,
 				  .HPTWRead(HPTWRead),
 				  .SelPTW(SelPTW),
 				  .WalkerInstrPageFaultF(WalkerInstrPageFaultF),
 				  .WalkerLoadPageFaultM(WalkerLoadPageFaultM),  
 				  .WalkerStorePageFaultM(WalkerStorePageFaultM));
 
-//  assign PageTableEntryF = PTE;
+  logic [`XLEN-1:0] TranslationPAdrXLEN;
+  generate // *** needs fixing about truncation dh 7/17/21
+    if (`XLEN == 32) assign TranslationPAdrXLEN = TranslationPAdr[31:0];
+    else             assign TranslationPAdrXLEN = {{(`XLEN-`PA_BITS){1'b0}}, TranslationPAdr[`PA_BITS-1:0]};
+  endgenerate
+  mux2 #(`XLEN) HPTWPAdrMux(TranslationPAdrXLEN, TranslationVAdr, UseTranslationVAdr, HPTWPAdrE); // *** misleading to call it PAdr, bad because some bits have been truncated
+  flop #(`XLEN) HPTWPAdrMReg(clk, HPTWPAdrE, HPTWPAdrM);  
   
   assign WalkerPageFaultM = WalkerStorePageFaultM | WalkerLoadPageFaultM;
 
diff --git a/wally-pipelined/src/mmu/pagetablewalker.sv b/wally-pipelined/src/mmu/pagetablewalker.sv
index 8c524fbd1..fe8aaf5b1 100644
--- a/wally-pipelined/src/mmu/pagetablewalker.sv
+++ b/wally-pipelined/src/mmu/pagetablewalker.sv
@@ -31,46 +31,29 @@
 
 module pagetablewalker
   (
-   // Control signals
    input logic		    clk, reset,
-   input logic [`XLEN-1:0]  SATP_REGW,
-
-   // Signals from TLBs (addresses to translate)
-   input logic [`XLEN-1:0]  PCF, MemAdrM,
-   input logic		    ITLBMissF, DTLBMissM,
-   input logic [1:0]	    MemRWM,
-
-   // Outputs to the TLBs (PTEs to write)
-   output logic [`XLEN-1:0] PTE, //PageTableEntryM,
-   output logic [1:0]	    PageType,
-   output logic		    ITLBWriteF, DTLBWriteM,
-   output logic 	    SelPTW,
-
-
-   // *** modify to send to LSU // *** KMG: These are inputs/results from the ahblite whose addresses should have already been checked, so I don't think they need to be sent through the LSU
-   input logic [`XLEN-1:0]  HPTWReadPTE,
-   input logic		    HPTWStall,
-
-   // *** modify to send to LSU
-   output logic [`XLEN-1:0] HPTWPAdrE, // this probalby should be `PA_BITS wide
-   output logic [`XLEN-1:0] HPTWPAdrM, // this probalby should be `PA_BITS wide
-   output logic		    HPTWRead,
-
-
-   // Faults
-   output logic		    WalkerInstrPageFaultF,
-   output logic		    WalkerLoadPageFaultM,
-   output logic		    WalkerStorePageFaultM
-   );
-
+   input logic [`XLEN-1:0]  SATP_REGW, // includes SATP.MODE to determine number of levels in page table
+   input logic [`XLEN-1:0]  PCF, MemAdrM, // addresses to translate
+   input logic		    ITLBMissF, DTLBMissM, // TLB Miss
+   input logic [1:0]	    MemRWM, // 10 = read, 01 = write
+   input logic [`XLEN-1:0]  HPTWReadPTE, // page table entry from LSU
+   input logic		    HPTWStall, // stall from LSU
+   output logic [`XLEN-1:0] PTE,  // page table entry to TLBs
+   output logic [1:0]	    PageType, // page type to TLBs
+   output logic		    ITLBWriteF, DTLBWriteM, // write TLB with new entry
+   output logic 	    SelPTW, // LSU Arbiter should select signals from the PTW rather than from the IEU
+   output logic [`XLEN-1:0]		    TranslationVAdr,
+   output logic [`PA_BITS-1:0]	    TranslationPAdr,
+   output logic                     UseTranslationVAdr,
+   output logic		    HPTWRead, // HPTW requesting to read memory
+   output logic		    WalkerInstrPageFaultF, WalkerLoadPageFaultM,WalkerStorePageFaultM // faults
+);
 
   generate
     if (`MEM_VIRTMEM) begin
       // Internal signals
       logic			    DTLBWalk; // register TLBs translation miss requests
       logic [`PPN_BITS-1:0]	    BasePageTablePPN;
-      logic [`XLEN-1:0]		    TranslationVAdr;
-      logic [`PA_BITS-1:0]	    TranslationPAdr;
       logic [`PPN_BITS-1:0]	    CurrentPPN;
       logic			    MemWrite;
       logic			    Executable, Writable, Readable, Valid;
@@ -96,13 +79,12 @@ module pagetablewalker
 
       // Determine which address to translate
  	  assign TranslationVAdr = DTLBWalk ? MemAdrM : PCF;
-    
-      flop #(`XLEN) HPTWPAdrMReg(clk, HPTWPAdrE, HPTWPAdrM);
-	  flopenrc #(1) TLBMissMReg(clk, reset, EndWalk, StartWalk | EndWalk, DTLBMissM, DTLBWalk);
-	  flopenl #(.TYPE(statetype)) WalkerStateReg(clk, reset, 1'b1, NextWalkerState, IDLE, WalkerState);
-	  flopenr #(`XLEN) PTEReg(clk, reset, PRegEn, HPTWReadPTE, PTE); // Capture page table entry from data cache
-	  assign CurrentPPN = PTE[`PPN_BITS+9:10];
+      assign CurrentPPN = PTE[`PPN_BITS+9:10];
 
+	  // State flops
+ 	  flopenrc #(1) TLBMissMReg(clk, reset, EndWalk, StartWalk | EndWalk, DTLBMissM, DTLBWalk); // track whether walk is for DTLB or ITLB
+	  flopenr #(`XLEN) PTEReg(clk, reset, PRegEn, HPTWReadPTE, PTE); // Capture page table entry from data cache
+	
       // Assign PTE descriptors common across all XLEN values
 	  // For non-leaf PTEs, D, A, U bits are reserved and ignored.  They do not cause faults while walking the page table
       assign {Executable, Writable, Readable, Valid} = PTE[3:0]; 
@@ -119,6 +101,7 @@ module pagetablewalker
 	  assign SelPTW = (WalkerState != IDLE) & (WalkerState != FAULT);
 	  assign DTLBWriteM = (WalkerState == LEAF) & DTLBWalk;
 	  assign ITLBWriteF = (WalkerState == LEAF) & ~DTLBWalk;
+	  assign UseTranslationVAdr = (NextWalkerState == LEAF) || (WalkerState == LEAF);
 
 	  // Raise faults.  DTLBMiss
 	  assign WalkerInstrPageFaultF = (WalkerState == FAULT) & ~DTLBWalk;
@@ -136,49 +119,31 @@ module pagetablewalker
 			default: NextPageType = PageType;
 		endcase
 
-	  // TranslationPAdr mux
-	  if (`XLEN==32) begin
-		logic [9:0] VPN1, VPN0;
-		assign VPN1 = TranslationVAdr[31:22];
-		assign VPN0 = TranslationVAdr[21:12];
+	  // TranslationPAdr muxing
+	  if (`XLEN==32) begin // RV32
+		logic [9:0] VPN;
+		logic [`PPN_BITS-1:0] PPN;
+		assign VPN = ((WalkerState == LEVEL1_SET_ADR) | (WalkerState == LEVEL1_READ)) ? TranslationVAdr[31:22] : TranslationVAdr[21:12]; // select VPN field based on HPTW state
+		assign PPN = ((WalkerState == LEVEL1_SET_ADR) | (WalkerState == LEVEL1_READ)) ? BasePageTablePPN : CurrentPPN; 
+		assign TranslationPAdr = {PPN, VPN, 2'b00}; 
+	  end else begin // RV64
+		logic [8:0] VPN;
+		logic [`PPN_BITS-1:0] PPN;
 		always_comb
-		  case (WalkerState)
-	    	LEVEL1_SET_ADR:  TranslationPAdr = {BasePageTablePPN, VPN1, 2'b00};
-	    	LEVEL1_READ:      TranslationPAdr = {BasePageTablePPN, VPN1, 2'b00};
-			LEVEL1:          if (NextWalkerState == LEAF) TranslationPAdr = {2'b00, TranslationVAdr[31:0]}; // ***check this and similar in LEVEL0 and LEAF
-			                 else TranslationPAdr = {CurrentPPN, VPN0, 2'b00};
-			LEVEL0_SET_ADR:  TranslationPAdr = {CurrentPPN, VPN0, 2'b00};
-			LEVEL0_READ: 	 TranslationPAdr = {CurrentPPN, VPN0, 2'b00};
-			LEVEL0: 		 TranslationPAdr = {2'b00, TranslationVAdr[31:0]};
-			LEAF:			 TranslationPAdr = {2'b00, TranslationVAdr[31:0]};
-			default:		 TranslationPAdr = 0; // cause seg fault if this is improperly used
-		  endcase
-	  end else begin
-		logic [8:0] VPN3, VPN2, VPN1, VPN0;
-		assign VPN3 = TranslationVAdr[47:39];
-		assign VPN2 = TranslationVAdr[38:30];
-		assign VPN1 = TranslationVAdr[29:21];
-		assign VPN0 = TranslationVAdr[20:12];
-		always_comb
-		  case (WalkerState)
-			LEVEL3_SET_ADR:  TranslationPAdr = {BasePageTablePPN, VPN3, 3'b000};
-	    	LEVEL3_READ:  	 TranslationPAdr = {BasePageTablePPN, VPN3, 3'b000};
-	    	LEVEL3:          if (NextWalkerState == LEAF) TranslationPAdr = TranslationVAdr[`PA_BITS-1:0];
-			                 else TranslationPAdr = {(SvMode == `SV48) ? CurrentPPN : BasePageTablePPN, VPN2, 3'b000};
-			LEVEL2_SET_ADR:  TranslationPAdr = {(SvMode == `SV48) ? CurrentPPN : BasePageTablePPN, VPN2, 3'b000};
-			LEVEL2_READ:  	 TranslationPAdr = {(SvMode == `SV48) ? CurrentPPN : BasePageTablePPN, VPN2, 3'b000};
-	   		LEVEL2: 		 if (NextWalkerState == LEAF) TranslationPAdr = TranslationVAdr[`PA_BITS-1:0];
-			                 else TranslationPAdr = {CurrentPPN, VPN1, 3'b000};
-	      	LEVEL1_SET_ADR:  TranslationPAdr = {CurrentPPN, VPN1, 3'b000};
-			LEVEL1_READ: 	 TranslationPAdr = {CurrentPPN, VPN1, 3'b000};
-	     	LEVEL1: 		 if (NextWalkerState == LEAF) TranslationPAdr = TranslationVAdr[`PA_BITS-1:0];
-			                 else TranslationPAdr = {CurrentPPN, VPN0, 3'b000};
-	    	LEVEL0_SET_ADR:  TranslationPAdr = {CurrentPPN, VPN0, 3'b000};
-			LEVEL0_READ: 	 TranslationPAdr = {CurrentPPN, VPN0, 3'b000};
-	  		LEVEL0: 		 TranslationPAdr = TranslationVAdr[`PA_BITS-1:0];
-			LEAF:			 TranslationPAdr = TranslationVAdr[`PA_BITS-1:0];
-			default: 		 TranslationPAdr = 0; // cause seg fault if this is improperly used
-		  endcase 
+			case (WalkerState) // select VPN field based on HPTW state
+				LEVEL3_SET_ADR:  VPN = TranslationVAdr[47:39];
+				LEVEL3_READ:  	 VPN = TranslationVAdr[47:39];
+				LEVEL3:          VPN = TranslationVAdr[38:30];
+				LEVEL2_SET_ADR:  VPN = TranslationVAdr[38:30];
+				LEVEL2_READ:  	 VPN = TranslationVAdr[38:30];
+				LEVEL2: 		 VPN = TranslationVAdr[29:21];
+				LEVEL1_SET_ADR:  VPN = TranslationVAdr[29:21];
+				LEVEL1_READ: 	 VPN = TranslationVAdr[29:21];
+				default:		 VPN = TranslationVAdr[20:12];
+			endcase
+		assign PPN = ((WalkerState == LEVEL3_SET_ADR) | (WalkerState == LEVEL3_READ) | 
+		              (SvMode != `SV48 & ((WalkerState == LEVEL2_SET_ADR) | (WalkerState == LEVEL2_READ)))) ? BasePageTablePPN : CurrentPPN;
+		assign TranslationPAdr = {PPN, VPN, 3'b000}; 
 	  end
 
 	  if (`XLEN == 32) begin
@@ -186,17 +151,18 @@ module pagetablewalker
 		assign TerapageMisaligned = 0; // not applicable
 		assign GigapageMisaligned = 0; // not applicable
 		assign MegapageMisaligned = |(CurrentPPN[9:0]); // must have zero PPN0
-		assign HPTWPAdrE = TranslationPAdr[31:0]; // ***not right?
 	  end else begin
 		assign InitialWalkerState = (SvMode == `SV48) ? LEVEL3_SET_ADR : LEVEL2_SET_ADR;
 		assign TerapageMisaligned = |(CurrentPPN[26:0]); // must have zero PPN2, PPN1, PPN0
 		assign GigapageMisaligned = |(CurrentPPN[17:0]); // must have zero PPN1 and PPN0
 		assign MegapageMisaligned = |(CurrentPPN[8:0]); // must have zero PPN0		  
-		assign HPTWPAdrE = {{(`XLEN-`PA_BITS){1'b0}}, TranslationPAdr[`PA_BITS-1:0]};
  	  end
 
     // Page Table Walker FSM
-	// ***Is there a w ay to reduce the number of cycles needed to do the walk?
+	// If the setup time on the D$ RAM is short, it should be possible to merge the LEVELx_READ and LEVELx states
+	// to decrease the latency of the HPTW.  However, if the D$ is a cycle limiter, it's better to leave the
+	// HPTW as shown below to keep the D$ setup time out of the critical path.
+	flopenl #(.TYPE(statetype)) WalkerStateReg(clk, reset, 1'b1, NextWalkerState, IDLE, WalkerState); 
 	always_comb 
 	  case (WalkerState)
 	    IDLE: if (StartWalk) 		NextWalkerState = InitialWalkerState;
@@ -231,14 +197,10 @@ module pagetablewalker
 									NextWalkerState = IDLE; // should never be reached
 		end
 	  endcase
-    end else begin
-      assign HPTWPAdrE = 0;
-      assign HPTWRead = 0;
-      assign WalkerInstrPageFaultF = 0;
-      assign WalkerLoadPageFaultM = 0;
-      assign WalkerStorePageFaultM = 0;
-      assign SelPTW = 0;
+    end else begin // No Virtual memory supported; tie HPTW outputs to 0
+      assign HPTWRead = 0; assign SelPTW = 0;
+      assign WalkerInstrPageFaultF = 0; assign WalkerLoadPageFaultM = 0; assign WalkerStorePageFaultM = 0;
+	  assign TranslationVAdr = 0; assign TranslationPAdr = 0; assign UseTranslationVAdr = 0;
     end
   endgenerate
-
 endmodule