BIOS.AMD64.MemCache.Mod 5.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221
  1. (* Aos, Copyright 2001, Pieter Muller, ETH Zurich *)
  2. MODULE MemCache; (** AUTHOR "pjm"; PURPOSE "Memory cache control"; *)
  3. IMPORT SYSTEM, Machine;
  4. CONST
  5. (** cache properties *)
  6. UC* = 0; WC* = 1; WT* = 4; WP* = 5; WB* = 6;
  7. PS = 4096; (* page size in bytes *)
  8. M = 100000H; (* 1K, 1M, 1G *)
  9. Ok = 0;
  10. TYPE
  11. SetCacheMessage = POINTER TO RECORD (Machine.Message)
  12. physAdr: ADDRESS; size, type: LONGINT;
  13. res: ARRAY Machine.MaxCPU OF LONGINT
  14. END;
  15. (* Return the value of the MTTRcap register. *)
  16. PROCEDURE -GetMTTRcapLow(): SET;
  17. CODE {SYSTEM.AMD64, SYSTEM.Privileged}
  18. MOV ECX, 0FEH ; MTTRcap
  19. RDMSR
  20. END GetMTTRcapLow;
  21. (*
  22. (* Return the value of the MTTRdefType register. *)
  23. PROCEDURE -GetMTTRdefTypeLow(): SET;
  24. CODE {SYSTEM.AMD64, SYSTEM.Privileged}
  25. XOR RAX, RAX
  26. MOV ECX, 2FFH ; MTTRdefType
  27. RDMSR
  28. END GetMTTRdefTypeLow;
  29. *)
  30. (* Return the value of the specified MTTRphysBase register. *)
  31. PROCEDURE -GetMTTRphysBaseLow(n: ADDRESS): SET;
  32. CODE {SYSTEM.AMD64, SYSTEM.Privileged}
  33. XOR RAX, RAX
  34. POP RCX
  35. SHL RCX, 1
  36. ADD RCX, 200H ; MTTRphysBase0
  37. RDMSR
  38. END GetMTTRphysBaseLow;
  39. (* Return the value of the specified MTTRphysMask register. *)
  40. PROCEDURE -GetMTTRphysMaskLow(n: ADDRESS): SET;
  41. CODE {SYSTEM.AMD64, SYSTEM.Privileged}
  42. XOR RAX, RAX
  43. POP RCX
  44. SHL RCX, 1
  45. ADD RCX, 201H ; MTTRphysMask0
  46. RDMSR
  47. END GetMTTRphysMaskLow;
  48. (* Set the specified MTTRphysBase register. *)
  49. PROCEDURE -SetMTTRphysBase(n: ADDRESS; high, low: SET);
  50. CODE {SYSTEM.AMD64, SYSTEM.Privileged}
  51. POP RAX
  52. POP RDX
  53. POP RCX
  54. SHL RCX, 1
  55. ADD RCX, 200H ; MTTRphysBase0
  56. WRMSR
  57. END SetMTTRphysBase;
  58. (* Set the specified MTTRphysMask register. *)
  59. PROCEDURE -SetMTTRphysMask(n: ADDRESS; high, low: SET);
  60. CODE {SYSTEM.AMD64, SYSTEM.Privileged}
  61. POP RAX
  62. POP RDX
  63. POP RCX
  64. SHL RCX, 1
  65. ADD RCX, 201H ; MTTRphysMask0
  66. WRMSR
  67. END SetMTTRphysMask;
  68. (** 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. *)
  69. PROCEDURE LocalSetCacheProperties*(physAdr: ADDRESS; size, type: LONGINT; VAR res: WORD);
  70. VAR i, n, f: LONGINT; mask, base: SET; j, k: ADDRESS;
  71. BEGIN
  72. ASSERT((physAdr MOD PS = 0) & (size MOD PS = 0) & (size # 0));
  73. IF (physAdr >= M) OR (physAdr < 0) THEN
  74. k := size; WHILE k > 0 DO k := ASH(k, 1) END; (* shift highest set bit into bit 31 *)
  75. IF k = 80000000H THEN (* only one bit was set => size is power of 2 *)
  76. IF physAdr MOD size = 0 THEN
  77. Machine.Acquire(Machine.Memory); (* hack *)
  78. IF Machine.MTTR IN Machine.features THEN (* MTTRs supported *)
  79. mask := GetMTTRcapLow();
  80. IF (type # WC) OR (10 IN mask) THEN
  81. n := SYSTEM.VAL(LONGINT, mask * {0..7});
  82. i := 0; f := -1; res := Ok;
  83. WHILE (i # n) & (res = Ok) DO
  84. mask := GetMTTRphysMaskLow(i);
  85. IF 11 IN mask THEN (* entry is valid *)
  86. mask := mask * {12..MAX(SET)};
  87. base := GetMTTRphysBaseLow(i) * mask;
  88. j := physAdr; k := physAdr+size;
  89. WHILE (j # k) & (SYSTEM.VAL(SET, j) * mask # base) DO INC(j, PS) END; (* performance! *)
  90. IF j # k THEN res := 1508 END (* cache type of region already set *)
  91. ELSE
  92. IF f = -1 THEN f := i END (* first free entry *)
  93. END;
  94. INC(i)
  95. END;
  96. IF res = Ok THEN
  97. IF f # -1 THEN
  98. SetMTTRphysBase(f, {}, SYSTEM.VAL(SET, physAdr) * {12..31} + SYSTEM.VAL(SET, type) * {0..7});
  99. SetMTTRphysMask(f, {0..3}, (-SYSTEM.VAL(SET, size-1)) * {12..31} + {11})
  100. ELSE
  101. res := 1506 (* out of cache control entries *)
  102. END
  103. ELSE
  104. (* skip *)
  105. END
  106. ELSE
  107. res := 1511 (* region type not supported *)
  108. END
  109. ELSE
  110. res := 1505 (* MTTRs not supported *)
  111. END;
  112. Machine.Release(Machine.Memory)
  113. ELSE
  114. res := 1510 (* region base must be aligned on size *)
  115. END
  116. ELSE
  117. res := 1509 (* region size must be power of 2 *)
  118. END
  119. ELSE
  120. res := 1507 (* implementation restriction - fixed entries not supported *)
  121. END
  122. END LocalSetCacheProperties;
  123. PROCEDURE HandleSetCacheProperties(id: LONGINT; CONST state: Machine.State; msg: Machine.Message);
  124. BEGIN
  125. WITH msg: SetCacheMessage DO
  126. (* to do: page 11-25 *)
  127. LocalSetCacheProperties(msg.physAdr, msg.size, msg.type, msg.res[id])
  128. END
  129. END HandleSetCacheProperties;
  130. (** Broadcast a LocalSetCacheProperties operation to all processors. *)
  131. PROCEDURE GlobalSetCacheProperties*(physAdr: ADDRESS; size, type: LONGINT; VAR res: WORD);
  132. VAR i: LONGINT; msg: SetCacheMessage;
  133. BEGIN
  134. NEW(msg); msg.physAdr := physAdr; msg.size := size; msg.type := type;
  135. FOR i := 0 TO Machine.MaxCPU-1 DO msg.res[i] := 2304 END; (* default result *)
  136. Machine.Broadcast(HandleSetCacheProperties, msg, {Machine.Self, Machine.FrontBarrier, Machine.BackBarrier});
  137. res := 0;
  138. FOR i := 0 TO Machine.MaxCPU-1 DO
  139. IF (res = 0) & (msg.res[i] # 0) THEN res := msg.res[i] END (* return first non-ok result found *)
  140. END
  141. END GlobalSetCacheProperties;
  142. (** Disable all caching on the current processor. *)
  143. PROCEDURE LocalDisableCaching*;
  144. CODE {SYSTEM.Pentium, SYSTEM.Privileged}
  145. PUSHFD
  146. CLI
  147. MOV EAX, CR0
  148. OR EAX, 40000000H
  149. AND EAX, 0DFFFFFFFH
  150. MOV CR0, EAX
  151. WBINVD
  152. MOV EAX, CR4
  153. AND EAX, 0FFFFFF7FH
  154. MOV CR4, EAX
  155. MOV EAX, CR3
  156. MOV CR3, EAX
  157. MOV ECX, 2FFH ; MTTRdefType
  158. MOV EAX, 0
  159. MOV EDX, 0
  160. WRMSR
  161. WBINVD
  162. MOV EAX, CR3
  163. MOV CR3, EAX
  164. MOV EAX, CR0
  165. OR EAX, 60000000H
  166. MOV CR0, EAX
  167. POPFD
  168. END LocalDisableCaching;
  169. PROCEDURE HandleDisableCaching(id: LONGINT; CONST state: Machine.State; msg: Machine.Message);
  170. BEGIN
  171. LocalDisableCaching
  172. END HandleDisableCaching;
  173. (** Broadcast a LocalDisableCaching operation to all processors. *)
  174. PROCEDURE GlobalDisableCaching*;
  175. BEGIN
  176. Machine.Broadcast(HandleDisableCaching, NIL, {Machine.Self, Machine.FrontBarrier, Machine.BackBarrier})
  177. END GlobalDisableCaching;
  178. END MemCache.
  179. (*
  180. to do:
  181. o change error codes
  182. *)