3 Display the memory type range registers
5 Copyright (c) 2012, Intel Corporation
6 All rights reserved. This program and the accompanying materials
7 are licensed and made available under the terms and conditions of the BSD License
8 which accompanies this distribution. The full text of the license may be found at
9 http://opensource.org/licenses/bsd-license.php
11 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
16 #include <WebServer.h>
17 #include <Library/MtrrLib.h>
19 #define VARIABLE_MTRR_VALID 0x800
21 CONST
char * mMemoryType
[ ] = {
33 Display a fixed MTRR row
35 @param [in] SocketFD The socket's file descriptor to add to the list.
36 @param [in] pPort The WSDT_PORT structure address
37 @param [in] Start Start address for the region
38 @param [in] End End address for the region
39 @param [in] Type Memory type
41 @retval EFI_SUCCESS The request was successfully processed
56 // Use break instead of goto
62 Status
= HttpSendAnsiString ( SocketFD
,
64 " <tr><td align=\"right\"><code>0x" );
65 if ( EFI_ERROR ( Status
)) {
72 Status
= HttpSendHexValue ( SocketFD
,
75 if ( EFI_ERROR ( Status
)) {
82 Status
= HttpSendAnsiString ( SocketFD
,
84 "</code></td><td align=\"right\"><code>0x" );
85 if ( EFI_ERROR ( Status
)) {
88 Status
= HttpSendHexValue ( SocketFD
,
91 if ( EFI_ERROR ( Status
)) {
98 Status
= HttpSendAnsiString ( SocketFD
,
100 "</code></td><td>" );
101 if ( EFI_ERROR ( Status
)) {
105 Status
= HttpSendAnsiString ( SocketFD
,
107 ( DIM ( mMemoryType
) > Type
)
108 ? mMemoryType
[ Type
]
110 if ( EFI_ERROR ( Status
)) {
117 Status
= HttpSendAnsiString ( SocketFD
,
124 // Return the final status
131 Display the memory type registers
133 @param [in] SocketFD The socket's file descriptor to add to the list.
134 @param [in] pPort The WSDT_PORT structure address
135 @param [out] pbDone Address to receive the request completion status
137 @retval EFI_SUCCESS The request was successfully processed
141 MemoryTypeRegistersPage (
143 IN WSDT_PORT
* pPort
,
155 CONST UINT64 mFixedAddresses
[( 8 * MTRR_NUMBER_OF_FIXED_MTRR
) + 1 ] = {
258 CONST UINT64
* pMemEnd
;
259 CONST UINT64
* pMemStart
;
269 // Send the Memory Type Registers page
273 // Send the page header
275 Status
= HttpPageHeader ( SocketFD
, pPort
, L
"Memory Type Range Registers" );
276 if ( EFI_ERROR ( Status
)) {
283 Status
= HttpSendAnsiString ( SocketFD
,
285 "<h1>Memory Type Range Registers</h1>\r\n" );
286 if ( EFI_ERROR ( Status
)) {
291 // Determine if MTRRs are supported
293 if ( !IsMtrrSupported ( )) {
294 Status
= HttpSendAnsiString ( SocketFD
,
296 "<p>Memory Type Range Registers are not supported!\r\n" );
297 if ( EFI_ERROR ( Status
)) {
303 // Get the capabilities
305 Capabilities
= AsmReadMsr64 ( MTRR_LIB_IA32_MTRR_CAP
);
306 DefType
= AsmReadMsr64 ( MTRR_LIB_IA32_MTRR_DEF_TYPE
);
309 // Display the capabilities
311 Status
= HttpSendAnsiString ( SocketFD
,
313 "<p>Capabilities: " );
314 if ( EFI_ERROR ( Status
)) {
317 Status
= HttpSendHexValue ( SocketFD
,
320 if ( EFI_ERROR ( Status
)) {
323 Status
= HttpSendAnsiString ( SocketFD
,
326 if ( EFI_ERROR ( Status
)) {
331 // Display the default type
333 Status
= HttpSendAnsiString ( SocketFD
,
336 if ( EFI_ERROR ( Status
)) {
339 Status
= HttpSendHexValue ( SocketFD
,
342 if ( EFI_ERROR ( Status
)) {
345 Status
= HttpSendAnsiString ( SocketFD
,
348 if ( EFI_ERROR ( Status
)) {
351 Status
= HttpSendAnsiString ( SocketFD
,
353 ( 0 != ( DefType
& MTRR_LIB_CACHE_MTRR_ENABLED
))
356 if ( EFI_ERROR ( Status
)) {
359 Status
= HttpSendAnsiString ( SocketFD
,
362 if ( EFI_ERROR ( Status
)) {
365 Status
= HttpSendAnsiString ( SocketFD
,
367 ( 0 != ( DefType
& MTRR_LIB_CACHE_FIXED_MTRR_ENABLED
))
370 if ( EFI_ERROR ( Status
)) {
373 Status
= HttpSendAnsiString ( SocketFD
,
376 if ( EFI_ERROR ( Status
)) {
379 Type
= DefType
& 0xff;
380 Status
= HttpSendAnsiString ( SocketFD
,
382 ( DIM ( mMemoryType
) > Type
)
383 ? mMemoryType
[ Type
]
385 if ( EFI_ERROR ( Status
)) {
388 Status
= HttpSendAnsiString ( SocketFD
,
391 if ( EFI_ERROR ( Status
)) {
396 // Determine if MTRRs are enabled
398 if ( 0 == ( DefType
& MTRR_LIB_CACHE_MTRR_ENABLED
)) {
399 Status
= HttpSendAnsiString ( SocketFD
,
401 "<p>All memory is uncached!</p>\r\n" );
402 if ( EFI_ERROR ( Status
)) {
410 MtrrGetAllMtrrs ( &Mtrr
);
413 // Determine if the fixed MTRRs are supported
415 if (( 0 != ( Capabilities
& 0x100 ))
416 && ( 0 != ( DefType
& MTRR_LIB_CACHE_FIXED_MTRR_ENABLED
))) {
419 // Beginning of table
421 Status
= HttpSendAnsiString ( SocketFD
,
423 "<h2>Fixed MTRRs</h2>\r\n"
425 " <tr><th>Index</th><th align=\"right\">Value</th><th align=\"right\">Start</th><th align=\"right\">End</th></tr>\r\n" );
426 if ( EFI_ERROR ( Status
)) {
431 // Display the fixed MTRRs
433 pMemStart
= &mFixedAddresses
[ 0 ];
434 for ( Count
= 0; DIM ( Mtrr
.Fixed
.Mtrr
) > Count
; Count
++ ) {
438 Status
= HttpSendAnsiString ( SocketFD
,
441 if ( EFI_ERROR ( Status
)) {
448 Status
= HttpSendValue ( SocketFD
,
451 if ( EFI_ERROR ( Status
)) {
458 Status
= HttpSendAnsiString ( SocketFD
,
460 "</td><td align=\"right\"><code>0x" );
461 if ( EFI_ERROR ( Status
)) {
464 Status
= HttpSendHexValue ( SocketFD
,
466 Mtrr
.Fixed
.Mtrr
[ Count
]);
467 if ( EFI_ERROR ( Status
)) {
474 Status
= HttpSendAnsiString ( SocketFD
,
476 "</code></td><td align=\"right\"><code>0x" );
477 if ( EFI_ERROR ( Status
)) {
480 Status
= HttpSendHexValue ( SocketFD
,
483 if ( EFI_ERROR ( Status
)) {
491 Status
= HttpSendAnsiString ( SocketFD
,
493 "</code></td><td align=\"right\"><code>0x" );
494 if ( EFI_ERROR ( Status
)) {
497 Status
= HttpSendHexValue ( SocketFD
,
500 if ( EFI_ERROR ( Status
)) {
507 Status
= HttpSendAnsiString ( SocketFD
,
509 "</code></td></tr>\r\n" );
510 if ( EFI_ERROR ( Status
)) {
514 if ( EFI_ERROR ( Status
)) {
521 Status
= HttpSendAnsiString ( SocketFD
,
524 if ( EFI_ERROR ( Status
)) {
529 // Beginning of table
531 Status
= HttpSendAnsiString ( SocketFD
,
534 " <tr><th align=\"right\">Start</th><th align=\"right\">End</th><th align=\"left\">Type</th></tr>\r\n" );
535 if ( EFI_ERROR ( Status
)) {
540 // Decode the fixed MTRRs
542 PreviousType
= Mtrr
.Fixed
.Mtrr
[ 0 ] & 0xff;
543 pMemStart
= &mFixedAddresses
[ 0 ];
545 for ( Count
= 0; DIM ( Mtrr
.Fixed
.Mtrr
) > Count
; Count
++ ) {
547 // Get the memory types
549 Type
= Mtrr
.Fixed
.Mtrr
[ Count
];
552 // Walk the memory range
554 for ( Index
= 0; 8 > Index
; Index
++ ) {
556 // Determine if this is the same memory type
558 if ( PreviousType
!= ( Type
& 0xff )) {
562 Status
= MtrrDisplayFixedRow ( SocketFD
,
567 if ( EFI_ERROR ( Status
)) {
572 // Start the next range of addresses
575 PreviousType
= Type
& 0xff;
579 // Set the next memory range and type
584 if ( EFI_ERROR ( Status
)) {
588 if ( EFI_ERROR ( Status
)) {
593 // Display the final row
595 Status
= MtrrDisplayFixedRow ( SocketFD
,
600 if ( EFI_ERROR ( Status
)) {
607 Status
= HttpSendAnsiString ( SocketFD
,
610 if ( EFI_ERROR ( Status
)) {
616 // Determine if the variable MTRRs are supported
618 MaxMtrrs
= Capabilities
& MTRR_LIB_IA32_MTRR_CAP_VCNT_MASK
;
619 if ( 0 < MaxMtrrs
) {
621 // Beginning of table
623 Status
= HttpSendAnsiString ( SocketFD
,
625 "<h2>Variable MTRRs</h2>\r\n"
627 " <tr><th>Index</th><th align=\"right\">Base</th><th align=\"right\">Mask</th><th align=\"right\">Start</th><th align=\"right\">End</th></tr>\r\n" );
628 if ( EFI_ERROR ( Status
)) {
633 // Display the variable MTRRs
635 for ( Count
= 0; MaxMtrrs
> Count
; Count
++ ) {
639 Status
= HttpSendAnsiString ( SocketFD
,
642 if ( EFI_ERROR ( Status
)) {
649 Status
= HttpSendValue ( SocketFD
,
652 if ( EFI_ERROR ( Status
)) {
659 Status
= HttpSendAnsiString ( SocketFD
,
661 "</td><td align=\"right\"><code>0x" );
662 if ( EFI_ERROR ( Status
)) {
665 Status
= HttpSendHexValue ( SocketFD
,
667 Mtrr
.Variables
.Mtrr
[ Count
].Base
);
668 if ( EFI_ERROR ( Status
)) {
675 Status
= HttpSendAnsiString ( SocketFD
,
677 "</td><td align=\"right\"><code>0x" );
678 if ( EFI_ERROR ( Status
)) {
681 Status
= HttpSendHexValue ( SocketFD
,
683 Mtrr
.Variables
.Mtrr
[ Count
].Mask
);
684 if ( EFI_ERROR ( Status
)) {
689 // Determine if the entry is valid
691 bValid
= ( Mtrr
.Variables
.Mtrr
[ Count
].Mask
& VARIABLE_MTRR_VALID
) ? TRUE
: FALSE
;
696 Status
= HttpSendAnsiString ( SocketFD
,
698 "</code></td><td align=\"right\"><code>" );
699 if ( EFI_ERROR ( Status
)) {
702 Addr
= Mtrr
.Variables
.Mtrr
[ Count
].Base
& 0xfffffffffffff000ULL
;
704 Status
= HttpSendAnsiString ( SocketFD
,
707 if ( EFI_ERROR ( Status
)) {
710 Status
= HttpSendHexValue ( SocketFD
,
715 Status
= HttpSendAnsiString ( SocketFD
,
719 if ( EFI_ERROR ( Status
)) {
726 Status
= HttpSendAnsiString ( SocketFD
,
728 "</code></td><td align=\"right\"><code>" );
729 if ( EFI_ERROR ( Status
)) {
734 // Determine the end address
736 Mask
= Mtrr
.Variables
.Mtrr
[ Count
].Mask
;
739 while ( 0 < Value
) {
744 Value
<<= 64 - ShiftCount
;
748 Value
&= ~VARIABLE_MTRR_VALID
;
751 Status
= HttpSendAnsiString ( SocketFD
,
754 if ( EFI_ERROR ( Status
)) {
757 Status
= HttpSendHexValue ( SocketFD
,
761 if ( EFI_ERROR ( Status
)) {
768 Status
= HttpSendAnsiString ( SocketFD
,
770 "</code></td><td>" );
771 if ( EFI_ERROR ( Status
)) {
775 Type
= Mtrr
.Variables
.Mtrr
[ Count
].Base
& 0xFF;
776 Status
= HttpSendAnsiString ( SocketFD
,
778 ( DIM ( mMemoryType
) > Type
)
779 ? mMemoryType
[ Type
]
782 if ( EFI_ERROR ( Status
)) {
789 Status
= HttpSendAnsiString ( SocketFD
,
792 if ( EFI_ERROR ( Status
)) {
796 if ( EFI_ERROR ( Status
)) {
803 Status
= HttpSendAnsiString ( SocketFD
,
806 if ( EFI_ERROR ( Status
)) {
814 // Send the page trailer
816 Status
= HttpPageTrailer ( SocketFD
, pPort
, pbDone
);
821 // Return the operation status
823 DBG_EXIT_STATUS ( Status
);