Ver código fonte

git-svn-id: https://svn.inf.ethz.ch/svn/lecturers/a2/trunk@8195 8c9fc860-2736-0410-a75d-ab315db34111

negelef 7 anos atrás
pai
commit
7a785892fd
2 arquivos alterados com 265 adições e 218 exclusões
  1. 0 218
      source/I386.MemCache.Mod
  2. 265 0
      source/I386.MemInfo.Mod

+ 0 - 218
source/I386.MemCache.Mod

@@ -1,218 +0,0 @@
-(* Aos, Copyright 2001, Pieter Muller, ETH Zurich *)
-
-MODULE MemCache; (** AUTHOR "pjm"; PURPOSE "Memory cache control"; *)
-
-IMPORT SYSTEM, Machine;
-
-CONST
-		(** cache properties *)
-	UC* = 0; WC* = 1; WT* = 4; WP* = 5; WB* = 6;
-
-	PS = 4096;	(* page size in bytes *)
-	M = 100000H;	(* 1K, 1M, 1G *)
-
-	Ok = 0;
-
-TYPE
-	SetCacheMessage = POINTER TO RECORD (Machine.Message)
-		physAdr: ADDRESS; size, type: LONGINT;
-		res: ARRAY Machine.MaxCPU OF LONGINT
-	END;
-
-(* Return the value of the MTTRcap register. *)
-
-PROCEDURE -GetMTTRcapLow(): SET;
-CODE {SYSTEM.Pentium, SYSTEM.Privileged}
-	MOV ECX, 0FEH	; MTTRcap
-	RDMSR
-END GetMTTRcapLow;
-
-(*
-(* Return the value of the MTTRdefType register. *)
-
-PROCEDURE -GetMTTRdefTypeLow(): SET;
-CODE {SYSTEM.Pentium, SYSTEM.Privileged}
-	MOV ECX, 2FFH	; MTTRdefType
-	RDMSR
-END GetMTTRdefTypeLow;
-*)
-
-(* Return the value of the specified MTTRphysBase register. *)
-
-PROCEDURE -GetMTTRphysBaseLow(n: ADDRESS): SET;
-CODE {SYSTEM.Pentium, SYSTEM.Privileged}
-	POP ECX
-	SHL ECX, 1
-	ADD ECX, 200H	; MTTRphysBase0
-	RDMSR
-END GetMTTRphysBaseLow;
-
-(* Return the value of the specified MTTRphysMask register. *)
-
-PROCEDURE -GetMTTRphysMaskLow(n: ADDRESS): SET;
-CODE {SYSTEM.Pentium, SYSTEM.Privileged}
-	POP ECX
-	SHL ECX, 1
-	ADD ECX, 201H	; MTTRphysMask0
-	RDMSR
-END GetMTTRphysMaskLow;
-
-(* Set the specified MTTRphysBase register. *)
-
-PROCEDURE -SetMTTRphysBase(n: ADDRESS; high, low: SET);
-CODE {SYSTEM.Pentium, SYSTEM.Privileged}
-	POP EAX
-	POP EDX
-	POP ECX
-	SHL ECX, 1
-	ADD ECX, 200H	; MTTRphysBase0
-	WRMSR
-END SetMTTRphysBase;
-
-(* Set the specified MTTRphysMask register. *)
-
-PROCEDURE -SetMTTRphysMask(n: ADDRESS; high, low: SET);
-CODE {SYSTEM.Pentium, SYSTEM.Privileged}
-	POP EAX
-	POP EDX
-	POP ECX
-	SHL ECX, 1
-	ADD ECX, 201H	; MTTRphysMask0
-	WRMSR
-END SetMTTRphysMask;
-
-(** Set the cache properties of the specified physical memory area on the current processor. {physAdr, size MOD PS = 0}  Must be called from supervisor mode. *)
-
-PROCEDURE LocalSetCacheProperties*(physAdr: ADDRESS; size, type: LONGINT; VAR res: LONGINT);
-VAR i, n, f: LONGINT; mask, base: SET; j, k: ADDRESS;
-BEGIN
-	ASSERT((physAdr MOD PS = 0) & (size MOD PS = 0) & (size # 0));
-	IF (physAdr >= M) OR (physAdr < 0) THEN
-		k := size; WHILE k > 0 DO k := ASH(k, 1) END;	(* shift highest set bit into bit 31 *)
-		IF k = 80000000H THEN	(* only one bit was set => size is power of 2 *)
-			IF physAdr MOD size = 0 THEN
-				Machine.Acquire(Machine.Memory);	(* hack *)
-				IF Machine.MTTR IN Machine.features THEN	(* MTTRs supported *)
-					mask := GetMTTRcapLow();
-					IF (type # WC) OR (10 IN mask) THEN
-						n := SYSTEM.VAL(LONGINT, mask * {0..7});
-						i := 0; f := -1; res := Ok;
-						WHILE (i # n) & (res = Ok) DO
-							mask := GetMTTRphysMaskLow(i);
-							IF 11 IN mask THEN	(* entry is valid *)
-								mask := mask * {12..MAX(SET)};
-								base := GetMTTRphysBaseLow(i) * mask;
-								j := physAdr; k := physAdr+size;
-								WHILE (j # k) & (SYSTEM.VAL(SET, j) * mask # base) DO INC(j, PS) END;	(* performance! *)
-								IF j # k THEN res := 1508 END	(* cache type of region already set *)
-							ELSE
-								IF f = -1 THEN f := i END	(* first free entry *)
-							END;
-							INC(i)
-						END;
-						IF res = Ok THEN
-							IF f # -1 THEN
-								SetMTTRphysBase(f, {}, SYSTEM.VAL(SET, physAdr) * {12..31} + SYSTEM.VAL(SET, type) * {0..7});
-								SetMTTRphysMask(f, {0..3}, (-SYSTEM.VAL(SET, size-1)) * {12..31} + {11})
-							ELSE
-								res := 1506	(* out of cache control entries *)
-							END
-						ELSE
-							(* skip *)
-						END
-					ELSE
-						res := 1511	(* region type not supported *)
-					END
-				ELSE
-					res := 1505	(* MTTRs not supported *)
-				END;
-				Machine.Release(Machine.Memory)
-			ELSE
-				res := 1510	(* region base must be aligned on size *)
-			END
-		ELSE
-			res := 1509	(* region size must be power of 2 *)
-		END
-	ELSE
-		res := 1507	(* implementation restriction - fixed entries not supported *)
-	END
-END LocalSetCacheProperties;
-
-PROCEDURE HandleSetCacheProperties(id: LONGINT; CONST state: Machine.State; msg: Machine.Message);
-BEGIN
-	WITH msg: SetCacheMessage DO
-		(* to do: page 11-25 *)
-		LocalSetCacheProperties(msg.physAdr, msg.size, msg.type, msg.res[id])
-	END
-END HandleSetCacheProperties;
-
-(** Broadcast a LocalSetCacheProperties operation to all processors. *)
-
-PROCEDURE GlobalSetCacheProperties*(physAdr: ADDRESS; size, type: LONGINT; VAR res: LONGINT);
-VAR i: LONGINT; msg: SetCacheMessage;
-BEGIN
-	NEW(msg); msg.physAdr := physAdr; msg.size := size; msg.type := type;
-	FOR i := 0 TO Machine.MaxCPU-1 DO msg.res[i] := 2304 END;	(* default result *)
-	Machine.Broadcast(HandleSetCacheProperties, msg, {Machine.Self, Machine.FrontBarrier, Machine.BackBarrier});
-	res := 0;
-	FOR i := 0 TO Machine.MaxCPU-1 DO
-		IF (res = 0) & (msg.res[i] # 0) THEN res := msg.res[i] END	(* return first non-ok result found *)
-	END
-END GlobalSetCacheProperties;
-
-(** Disable all caching on the current processor. *)
-
-PROCEDURE LocalDisableCaching*;
-CODE {SYSTEM.Pentium, SYSTEM.Privileged}
-	PUSHFD
-	CLI
-
-	MOV EAX, CR0
-	OR EAX, 40000000H
-	AND EAX, 0DFFFFFFFH
-	MOV CR0, EAX
-
-	WBINVD
-
-	MOV EAX, CR4
-	AND EAX, 0FFFFFF7FH
-	MOV CR4, EAX
-
-	MOV EAX, CR3
-	MOV CR3, EAX
-
-	MOV ECX, 2FFH	; MTTRdefType
-	MOV EAX, 0
-	MOV EDX, 0
-	WRMSR
-
-	WBINVD
-
-	MOV EAX, CR3
-	MOV CR3, EAX
-
-	MOV EAX, CR0
-	OR EAX, 60000000H
-	MOV CR0, EAX
-
-	POPFD
-END LocalDisableCaching;
-
-PROCEDURE HandleDisableCaching(id: LONGINT; CONST state: Machine.State; msg: Machine.Message);
-BEGIN
-	LocalDisableCaching
-END HandleDisableCaching;
-
-(** Broadcast a LocalDisableCaching operation to all processors. *)
-
-PROCEDURE GlobalDisableCaching*;
-BEGIN
-	Machine.Broadcast(HandleDisableCaching, NIL, {Machine.Self, Machine.FrontBarrier, Machine.BackBarrier})
-END GlobalDisableCaching;
-
-END MemCache.
-
-(*
-to do:
-o change error codes
-*)

+ 265 - 0
source/I386.MemInfo.Mod

@@ -0,0 +1,265 @@
+(* Aos, Copyright 2001, Pieter Muller, ETH Zurich *)
+
+MODULE MemInfo; (** AUTHOR "pjm"; PURPOSE "Memory mapping information"; *)
+
+IMPORT SYSTEM, KernelLog, Machine;
+
+CONST
+	SoftInt = Machine.SoftInt;
+
+		(* standard multipliers *)
+	K = 1024;  M = 100000H;	(* 1K, 1M *)
+
+	PS = 4096;
+	RS = 4*M;	(* region covered by a page table in bytes *)
+	PTEs = RS DIV PS;	(* number of page table/directory entries *)
+
+VAR
+	kernelPD: ADDRESS;
+	msrlow, msrhigh: SET;
+
+PROCEDURE GetCR3(VAR state: Machine.State);
+CODE {SYSTEM.i386, SYSTEM.Privileged}
+	MOV EAX, CR3
+	MOV kernelPD, EAX
+END GetCR3;
+
+PROCEDURE -DoSoftInt(eax: LONGINT);
+CODE {SYSTEM.i386}
+	POP EAX
+	INT SoftInt
+END DoSoftInt;
+
+(* Display mapped ranges. *)
+
+PROCEDURE DisplayMap*;
+VAR i, j: LONGINT; pt: LONGINT; virt, phys, virt0, phys0, size: LONGINT;
+
+	PROCEDURE Page;
+	BEGIN
+		IF (phys = phys0+size) & (virt = virt0+size) THEN
+			INC(size, PS)
+		ELSE
+			IF size # 0 THEN
+				KernelLog.Hex(virt0, 9); KernelLog.Hex(phys0, 9);
+				KernelLog.IntSuffix(size, 8, "B"); KernelLog.Ln
+			END;
+			virt0 := virt;  phys0 := phys;  size := PS
+		END
+	END Page;
+
+BEGIN
+	Machine.InstallHandler(GetCR3, SoftInt);	(* ignore race *)
+	DoSoftInt(0);
+	Machine.RemoveHandler(GetCR3, SoftInt);
+	KernelLog.Enter; KernelLog.Char(0EX); KernelLog.Ln;
+	KernelLog.String(" Virtual  Physical Size");  KernelLog.Ln;
+	virt := 0;  virt0 := 0;  phys0 := 0;  size := 0;
+	FOR i := 0 TO PTEs-1 DO
+		SYSTEM.GET(kernelPD + SIZEOF(ADDRESS)*i, pt);
+		IF ODD(pt) THEN	(* present *)
+			pt := pt - pt MOD PS;
+			FOR j := 0 TO PTEs-1 DO
+				SYSTEM.GET(pt, phys);
+				IF ODD(phys) THEN
+					DEC(phys, phys MOD PS);
+					Page
+				END;
+				INC(pt, 4);  INC(virt, 4*K)
+			END
+		ELSE
+			INC(virt, 4*M)
+		END
+	END;
+	virt := -1;  Page;
+	KernelLog.Char(0FX); KernelLog.Exit;
+END DisplayMap;
+
+PROCEDURE Write64(s: ARRAY OF CHAR; low, high: SET);
+BEGIN
+	KernelLog.String(s);  KernelLog.Char("=");
+	KernelLog.Hex(SYSTEM.VAL(LONGINT, high), 8);
+	KernelLog.Hex(SYSTEM.VAL(LONGINT, low), 9)
+END Write64;
+
+PROCEDURE Bits(s: ARRAY OF CHAR; x: SET; ofs, n: LONGINT);
+BEGIN
+	KernelLog.String(s); KernelLog.Char("="); KernelLog.Bits(x, ofs, n)
+END Bits;
+
+PROCEDURE -RealReadMSR(msr: LONGINT; VAR low, high: SET);
+CODE {SYSTEM.Pentium, SYSTEM.Privileged}
+	POP EDI
+	POP ESI
+	POP ECX
+	RDMSR
+	MOV [ESI], EAX
+	MOV [EDI], EDX
+END RealReadMSR;
+
+PROCEDURE IntReadMSR(VAR state: Machine.State);
+BEGIN
+	RealReadMSR(state.EAX, msrlow, msrhigh)
+END IntReadMSR;
+
+PROCEDURE ReadMSR(msr: LONGINT; VAR low, high: SET);
+BEGIN
+	Machine.InstallHandler(IntReadMSR, SoftInt);	(* ignore race *)
+	DoSoftInt(msr);
+	Machine.RemoveHandler(IntReadMSR, SoftInt);
+	low := msrlow; high := msrhigh
+END ReadMSR;
+
+PROCEDURE DisplayMTTR*;
+VAR version, i, j, k, vcnt: LONGINT; features, low, high, mask: SET; vendor: Machine.Vendor;
+BEGIN
+	KernelLog.Enter;
+(*	Machine.CPUID(vendor, version, features);
+	KernelLog.String("CPU: ");  KernelLog.Int(ASH(version, -8) MOD 16, 1);
+	KernelLog.Char(".");  KernelLog.Int(ASH(version, -4) MOD 16, 1);
+	KernelLog.Char(".");  KernelLog.Int(version MOD 16, 1);
+	Bits(", features", features, 0, 32);
+	KernelLog.String(", vendor ");  KernelLog.String(vendor);
+	KernelLog.Ln; *)
+	features := Machine.features;
+	IF 5 IN features THEN	(* MSR supported *)
+		IF 12 IN features THEN	(* MTTR supported *)
+			ReadMSR(0FEH, low, high);
+			vcnt := SYSTEM.VAL(LONGINT, low) MOD 256;
+			KernelLog.String("VCNT="); KernelLog.Int(vcnt, 1);
+			Bits(", FIX", low, 8, 1); Bits(", WC", low, 10, 1);
+			KernelLog.Ln;
+			IF 8 IN low THEN
+				ReadMSR(2FFH, low, high);  Write64("DefType", low, high);  KernelLog.Ln;
+				ReadMSR(250H, low, high);  Write64("Fix64k", low, high);  KernelLog.Ln;
+				ReadMSR(258H, low, high);  Write64("Fix16k", low, high);  KernelLog.Ln;
+				ReadMSR(259H, low, high);  Write64("Fix16k", low, high);  KernelLog.Ln;
+				ReadMSR(268H, low, high);  Write64("Fix4k", low, high);  KernelLog.Ln;
+				ReadMSR(269H, low, high);  Write64("Fix4k", low, high);  KernelLog.Ln;
+				ReadMSR(26AH, low, high);  Write64("Fix4k", low, high);  KernelLog.Ln;
+				ReadMSR(26BH, low, high);  Write64("Fix4k", low, high);  KernelLog.Ln;
+				ReadMSR(26CH, low, high);  Write64("Fix4k", low, high);  KernelLog.Ln;
+				ReadMSR(26DH, low, high);  Write64("Fix4k", low, high);  KernelLog.Ln;
+				ReadMSR(26EH, low, high);  Write64("Fix4k", low, high);  KernelLog.Ln;
+				ReadMSR(26FH, low, high);  Write64("Fix4k", low, high);  KernelLog.Ln;
+				FOR i := 0 TO vcnt-1 DO
+					KernelLog.Int(i, 1);
+					ReadMSR(200H+2*i, low, high);  Write64(" base", low, high);
+					ReadMSR(200H+2*i+1, low, high);  Write64(", mask", low, high);
+					IF 11 IN low THEN	(* valid *)
+						mask := LSH(low, -12);
+						FOR j := 0 TO 3 DO
+							IF j IN high THEN INCL(mask, 20+j) END
+						END;
+						j := 0;  WHILE (j # 32) & ~(j IN mask) DO INC(j) END;
+						k := 31;  WHILE (k # -1) & ~(k IN mask) DO DEC(k) END;
+						IF (k = 23) & (k >= j) & (mask = {j..k}) THEN
+							KernelLog.String(", ");  KernelLog.IntSuffix(SYSTEM.VAL(LONGINT, {j})*4*1024, 1, "B")
+						ELSE
+							KernelLog.String(" discon=");  KernelLog.Hex(SYSTEM.VAL(LONGINT, mask), 8)
+						END
+					END;
+					KernelLog.Ln
+				END
+			ELSE
+				KernelLog.String("Fixed range registers not supported");  KernelLog.Ln
+			END
+		ELSE
+			KernelLog.String("MTTR not supported");  KernelLog.Ln
+		END
+	ELSE
+		KernelLog.String("MSR not supported");  KernelLog.Ln
+	END;
+	KernelLog.Exit;
+END DisplayMTTR;
+
+(*
+PROCEDURE IntSetCache(VAR state: Machine.State);
+VAR res: LONGINT;
+BEGIN
+	Machine.SetLocalCacheProperties(0FA800000H, 800000H, Machine.WC, res);
+	KernelLog.Enter; KernelLog.String("SetCache "); KernelLog.Int(res, 1); KernelLog.Exit
+END IntSetCache;
+
+PROCEDURE Test*;
+BEGIN
+	Machine.InstallHandler(IntSetCache, SoftInt);	(* ignore race *)
+	DoSoftInt(0);
+	Machine.RemoveHandler(IntSetCache, SoftInt)
+END Test;
+
+PROCEDURE -SetMTTRphysBase(n: LONGINT; high, low: LONGINT);
+CODE {SYSTEM.Pentium, SYSTEM.Privileged}
+	POP EAX
+	POP EDX
+	POP ECX
+	SHL ECX, 1
+	ADD ECX, 200H	; MTTRphysBase0
+	WRMSR
+END SetMTTRphysBase;
+
+PROCEDURE -SetMTTRphysMask(n: LONGINT; high, low: LONGINT);
+CODE {SYSTEM.Pentium, SYSTEM.Privileged}
+	POP EAX
+	POP EDX
+	POP ECX
+	SHL ECX, 1
+	ADD ECX, 201H	; MTTRphysMask0
+	WRMSR
+END SetMTTRphysMask;
+
+(*
+1 000000000H 4GB WB
+0 0F0000000H 128MB UC
+4 0F8000000H 64MB UC
+- 0FC000000H 32MB WB (implicit)
+3 0FE000000H 32MB UC
+2 100000000H 256MB WB
+
+WB 0MB-2048MB 2048MB
+WB 2048MB-3072MB 1024MB
+WB 3072MB-3584MB 512MB
+WB 3584MB-3840MB 256MB
+WC 4032MB-4064MB 32MB
+WB 4096MB-4352MB 256MB
+*)
+
+PROCEDURE IntSetCache2(VAR state: Machine.State);
+BEGIN
+	SetMTTRphysBase(3, 0, 0FE000000H);
+	SetMTTRphysMask(3, 0FH, 0FE000800H);
+	SetMTTRphysBase(4, 0, 0F8000000H);
+	SetMTTRphysMask(4, 0FH, 0FC000800H);
+	SetMTTRphysBase(0, 0, 0F0000000H);
+	SetMTTRphysMask(0, 0FH, 0F8000800H)
+END IntSetCache2;
+
+PROCEDURE Test2*;
+BEGIN
+	Machine.InstallHandler(IntSetCache2, SoftInt);	(* ignore race *)
+	DoSoftInt(0);
+	Machine.RemoveHandler(IntSetCache2, SoftInt)
+END Test2;
+
+PROCEDURE Test3*;
+VAR res: LONGINT;
+BEGIN
+	Processors.GlobalSetCacheProperties(0FA800000H, 800000H, Machine.WC, res);
+	KernelLog.Enter; KernelLog.String("SetCache "); KernelLog.Int(res, 1); KernelLog.Exit
+END Test3;
+*)
+
+END MemInfo.
+
+System.Free MemInfo ~
+
+MemInfo.DisplayMap
+MemInfo.DisplayMTTR
+
+MemInfo.Test
+MemInfo.Test2
+MemInfo.Test3
+
+DisplayTests.Mod
+
+PCITools.Scan