⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 pentiumlib.c

📁 vxworks源码源码解读是学习vxworks的最佳途径
💻 C
字号:
/* pentiumLib.c - Pentium and PentiumPro library *//* Copyright 1984-1996 Wind River Systems, Inc. */#include "copyright_wrs.h"/*modification history--------------------01c,24mar99,jdi  doc: added basic formatting cmds, particularly .CS/.CE		 to set off code snippets as per standard practice.01b,17apr98,hdn  fixed typo.01b,17apr98,hdn  added documentation.01a,09jul97,hdn  written.*//*DESCRIPTIONThis library provides Pentium and PentiumPro specific routines. MTRR (Memory Type Range Register) are a new feature introduced in the PentiumPro processor that allow the processor to optimize memory operationsfor different types of memory, such as RAM, ROM, frame buffer memory, andmemory-mapped IO.  MTRRs configure an internal map of how physical address ranges are mapped to various types of memory.  The processor uses this internalmap to determine the cacheability of various physical memory locations and theoptimal method of accessing memory locations.  For example, if a memorylocation is specified in an MTRR as write-through memory, the processor handlesaccesses to this location as follows.  It reads data from that location in lines and caches the read data or maps all writes to that location to the busand updates the cache to maintain cache coherency.  In mapping the physicaladdress space with MTRRs, the processor recognizes five types of memory:uncacheable (UC), write-combining (WC), write-through (WT),write-protected (WP), and write-back (WB).There is one table - sysMtrr[] in sysLib.c - and four routines to interfacethe MTRR.  These four routines are:.CS  void pentiumMtrrEnable (void)  void pentiumMtrrDisable (void)  void pentiumMtrrGet      (      MTRR * pMtrr		/@ MTRR table @/      )  void pentiumMtrrSet (void)      (      MTRR * pMtrr		/@ MTRR table @/      ).CEpentiumMtrrEnable() enables MTRR, pentiumMtrrDisable() disables MTRR.pentiumMtrrGet() gets MTRRs to the specified MTRR table.pentiumMtrrGet() sets MTRRs from the specified MTRR table.The MTRR table is defined as follows:.CStypedef struct mtrr_fix         /@ MTRR - fixed range register @/    {    char type[8];		/@ address range: [0]=0-7 ... [7]=56-63 @/    } MTRR_FIX;typedef struct mtrr_var         /@ MTRR - variable range register @/    {    long long int base;		/@ base register @/    long long int mask;		/@ mask register @/    } MTRR_VAR;typedef struct mtrr             /@ MTRR @/    {    int cap[2];                 /@ MTRR cap register @/    int deftype[2];             /@ MTRR defType register @/    MTRR_FIX fix[11];           /@ MTRR fixed range registers @/    MTRR_VAR var[8];            /@ MTRR variable range registers @/    } MTRR;.CEFixed Range Register's type array can be one of following memory types.MTRR_UC (uncacheable), MTRR_WC (write-combining), MTRR_WT (write-through), MTRR_WP (write-protected), and MTRR_WB (write-back).MTRR is enabled in sysHwInit().SEE ALSO:.I "Pentium, PentiumPro Family Developer's Manual"*//* includes */#include "vxWorks.h"#include "regs.h"#include "arch/i86/pentiumLib.h"#include "intLib.h"#include "cacheLib.h"/* defines */typedef long long int	ll_int;/* locals */LOCAL char mtrrBusy = FALSE;		/* MTRR busy flag *//********************************************************************************* pentiumMtrrEnable - enable MTRR (Memory Type Range Register)** This routine enables the MTRR that provide a mechanism for associating the* memory types with physical address ranges in system memory.** RETURNS: N/A*/void pentiumMtrrEnable (void)    {    int oldLevel;    int deftype[2];    int oldCr4;    oldLevel = intLock ();                      /* LOCK INTERRUPT */    cacheFlush (DATA_CACHE, NULL, NULL);	/* flush cache w WBINVD */    oldCr4 = pentiumCr4Get ();			/* save CR4 */    pentiumCr4Set (oldCr4 & ~CR4_PGE);		/* clear PGE bit */    pentiumTlbFlush ();				/* flush TLB */    pentiumMsrGet (MSR_MTRR_DEFTYPE, (ll_int *)&deftype);    deftype[0] |= (MTRR_E | MTRR_FE);		/* set enable bits */    pentiumMsrSet (MSR_MTRR_DEFTYPE, (ll_int *)&deftype);    cacheFlush (DATA_CACHE, NULL, NULL);	/* flush cache w WBINVD */    pentiumTlbFlush ();				/* flush TLB */    pentiumCr4Set (oldCr4);			/* restore CR4 */    intUnlock (oldLevel);			/* UNLOCK INTERRUPT */    }/********************************************************************************* pentiumMtrrDisable - disable MTRR (Memory Type Range Register)** This routine disables the MTRR that provide a mechanism for associating the* memory types with physical address ranges in system memory.** RETURNS: N/A*/void pentiumMtrrDisable (void)    {    int oldLevel;    int deftype[2];    int oldCr4;    oldLevel = intLock ();                      /* LOCK INTERRUPT */    cacheFlush (DATA_CACHE, NULL, NULL);	/* flush cache w WBINVD */    oldCr4 = pentiumCr4Get ();			/* save CR4 */    pentiumCr4Set (oldCr4 & ~CR4_PGE);		/* clear PGE bit */    pentiumTlbFlush ();				/* flush TLB */    pentiumMsrGet (MSR_MTRR_DEFTYPE, (ll_int *)&deftype);    deftype[0] &= ~(MTRR_E | MTRR_FE);		/* clear enable bits */    pentiumMsrSet (MSR_MTRR_DEFTYPE, (ll_int *)&deftype);    cacheFlush (DATA_CACHE, NULL, NULL);	/* flush cache w WBINVD */    pentiumTlbFlush ();				/* flush TLB */    pentiumCr4Set (oldCr4);			/* restore CR4 */    intUnlock (oldLevel);			/* UNLOCK INTERRUPT */    }/********************************************************************************* pentiumMtrrGet - get MTRRs to a specified MTRR table** This routine gets MTRRs to a specified MTRR table with RDMSR instruction.* The read MTRRs are CAP register, DEFTYPE register, fixed range MTRRs, and* variable range MTRRs.** RETURNS: OK, or ERROR if MTRR is being accessed.*/STATUS pentiumMtrrGet    (    MTRR * pMtrr		/* MTRR table */    )    {    int ix;    int addr = MSR_MTRR_PHYS_BASE0;    /* mutual exclusion ON */    if (pentiumBts (&mtrrBusy) != OK)	return (ERROR);	    pentiumMsrGet (MSR_MTRR_CAP, (ll_int *)&pMtrr->cap);    pentiumMsrGet (MSR_MTRR_DEFTYPE, (ll_int *)&pMtrr->deftype);    if (pMtrr->cap[0] & MTRR_FIX_SUPPORT)	{        pentiumMsrGet (MSR_MTRR_FIX_00000, (ll_int *)&pMtrr->fix[0].type);        pentiumMsrGet (MSR_MTRR_FIX_80000, (ll_int *)&pMtrr->fix[1].type);        pentiumMsrGet (MSR_MTRR_FIX_A0000, (ll_int *)&pMtrr->fix[2].type);        pentiumMsrGet (MSR_MTRR_FIX_C0000, (ll_int *)&pMtrr->fix[3].type);        pentiumMsrGet (MSR_MTRR_FIX_C8000, (ll_int *)&pMtrr->fix[4].type);        pentiumMsrGet (MSR_MTRR_FIX_D0000, (ll_int *)&pMtrr->fix[5].type);        pentiumMsrGet (MSR_MTRR_FIX_D8000, (ll_int *)&pMtrr->fix[6].type);        pentiumMsrGet (MSR_MTRR_FIX_E0000, (ll_int *)&pMtrr->fix[7].type);        pentiumMsrGet (MSR_MTRR_FIX_E8000, (ll_int *)&pMtrr->fix[8].type);        pentiumMsrGet (MSR_MTRR_FIX_F0000, (ll_int *)&pMtrr->fix[9].type);        pentiumMsrGet (MSR_MTRR_FIX_F8000, (ll_int *)&pMtrr->fix[10].type);	}    for (ix = 0; ix < (pMtrr->cap[0] & MTRR_VCNT); ix++)	{        pentiumMsrGet (addr, &pMtrr->var[ix].base);        pentiumMsrGet (addr + 1, &pMtrr->var[ix].mask);	}    /* mutual exclusion OFF */    (void) pentiumBtc (&mtrrBusy);    return (OK);    }/********************************************************************************* pentiumMtrrSet - set MTRRs from specified MTRR table with WRMSR instruction.** This routine sets MTRRs from specified MTRR table with WRMSR instruction.* The written MTRRs are DEFTYPE register, fixed range MTRRs, and variable* range MTRRs.** RETURNS: OK, or ERROR if MTRR is enabled or being accessed.*/STATUS pentiumMtrrSet     (    MTRR * pMtrr		/* MTRR table */    )    {    int ix;    int addr = MSR_MTRR_PHYS_BASE0;    /* MTRR should be disabled */    pentiumMsrGet (MSR_MTRR_DEFTYPE, (ll_int *)&pMtrr->deftype);    if ((pMtrr->deftype[0] & (MTRR_E | MTRR_FE)) != 0)	return (ERROR);    /* mutual exclusion ON */    if (pentiumBts (&mtrrBusy) != OK)	return (ERROR);	    pentiumMsrSet (MSR_MTRR_DEFTYPE, (ll_int *)&pMtrr->deftype);    pentiumMsrGet (MSR_MTRR_CAP, (ll_int *)&pMtrr->cap);    if (pMtrr->cap[0] & MTRR_FIX_SUPPORT)	{        pentiumMsrSet (MSR_MTRR_FIX_00000, (ll_int *)&pMtrr->fix[0].type);        pentiumMsrSet (MSR_MTRR_FIX_80000, (ll_int *)&pMtrr->fix[1].type);        pentiumMsrSet (MSR_MTRR_FIX_A0000, (ll_int *)&pMtrr->fix[2].type);        pentiumMsrSet (MSR_MTRR_FIX_C0000, (ll_int *)&pMtrr->fix[3].type);        pentiumMsrSet (MSR_MTRR_FIX_C8000, (ll_int *)&pMtrr->fix[4].type);        pentiumMsrSet (MSR_MTRR_FIX_D0000, (ll_int *)&pMtrr->fix[5].type);        pentiumMsrSet (MSR_MTRR_FIX_D8000, (ll_int *)&pMtrr->fix[6].type);        pentiumMsrSet (MSR_MTRR_FIX_E0000, (ll_int *)&pMtrr->fix[7].type);        pentiumMsrSet (MSR_MTRR_FIX_E8000, (ll_int *)&pMtrr->fix[8].type);        pentiumMsrSet (MSR_MTRR_FIX_F0000, (ll_int *)&pMtrr->fix[9].type);        pentiumMsrSet (MSR_MTRR_FIX_F8000, (ll_int *)&pMtrr->fix[10].type);	}    for (ix = 0; ix < (pMtrr->cap[0] & MTRR_VCNT); ix++)	{        pentiumMsrGet (addr, &pMtrr->var[ix].base);        pentiumMsrGet (addr + 1, &pMtrr->var[ix].mask);	}    /* mutual exclusion OFF */    (void) pentiumBtc (&mtrrBusy);    return (OK);    }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -