📄 pcichaindma.c
字号:
/* pciChainDma.c - DMA Demo using the idma channels from mem to pci *//************************************************************************** * * Copyright (c) 2005 Curtiss-Wright Controls, Inc. All rights * reserved. This Source Code is the Property of Curtiss-Wright * Controls, Inc. and can only be used in accordance with Source * Code License Agreement(s) of Curtiss-Wright Controls, Inc. or any * of its subsidiaries. * **************************************************************************//***************************************************************************** THIS CODE IS PROVIDED "AS IS". CWCEC MAKES NO WARRANTIES, EXPRESSED, ** IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY, COMPLETENESS OR PERFORMANCE.******************************************************************************//*modification history--------------------01c,12dec05,tis rename Discovery_II directory to Discovery_III CR#12858.01b,04aug05,rcd added PCI to memory example 01a,01aug04,rcd written *//* * DESCRIPTION * * This is a simple chained dma test from Local CPU0 RAM to PCI bus. * * This code is for demonstration purposes only * * Usage: pcidmatest() * * NOTE: This example is destructive on the memory defined by DATA_DEST_ADRS */ #include <vxWorks.h>#include <stdio.h>#include <cacheLib.h>#include <memLib.h>#include <usrLib.h>#include <semLib.h>#include <logLib.h>#include <taskLib.h>#include <string.h>#include "config.h"#include "h/drv/discovery_III/gt644xx.h"#include "h/drv/discovery_III/dma/gtDma_dy4.h"#include "h/drv/discovery_III/dma/gtDmaIntCntrl_dy4.h"extern void sysGtDmaWindowSet(void);/* NOTE: hard code to a known high mem area for debugging */#define DATA_SRC_ADRS 0x8000000 /* Source is Local CPU0 RAM location */#define DATA_DEST_ADRS 0x90000000 /* Handle address return by starlink driver on sender node */#define DMA_REC_ADRS 0xe000000 /* Address to hold records in Local CPU0 RAM *//* DMA window size, will use DATA_SRC_ADRS as base */#define DMA_WINDOW_SIZE 0x8000000/* globals */int testinit=0;/************************************************************************ Callback function for PCI DMA completion.***********************************************************************/void dmaCallback (void){ logMsg("DMA Completed!\n",0,0,0,0,0,0);}void dmaErrorCallback1 (void){ logMsg("DMA 1 ERROR: address miss!\n",0,0,0,0,0,0);}void dmaErrorCallback2 (void){ logMsg("DMA 2 ERROR: access protection!\n",0,0,0,0,0,0);}void dmaErrorCallback3 (void){ logMsg("DMA 3 ERROR: record ownership!\n",0,0,0,0,0,0);}/* * dmaShow: visual data check function * */void dmashow(UINT32 dma_block_size) { /* dump the beginning and end of the blocks */ printf("\n Block 0: BEGIN\n"); d( (UINT8 *)DATA_DEST_ADRS,8,4); printf("\n---> Block 0 - 1: BOUNDARY\n"); d( (UINT8 *)DATA_DEST_ADRS+dma_block_size-16,32,4); printf("\n--->Block 1 - 2: BOUNDARY\n"); d( (UINT8 *)DATA_DEST_ADRS+(dma_block_size*2)-16,32,4); printf("\n--->Block 2 - 3: BOUNDARY\n"); d( (UINT8 *)DATA_DEST_ADRS+(dma_block_size*3)-16,32,4); }/**************************************************************************** pcidmatest - loops through a series of simple chained dma's.* * This function builds a chain of 4 dma control records at DMA_REC_ADRS.* Data is DMA'd from DATA_SRC_ADRS to DATA_DEST_ADRS in chains with * block sizes of 0x100 - 0xA00000 in 0x80000 increments.* NOTE: All data at DATA_DEST_ADRS will be overwritten.** This function also demonstrates the use of DMA windows. A DMA window* must be opened for control record, source & destination data access.** RETURNS: N/A* */void pcidmatest(){ DMA_RECORD *gtDmaRecordArray; int result,i; UINT8 *sourceAddress, *destAddress; UINT32 dma_block_size, dma_data_size; dma_block_size = 0x1000; /* start small */ dma_data_size = 4 * dma_block_size; /* hard code to a known area */ sourceAddress = (UINT8 *)DATA_SRC_ADRS; destAddress = (UINT8 *)DATA_DEST_ADRS; gtDmaRecordArray = (DMA_RECORD *)DMA_REC_ADRS; /* set up a dma window which includes the chain records */ /*CPU0 space */ if(gtDmaSetMemorySpace(DMA_WINDOW0, DMA_DRAM_CS0, 0x0, (UINT32) sourceAddress, (UINT32) DMA_WINDOW_SIZE) == false) { printf("\nDMA Memory Window Error\n"); return; } if(gtDmaSetAccessProtect(0, 0, DMA_FULL_ACCESS) == false) { printf("\nDMA Memory Protect Error\n"); return; }/* PCI0 Mem space - Use window1 when you use PCI override option as per Disco manual. Please refer to gtDma_dy4.h.*/ if ( gtDmaSetMemorySpace(DMA_WINDOW1, DMA_PCI_0, DMA_NO_ATTR | DMA_PCI_NO_SWAP | DMA_PCI_MEMORY_SPACE, 0xc0000000, /*this can change according to your BAR value */ 0x10000000)== false) { logMsg("DMA PCI0 Memory Window Setup Error\n",0,0,0,0,0,0); } if(gtDmaSetAccessProtect(DMA_ENG_0, DMA_WINDOW1, DMA_FULL_ACCESS) == false) { logMsg("DMA PCI0 Memory Window Protect Error\n",0,0,0,0,0,0); } /* PCI1 Mem space - Use window2 when you use PCI override option. Please refer to gtDma_dy4.h. The following BAR and size is starlink PMC site 2 on 182 as an example */ if ( gtDmaSetMemorySpace(DMA_WINDOW2, DMA_PCI_1, DMA_NO_ATTR | DMA_PCI_NO_SWAP | DMA_PCI_MEMORY_SPACE, 0x90000000, /* this can change according to your BAR value */ 0x10000000)== false) { logMsg("DMA PCI1 Memory Window Setup Error\n",0,0,0,0,0,0); } if(gtDmaSetAccessProtect(DMA_ENG_0, DMA_WINDOW2, DMA_FULL_ACCESS) == false) { logMsg("DMA PCI1 Memory Window Protect Error\n",0,0,0,0,0,0); } gtDmaRecordArray[0].ByteCnt = (UINT32) dma_block_size; gtDmaRecordArray[0].DestAdd = (UINT32) destAddress+dma_block_size; gtDmaRecordArray[0].SrcAdd = (UINT32) sourceAddress+dma_block_size; gtDmaRecordArray[0].NextRecPtr = (UINT32) >DmaRecordArray[1]; gtDmaRecordArray[1].ByteCnt = (UINT32) dma_block_size; gtDmaRecordArray[1].DestAdd = (UINT32) (destAddress + (2*dma_block_size)); gtDmaRecordArray[1].SrcAdd = (UINT32) (sourceAddress + (2*dma_block_size)); gtDmaRecordArray[1].NextRecPtr = (UINT32) >DmaRecordArray[2]; gtDmaRecordArray[2].ByteCnt = (UINT32) dma_block_size; gtDmaRecordArray[2].DestAdd = (UINT32) (destAddress + (3*dma_block_size)); gtDmaRecordArray[2].SrcAdd = (UINT32) (sourceAddress + (3*dma_block_size)); gtDmaRecordArray[2].NextRecPtr = (UINT32)NULL; printf("\n-----------------------------------------------------------\n"); printf("DMA CHAIN DUMP:\n"); for (i=0;i<3;i++) { printf("\n-------------------------------------------------------\n"); printf("gtDmaRecordArray[%d].ByteCount: 0x%x\n", i, gtDmaRecordArray[i].ByteCnt); printf("gtDmaRecordArray[%d].DestAdd : 0x%x\n", i, gtDmaRecordArray[i].DestAdd); printf("gtDmaRecordArray[%d].SrcAdd: 0x%x\n", i, gtDmaRecordArray[i].SrcAdd); printf("gtDmaRecordArray[%d].NextRecPtr: 0x%x\n", i, gtDmaRecordArray[i].NextRecPtr); } printf("\n"); /* flush dma control records to memory */ cacheFlush(DATA_CACHE, gtDmaRecordArray, 4 * sizeof(DMA_RECORD)); cachePipeFlush(); /* put a pattern in at the src */ memset (sourceAddress,0xA5,dma_data_size); /* clear the destination */ memset (destAddress,0x00,dma_data_size); /* flush dma data to memory */ cacheFlush(DATA_CACHE, destAddress, dma_data_size); cacheFlush(DATA_CACHE, sourceAddress, dma_data_size); cachePipeFlush(); if (testinit == 0) { result = gtDmaIntConnect(DMA_CHAN0_COMPLETION, &dmaCallback,0,0); if (result != OK) printf("Something went wrong with gtDmaIntConnect call\n"); result = gtDmaIntConnect(DMA_CHAN0_ADDR_MISS, &dmaErrorCallback1,0,0); if (result != OK) printf("Something went wrong with gtDmaIntConnect call\n"); result = gtDmaIntConnect(DMA_CHAN0_ACC_PROT, &dmaErrorCallback2,0,0); if (result != OK) printf("Something went wrong with gtDmaIntConnect call\n"); result = gtDmaIntConnect(DMA_CHAN0_OWN, &dmaErrorCallback3,0,0); if (result != OK) printf("Something went wrong with gtDmaIntConnect call\n"); gtDmaIntEnable(DMA_CHAN0_ADDR_MISS); gtDmaIntEnable(DMA_CHAN0_ACC_PROT); gtDmaIntEnable(DMA_CHAN0_OWN); testinit=1; } gtDmaIntEnable(DMA_CHAN0_COMPLETION); gtDmaTransfer2 ( DMA_ENG_0, (UINT32)sourceAddress, (UINT32)destAddress, dma_block_size, DMA_BLOCK_TRANSFER_MODE | DMA_DEST_ADDR_IN_PCI1, >DmaRecordArray[0]); /* force PPC to look at memory */ cacheInvalidate(DATA_CACHE, destAddress, dma_data_size); taskDelay(120); dmashow(dma_block_size); printf("\nTest with dma block size 0x%x bytes COMPLETED\n", dma_block_size); printf("\n==========================================================\n"); taskDelay(120); }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -