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

📄 i81xgart.c

📁 zinc60t22.tar.gz:zinc在tornado2.2.x下的补丁
💻 C
📖 第 1 页 / 共 2 页
字号:
/* sysI81xGart.c - Graphics Address Resolution Table driver for i81x/81xE chipsets *//* Copyright 1984-2003 Wind River Systems, Inc. */#include "copyright_wrs.h"/*modification history--------------------01c,18jun03,jlb  Update to Tornado 2.201b,20aug01,dmh  rewritten01a,10aug00,mks  written.*//*DESCRIPTIONModern 3D graphics processing on PCs requires fast processing of texture mapsby both the host processor and the graphics device. After the CPU performstransformations on a texture, the data must travel across the bus to thegraphics controller for display. For animation, these textures are continuouslybeing updated by the host processor and the transmission of large data blocksacross a slow bus is time consuming.Intel's new accelerated graphics processor (AGP) architecture provides fastaccess by the graphics device to system memory, enabling data common to thegraphic and host processors to be stored in host memory. Thus, AGP allowstextures to be accessed directly from system memory during rendering rather thanbeing pre-fetched to local graphics memory.Because of host paging, blocks of memory with contiguous linear addresses maynot be contiguous physically. However, the graphics device must see datastructures such as texture maps as a contiguous block. To solve this problem,AGP hardware is equipped with core logic to translate addresses through amemory-based graphics address remapping table, or GART. The GART performs amapping function similar to the host's paging tables, but the two mechanisms areindependent and should not be confused. This address remapping applies only to asingle, programmable range of the system physical address space, as shown in thefollowing diagram. Only addresses within the GART's aperture have the mappingapplied; other addresses are passed through unchanged..LP.I USAGEThis library provides low level access routines for graphics address remappingtable (GART). There are many functions provided here to intialize the library,create and remove entries from GART, etc.The functions addressed here include:.IP "   -"Initialization of the library.INCLUDE FILES: i81xEGart.h*//* includes */#include <vxWorks.h>#include <asm.h>#include <regs.h>#include <stdio.h>#include <stdlib.h>#include <string.h>#include <vmLib.h>#include <drv/pci/pciConfigLib.h>#include <ugl/driver/graphics/intel/i81x.h>#include <ugl/driver/graphics/intel/i81xGart.h>#define I81xGART_GFX_APERTURE_SIZE    4    /* 4 MB *//* local */static I81xGART_INIT_PARAMS_TYPE i81xGartInitParams[] = {     /* size, # of main mem entries, 2^order, # of display cache entries */     {32, 8192, 4096, 0},     {64, 16384, 4096, 0} };static volatile unsigned char * i81xGartMMAddr;#define I81xGART_MEMMAP_OUT(offset, val) *(volatile unsigned long int *) \                            (i81xGartMMAddr + offset) = (val)#define I81xGART_MEMMAP_IN(offset)       *(volatile unsigned long int *) \                            (i81xGartMMAddr + offset)static I81xGART_CHIPSET_CLASS i81xGartChipset;static I81xGART_INIT_PARAMS_TYPE * i81xGartInitPtr;static unsigned long i81xGartStartAddr;static unsigned long i81xGartGMPhysAddr;static unsigned long i81xGartEntrySettings;static unsigned long * i81xGartTablePtr;static ULONG * i81xGartCmdLinearAddr;static ULONG * i81xGartCmdLinearAddrStore;static ULONG i81xGartCmdCounter;static ULONG * i81xGartAperturePhyBase;static ULONG * i81xGartSrcDataPhyBase;static ULONG * i81xGartCmdDataPhyBase;/* forward declaration */static void i81xGartFlushCache (void);#define FLUSH_CACHE()    i81xGartFlushCache()#define PGE_EMPTY(p) (!(p) || (p) == 0)#if 0#define I81xGART_DEBUG#define I81xCMD_DEBUG#define I81xGART_DEBUG_LVL2#else#endif/********************************************************************************* i81xGartFlushCache -** RETURNS: OK, if successful else ERROR*/static void i81xGartFlushCache    (    void    )    {    __asm__ volatile("wbinvd" : : : "memory" );    }/********************************************************************************* i81xGartInsertPageIdx -** RETURNS: OK, if successful else ERROR*/static STATUS i81xGartInsertPageIdx    (    int gart_index,    void * pagePhyAdrs    )    {    unsigned long tmp_value;    if (gart_index < 0 ||       gart_index >= i81xGartInitPtr->num_entries)        {        return (ERROR);        }    if(pagePhyAdrs == NULL)        {#ifdef I81xGART_DEBUG_LVL2        printf ("error: i81xGartInsertPageIdx: pagePhyAdrs == NULL.\n");#endif        return (ERROR);        }    tmp_value = i81xGartTablePtr[gart_index];    if (!PGE_EMPTY(tmp_value))        {#ifdef I81xGART_DEBUG_LVL2        printf ("error: i81xGartInsertPageIdx: !PGE_EMPTY(0x%X)\n",                (int) tmp_value);#endif        return (ERROR);        }    tmp_value = (unsigned long) pagePhyAdrs;    /* Make entry in GTT = I81xGART_PTE_MAIN_UNCACHED | I81xGART_PTE_VALID */    tmp_value |= i81xGartEntrySettings;    /* Write an entry into GTT */#ifdef I81xGART_DEBUG_LVL2    printf ("status: i81xGartInsertPageIdx: Writing 0x%X to gart_index 0x%X\n",            (int) tmp_value, gart_index);#endif    i81xGartChipset.write_entry(gart_index, tmp_value);    if (i81xGartChipset.cache_flush_req)        FLUSH_CACHE();    i81xGartChipset.tlb_flush();    return (OK);    }/********************************************************************************* i81xGartInsertPage -** RETURNS: OK, if successful else ERROR*/static STATUS i81xGartInsertPage    (    void * pagePhyAdrs    )    {    unsigned long tmp_value;    int i;    if(pagePhyAdrs == NULL)        {#ifdef I81xGART_DEBUG_LVL2        printf ("error: i81xGartInsertPage: pagePhyAdrs == NULL.\n");#endif        return (ERROR);        }    for (i = 0; i < i81xGartInitPtr->num_entries; i++)        {        tmp_value = i81xGartTablePtr[i];        if (PGE_EMPTY(tmp_value))            {#ifdef I81xGART_DEBUG_LVL2            printf ("status: i81xGartInsertPage: i81xGartInsertPageIdx (%d, 0x%X).\n",                    i, (int) pagePhyAdrs);#endif            i81xGartInsertPageIdx (i, pagePhyAdrs);            break;            }        }    return (OK);    }/********************************************************************************* i81xGartCreateGtt -** RETURNS: OK, if successful else ERROR*/static STATUS i81xGartCreateGtt    (    int size    )    {    void * table;    int i;    I81xGART_INIT_PARAMS_TYPE * gart_init_p = NULL;    int j = (sizeof (i81xGartInitParams) / sizeof (I81xGART_INIT_PARAMS_TYPE));#ifdef I81xGART_DEBUG    printf ("status: i81xGartCreateGtt: i81xGartInitParams[%d]\n", j);#endif    /* Find the corresponding entry in i81xGartInitParams[] for given size */    for (i = 0; i < j ; i++)        {        if(size == i81xGartInitParams[i].size)            {            gart_init_p = &i81xGartInitParams[i];            }        }#ifdef I81xGART_DEBUG    printf ("status: i81xGartCreateGtt: gart_init_p 0x%X\n", (int) gart_init_p);#endif    /* Any valid entry ? */    if (gart_init_p == NULL)        {#ifdef I81xGART_DEBUG        printf ("error: i81xGartCreateGtt: gart_init_p == NULL\n");#endif        return (ERROR);        }    /* Pointer to currently selected i81xGartInitParams entry */    i81xGartInitPtr = (I81xGART_INIT_PARAMS_TYPE *) gart_init_p;#ifdef I81xGART_DEBUG    printf ("status: i81xGartCreateGtt: calling memalign()\n");#endif    /* Allocate 4KB aligned memory block: 32K for 32M or 64K for 64M */    table = (void *) memalign (i81xGartInitPtr->page_order,                               (i81xGartInitPtr->size * 1024));    if (table == NULL)        {#ifdef I81xGART_DEBUG        printf ("error: i81xGartCreateGtt: memalign failed\n");#endif        return (ERROR);        }#ifdef I81xGART_DEBUG    printf ("status: i81xGartCreateGtt: called memalign(): table 0x%X\n",            (int) table);#endif    /* Zeroing out allocated memory block */    memset(table, 0, (i81xGartInitPtr->size * 1024));    i81xGartStartAddr = (unsigned long) table;    i81xGartTablePtr = (unsigned long *) i81xGartStartAddr;#ifdef I81xGART_DEBUG    printf ("status: i81xGartCreateGtt: i81xGartStartAddr 0x%X\n", (int) table);#endif    return (OK);    }/********************************************************************************* i81xGartInitGtt -** RETURNS: OK, if successful else ERROR*/static STATUS i81xGartInitGtt    (    void    )    {    unsigned int size;    unsigned int miscc;    unsigned int smram;    /* Check if internal graphics core (GFX) enabled */    pciConfigInByte (i81xGartChipset.hosthub.bus, i81xGartChipset.hosthub.dev,                     i81xGartChipset.hosthub.fn, I81xGART_SMRAM,                     (UINT8 *) &smram);    if ( (smram & I81xGART_GMS) == I81xGART_GMS_DISABLE )        {#ifdef I81xGART_DEBUG        printf("error: i81xGartInitGtt: i81x GFX is disabled\n");#endif        return (ERROR);        }    /* Find GTT's size */    pciConfigInWord (i81xGartChipset.hosthub.bus, i81xGartChipset.hosthub.dev,                     i81xGartChipset.hosthub.fn, I81xGART_MISCC,                     (UINT16 *) &miscc);    /* If lower most bit is 0, mem = 64M else 32M */    if (miscc & I81xGART_GFX_MEM_WIN_SIZE)        size = 32;    else        size = 64;#ifdef I81xGART_DEBUG    printf ("status: i81xGartInitGtt: GART MEM WIN SIZE %d\n", size);#endif    /* Initialize gart_init. */    if (i81xGartCreateGtt (size) != OK)        {#ifdef I81xGART_DEBUG        printf( "error: i81xGartInitGtt: unable to get memory for GART.\n");#endif        return (ERROR);        }    /* Make room for local display cache entries, if display cache exists */    I81xGART_MEMMAP_OUT(I81xGART_DRAM_CTL, I81xGART_DRAM_ROW_0_SDRAM);    if (I81xGART_MEMMAP_IN(I81xGART_DRAM_CTL) & I81xGART_DRAM_ROW_0)        {#ifdef I81xGART_DEBUG        printf( "status: i81xGartInitGtt: detected 4MB dedicated video ram\n");#endif        i81xGartInitPtr->num_dcache_entries = 1024;        i81xGartInitPtr->num_entries -= 1024;        }    return (OK);    }/********************************************************************************* i81xGartWriteEntry** RETURNS: OK, if successful else ERROR*/static void i81xGartWriteEntry    (    int entry,    unsigned long val    )    {    I81xGART_MEMMAP_OUT((I81xGART_PTE_BASE + (entry * 4)), val);    }/* Writing via mmio already flushes all tlb's on the graphics device. */static void i81xGartTlbFlush    (    void    )    {    }/********************************************************************************* i81xGartConfigure -** RETURNS: OK, if successful else ERROR*/static STATUS i81xGartConfigure    (    void    )    {    int i;    /* Fill in GTT Start Address and enable GTT */    I81xGART_MEMMAP_OUT(I81xGART_PGETBL_CTL, i81xGartStartAddr | I81xGART_PGETBL_ENABLED);#ifdef I81xGART_DEBUG    printf ("status: i81xGartConfigure: PGETBL_CTL 0x%X\n",            (int) I81xGART_MEMMAP_IN(I81xGART_PGETBL_CTL));#endif    if (i81xGartChipset.cache_flush_req)        FLUSH_CACHE();    /* Load the dcache, if present. */    for (i = i81xGartInitPtr->num_entries ;         i < i81xGartInitPtr->num_entries + i81xGartInitPtr->num_dcache_entries ;         i++)        {        I81xGART_MEMMAP_OUT((I81xGART_PTE_BASE + (i * 4)),               ((i*4096) | I81xGART_PTE_LOCAL | I81xGART_PTE_VALID));        }    return (OK);    }/********************************************************************************* i81xGartDisableGtt** RETURNS: OK, if successful else ERROR*/static void i81xGartDisableGtt    (    void    )    {    I81xGART_MEMMAP_OUT(I81xGART_PGETBL_CTL, 0);    }/********************************************************************************* i81xGartFindSupported -** RETURNS: OK, if successful else ERROR*/static int i81xGartFindSupported    (    void    )    {    /* Default chipset - NOT_SUPPORTED */    i81xGartChipset.type = NOT_SUPPORTED;    /* Find Bus/Dev/Instance of HOST-HUB, if exists */    if (pciFindDevice (INTEL_PCI_VENDOR_ID, INTEL_82815_FASTFSB_BRIDGE, 0,                       &i81xGartChipset.hosthub.bus,                       &i81xGartChipset.hosthub.dev,                       &i81xGartChipset.hosthub.fn) != OK)        {#ifdef I81xGART_DEBUG        printf("error: i81xGartFindSupported: could not find GMCH DEV 0\n");#endif        return (ERROR);        }    /* Find Bus/Dev/Instance of GFX, if exists */    if (pciFindDevice (INTEL_PCI_VENDOR_ID,                       INTEL_82815_FASTFSB_GRAPHICS_ENABLED, 0,                       &i81xGartChipset.gfx.bus,                       &i81xGartChipset.gfx.dev,                       &i81xGartChipset.gfx.fn) != OK)        {#ifdef I81xGART_DEBUG        printf("error: i81xGartFindSupported: could not find GMCH DEV 2\n");#endif        return (ERROR);        }    /* Chipset = INTEL_815, if both of above mentioned checks are success */    i81xGartChipset.type    = INTEL_815;    switch(i81xGartChipset.type)        {        case INTEL_815:        case INTEL_815E:            /* GART entry setting for uncache main memory addresses */            i81xGartEntrySettings    = I81xGART_PTE_VALID;            i81xGartChipset.cache_flush_req     = TRUE;            i81xGartChipset.initialize          = i81xGartInitGtt;            i81xGartChipset.configure           = i81xGartConfigure;            i81xGartChipset.fetch_size          = 0;            i81xGartChipset.cleanup             = i81xGartDisableGtt;            i81xGartChipset.tlb_flush           = i81xGartTlbFlush;            i81xGartChipset.write_entry     = i81xGartWriteEntry;            break;        case NOT_SUPPORTED:        default:            break;        }    if (i81xGartChipset.type == NOT_SUPPORTED)        {#ifdef I81xGART_DEBUG        printf("error: i81xGartFindSupported: i81xGartChipset.type NOTSUPPORTED\n");#endif        return (ERROR);        }    else        return (OK);    }/********************************************************************************* i81xGartMapMem** RETURNS: OK, if successful else ERROR*/STATUS i81xGartMapMem    (    VOID    )    {    unsigned int mmbase;    unsigned int temp;    /* Check if the current chipset is supported or not */    if (i81xGartFindSupported() != OK)        {#ifdef I81xGART_DEBUG        printf("error: i81xGartMapMem: i81xGartFindSupported\n");#endif    return (ERROR);        }    /* Read MMADDR BAR register */    pciConfigInLong (i81xGartChipset.gfx.bus, i81xGartChipset.gfx.dev,                     i81xGartChipset.gfx.fn , I81xGART_MMADDR, &mmbase);    /* Get Addr [31:19] of memory mapped address space */    mmbase &= 0xfff80000;    /* MMADDR[31:19] */    /* Virtual and Physical have 1:1 correspondance */    i81xGartMMAddr = (unsigned char *) mmbase;    /* gmaddr - physical address to remap too (a pci range of this device) */    pciConfigInLong (i81xGartChipset.gfx.bus, i81xGartChipset.gfx.dev,                     i81xGartChipset.gfx.fn, I81xGART_GMADDR,                     (UINT32 *) &temp);    i81xGartGMPhysAddr = (temp & 0xFFFFFFF0);    return (OK);    }/********************************************************************************* i81xGartReserveCont -** RETURNS: OK, if successful else ERROR*/LOCAL void * i81xGartReserveCont    (    int fourKBlocks    )    {    int i;    char * xPtr;    char * tmpPtr;    /* validate input */    if (fourKBlocks < 0)        {#ifdef I81xGART_DEBUG_LVL2        printf ("error: i81xGartReserveCont: invalid input %d\n", fourKBlocks);#endif        return (NULL);

⌨️ 快捷键说明

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