a/ We have XILINX FPGA connected to GPMC chip_select 1 and trying to do basic read / write in Asynchronous mode.
a/ We are getting the error of :-
1/ "..Precise External Abort on non-linefetch (0x1018) at 0x4006c000.."
2/ " ..Bus Error"
We are using an sample code in which we are mapping the GPMC chip select area using mmap
(this is from one of TI Google groups)
d/ w.r.t DM816x EVM , if you could let me know :-
a/ At what address range of GPMC (chip select 1) we can map FPGA (8/16 bit asynchronous mode).
b/ Since by NAND driver ( CS_0) already does the GPMC pin muxing , i am assuming no additional
GPMC pin muxing for GPMC would be required.
e/ Please do share if you have any sample /scratch code tested for similar asynchronous mode of GPMC from Linux.
Below is the code
#include <stdint.h> #include <stdio.h> #include <fcntl.h> #include <sys/mman.h> #include <unistd.h> #define GPMC_BASE 0x50000000 #define REGLEN 0x10000000 #define GPMC_REVISION 0x0 #define GPMC_CONFIG1_1 (0X50000090) #define GPMC_CONFIG2_1 (0X50000094) #define GPMC_CONFIG3_1 (0X50000098) #define GPMC_CONFIG4_1 (0X5000009C) #define GPMC_CONFIG5_1 (0X500000A0) #define GPMC_CONFIG6_1 (0X500000A4) #define GPMC_CONFIG7_1 (0X500000A8) #define GPMC_CHIPSELECTCONFIGDISPLACEMENT (0x30 / 4) #define GPMC_CONFIG1 (0x60 / 4) #define GPMC_CONFIG2 (0x64 / 4) #define GPMC_CONFIG3 (0x68 / 4) #define GPMC_CONFIG4 (0x6c / 4) #define GPMC_CONFIG5 (0x70 / 4) #define GPMC_CONFIG6 (0x74 / 4) #define GPMC_CONFIG7 (0x78 / 4) static volatile uint32_t* registers = NULL; static volatile uint8_t* extbus = NULL; static unsigned int valid = 0; static int devmemfd = -1; static unsigned int size = 0x100; static unsigned int revision_id = 0; //map memory of length "len" at offset "offset" static void* util_mapmemoryblock(off_t offset, size_t len) { devmemfd = open("/dev/mem", O_RDWR | O_SYNC); void* registers = mmap(NULL, len, PROT_READ | PROT_WRITE, MAP_SHARED, devmemfd, offset); if (registers == MAP_FAILED) { printf("\n[GPMC]: Failed in getting Memory acess \n"); }else{ printf("\n[GPMC]: Sucess in getting Memory acess \n"); } return registers; } static void util_unmapmemoryblock(void* block, size_t len) { printf("\n[GPMC]: Releasing the amemory acess \n"); munmap((void*) block, len); if (devmemfd != -1) { printf("\n[GPMC]: Closing the interface file \n"); close(devmemfd); } } static void gpmc_mapregisters() { registers = (uint32_t*) util_mapmemoryblock(GPMC_BASE, REGLEN); } static void gpmc_unmapregisters() { util_unmapmemoryblock((void*) registers, REGLEN); } static void gpmc_setup(void) { printf("\n[GPMC]: Getting Memory acess for GPMC configuration register \n"); gpmc_mapregisters(); if (registers != MAP_FAILED) { valid =1; int chipselect = 1; int displacement = GPMC_CHIPSELECTCONFIGDISPLACEMENT * chipselect; printf("\n[GPMC]: Initial revision_id is %X \n",revision_id); revision_id = *(registers + GPMC_REVISION); printf("\n[GPMC]: Updated revision_id is %X \n",revision_id); printf("\n[GPMC]: Disable before playing with the registers \n"); *(registers + displacement + GPMC_CONFIG7) = 0x00000000; printf("\n[GPMC]: No burst, async, 8-bit, non multiplexed \n"); *(registers + displacement + GPMC_CONFIG1) = 0x00000000; printf("\n[GPMC]: Assert CS on fclk 0, deassert CS on fclk 3 \n"); *(registers + displacement + GPMC_CONFIG2) = 0x00000300; printf("\n[GPMC]: Unused ADV/ALE \n"); *(registers + displacement + GPMC_CONFIG3) = 0x00000000; printf("\n[GPMC]: Assert OE on fclk 1, deassert OE on fclk 3 \n"); *(registers + displacement + GPMC_CONFIG4) = 0x00000301; printf("\n[GPMC]: Data valid on fclk 2, cycle time 3 fclks \n"); *(registers + displacement + GPMC_CONFIG5) = 0x00020003; printf("\n[GPMC]: No back to back cycle restrictions \n"); *(registers + displacement + GPMC_CONFIG6) = 0x00000000; printf("\n[GPMC]: CS1: Set base address 0x02000000, 16MB region, and enable CS \n"); *(registers + displacement + GPMC_CONFIG7) = 0x00000f42; printf("\n[GPMC]: Releasing Memory acess for GPMC configuration register \n"); gpmc_unmapregisters(); } } void bus_init() { // Configure the GPMC gpmc_setup(); if(valid == 1 ){ //Configure the Chip Select for 256 Bytes printf("\n[GPMC]: Getting Memory acess for FPGA \n"); extbus = (uint8_t*) util_mapmemoryblock(0x01000000, size); }else { printf("\n[GPMC]: Configuration access was invalid \n"); } } void bus_writebyte(uint8_t address, uint8_t data) { *(unsigned char *)(extbus + address) = data; } uint32_t bus_readbyte(uint8_t address) { return *(unsigned char *)(extbus + address); } void bus_shutdown() { printf("\n[GPMC]: Releasing Memory acess for FPGA & doing shutdown\n"); util_unmapmemoryblock((void*) extbus, size); } int main() { int i = 0; printf("\n[GPMC]: Calling the Init Function now _VER_2.1\n"); bus_init(); if (extbus == NULL){ printf("\n[GPMC]: The FPGA memory is not yet mapped \n"); goto exit_code; }else{ printf("\n[GPMC]: The FPGA memory is mapped @ %p \n",extbus); } printf("\n[GPMC]: ===========================================\n\n"); for (i; i < 10; i++) { printf("\n[GPMC]: Read byte at address %x: %X\n", i, bus_readbyte(i)); } printf("\n[GPMC]: ===========================================\n\n"); bus_shutdown(); printf("\n[GPMC]: Code terminates \n"); return(0); exit_code : printf("\n[GPMC]: Code terminates \n"); return(0); } /* And the OUTPUT LOG is root@dm816x-evm:~# root@dm816x-evm:~# root@dm816x-evm:~# ./gpmc_test [GPMC]: Calling the Init Function now _VER_2.1 [GPMC]: Getting Memory acess for GPMC configuration register [GPMC]: Sucess in getting Memory acess [GPMC]: Initial revision_id is 0 [GPMC]: Updated revision_id is 60 [GPMC]: Disable before playing with theUnhandled fault: Precise External Abort on non-linefetch (0x1018) at 0x4006c000 registers [GPMC]: No burst, async, 8-bit, non multiplexed [GPMC]: Assert CS on fclk 0, deassert CS on fclk 3 [GPMC]: Unused ADV/ALE [GPMC]: Assert OE on fclk 1, deassert OE on fclk 3 [GPMC]: Data valid on fclk 2, cycle time 3 fclks [GPMC]: No back to back cycle restrictions [GPMC]: CS1: Set base address 0x02000000, 16MB region, and enable CS [GPMC]: Releasing Memory acess for GPMC configuration register [GPMC]: Releasing the amemory acess [GPMC]: Closing the interface file [GPMC]: Getting Memory acess for FPGA [GPMC]: Sucess in getting Memory acess [GPMC]: The FPGA memory is mapped @ 0x4006c000 [GPMC]: =========================================== Bus error root@dm816x-evm:~# root@dm816x-evm:~# root@dm816x-evm:~# root@dm816x-evm:~# root@dm816x-evm:~# */
Thanks
Ashish.