Forum Discussion
Altera PCI Express Development Kit: Linux DMA Driver
Hi,
I am a newbie to FPGA design and implementation. While installing the PCI express board on LINUX machine, I don't see Demo application driver for DMA read and write for LINUX (Manual talks about windows installation). I want to generate DMA read and write in Linux box. Does anyone have pointer to a sample application, driver or sof file for the same. Let me know if I am wrong in understanding. Thanks in advance. -Vineet64 Replies
- Altera_Forum
Honored Contributor
Your bar_min_len should be alright. I kept mine the same length (as in {32768,0,256,0,0,0}) as it was before, but I've tried both ways and I'm successful in either case. Have your tried running the driver against the reference design provided with the board? That design was compiled in 7.2, which works for me on my computer, running 32 bit Red Hat. In fact, 7.2 & 9.0 are the only software versions I can get to work... lspci won't show the board using 8.x.
- Altera_Forum
Honored Contributor
--- Quote Start --- Your bar_min_len should be alright. I kept mine the same length (as in {32768,0,256,0,0,0}) as it was before, but I've tried both ways and I'm successful in either case. Have your tried running the driver against the reference design provided with the board? That design was compiled in 7.2, which works for me on my computer, running 32 bit Red Hat. In fact, 7.2 & 9.0 are the only software versions I can get to work... lspci won't show the board using 8.x. --- Quote End --- I am not sure what you mean by reference design. I am using following: www.altera.com/literature/an/an456.pdf With windows driver it works. Also, in Linux with 8.x, I can see the board using lspci. Thanks again Rob. - Altera_Forum
Honored Contributor
I tried 9.0 version and it gives me same error :( Any further pointers. Likewise ??
- Altera_Forum
Honored Contributor
Oh, I've never even seen that before, but I think AN456 is the same as what I'm talking about, which came on a disc (windoze) with the AGX development kit. Furthermore, when you create a new PCIe megafunction, Quartus generates a chaining dma example design in <mf_name>_examples/chaining_dma. I use that project file and set the device and pin-outs according to these reference designs. Also, I can only get it to work by using data/descriptor, and in the aforementioned verisions. Are you using one *.pof from the application note, or are you compiling and building your own?
- Altera_Forum
Honored Contributor
--- Quote Start --- Oh, I've never even seen that before, but I think AN456 is the same as what I'm talking about, which came on a disc (windoze) with the AGX development kit. Furthermore, when you create a new PCIe megafunction, Quartus generates a chaining dma example design in <mf_name>_examples/chaining_dma. I use that project file and set the device and pin-outs according to these reference designs. Also, I can only get it to work by using data/descriptor, and in the aforementioned verisions. Are you using one *.pof from the application note, or are you compiling and building your own? --- Quote End --- I using default and haven't tried building my own - Altera_Forum
Honored Contributor
Alright:
I downloaded the application note and tried out all 4 of the .sof files provided for Arria GX... x1 Legacy: no device in lspci x4 Legacy: device shows, driver hangs with EPLAST=44 on the 1st memory transfer. x1 ST: no device in lspci x4 ST: no device in lspci So I think I have more or less duplicated your environment with the x4 legacy example. The quartus settings files for these projects indicate that the application note was built using Quartus 8.0 sp1. You can use any version to program the device, but in less you recompile the project AND the megafunction, the design remains 8.0, which is error-prone according to the linux driver authors. The best advice I can give you is: 1. Try the 7.2 High Performance design that is on the CD that comes with the AGX development board. For me the linux driver's memory test passes with that example. 2. Instantiate a PCIe megafunction in quartus, open the project it builds in <mf_name>_examples/chainingdma, set the device and pins, and use that design. This is the route I take, but it only works using versions 7.2 or 9.0. - Altera_Forum
Honored Contributor
--- Quote Start --- Alright: I downloaded the application note and tried out all 4 of the .sof files provided for Arria GX... x1 Legacy: no device in lspci x4 Legacy: device shows, driver hangs with EPLAST=44 on the 1st memory transfer. x1 ST: no device in lspci x4 ST: no device in lspci So I think I have more or less duplicated your environment with the x4 legacy example. The quartus settings files for these projects indicate that the application note was built using Quartus 8.0 sp1. You can use any version to program the device, but in less you recompile the project AND the megafunction, the design remains 8.0, which is error-prone according to the linux driver authors. The best advice I can give you is: 1. Try the 7.2 High Performance design that is on the CD that comes with the AGX development board. For me the linux driver's memory test passes with that example. 2. Instantiate a PCIe megafunction in quartus, open the project it builds in <mf_name>_examples/chainingdma, set the device and pins, and use that design. This is the route I take, but it only works using versions 7.2 or 9.0. --- Quote End --- THanks Rob. I will get back to you with updates - Altera_Forum
Honored Contributor
Rob, Is following line is redundant in driver ?
irq_line = dev->irq; I mean why is this needed when pci_read_config_byte is called to get the irq_line - Altera_Forum
Honored Contributor
Yes, it looks like irq_line is assigned two different values, first from reading the appropriate configuration byte, then with the line above. Probably left over from testing the driver. I would say that "irq_line = dev->irq;" is the more important line in the driver, since the variable discards what it receives from the configuration byte and uses this value. So you could delete the pci_read_config_byte line and the printk statement that prints its value. But it provides a nice little bit of debugging info and it works just fine.
- Altera_Forum
Honored Contributor
--- Quote Start --- Yes, it looks like irq_line is assigned two different values, first from reading the appropriate configuration byte, then with the line above. Probably left over from testing the driver. I would say that "irq_line = dev->irq;" is the more important line in the driver, since the variable discards what it receives from the configuration byte and uses this value. So you could delete the pci_read_config_byte line and the printk statement that prints its value. But it provides a nice little bit of debugging info and it works just fine. --- Quote End --- Well it didn't make any difference though. In mean time, i have tested it in 32-bit Linux. Log is as below (it is with Quartus 8.0/8.1/9.0): ======================================= altpciechdma init(), built at Mar 20 2009 22:14:41 probe(dev = 0xf79c5400, pciid = 0xf8b77c20) Testing probe function probe() ape = 0xf63196c0 sizeof(struct ape_chdma_table) = 4096. table_virt = 0xfffffffff3e57000, table_bus = 0x 33e57000. ACPI: PCI Interrupt 0000:06:00.0[A] -> GSI 16 (level, low) -> IRQ 16 PCI: Setting latency timer of device 0000:06:00.0 to 64 Enabled MSI interrupting. RevisionID is supported by this driver 0x1 VendorID is supported by this driver 0x1172 DeviceID is supported by this driver 0xe001 Could not set 64-bit DMA mask. Using a 32-bit DMA mask. IRQ pin# 1 (0=none, 1=INTA#...4=INTD#). IRQ line# 11. IRQ line post assigning# 216. Succesfully requested IRQ# 216 with dev_id 0xf63196c0 BAR0 0xf0000000-0xf0ffffff flags 0x0000120c BAR2 0xb7200000-0xb72003ff flags 0x00000200 BAR[0] mapped at 0xf8b60000 with length 32768(/16777216). BAR[2] mapped at 0xf8b58000 with length 256(/1024). bar_tests(), PAGE_SIZE = 0x1000 write_header = 0xf8b58000. read_header = 0xf8b58010. &write_header->w3 (intiates DMA) = 0xf8b5800c &read_header->w3 (initiates DMA) = 0xf8b5801c ape->table_virt = 0xf3e57000. Allocated cache-coherent DMA buffer (virtual address = 0xfffffffff3e70000, bus address = 0x0000000033e70000). writing read header 0x000400ff to 0xf8b58010 writing higher bus address 0x00000000 to 0xf8b58014 writing lower bus address 0x33e57000 to 0xf8b58018 Flush posted writes Start DMA read writing (to w3 initiate DMA) 0x000000fe to 0xf8b5801c EPLAST(w3 register ORed) = 64222 POLL FOR READ: EPLAST = 64222, n = 254 EPLAST = 9, n = 254 EPLAST = 20, n = 254 EPLAST = 31, n = 254 EPLAST = 42, n = 254 EPLAST = 52, n = 254 EPLAST = 63, n = 254 EPLAST = 73, n = 254 EPLAST = 84, n = 254 EPLAST = 94, n = 254 EPLAST = 105, n = 254 EPLAST = 116, n = 254 EPLAST = 127, n = 254 EPLAST = 137, n = 254 EPLAST = 148, n = 254 EPLAST = 159, n = 254 EPLAST = 169, n = 254 EPLAST = 180, n = 254 EPLAST = 190, n = 254 EPLAST = 201, n = 254 EPLAST = 211, n = 254 EPLAST = 222, n = 254 EPLAST = 232, n = 254 EPLAST = 243, n = 254 EPLAST = 254, n = 254 DONE# IRQs during transfer: 2 Start DMA write POLL FOR WRITE: EPLAST = 64222, n = 254 EPLAST = 9, n = 254 EPLAST = 21, n = 254 EPLAST = 32, n = 254 EPLAST = 43, n = 254 EPLAST = 55, n = 254 EPLAST = 66, n = 254 EPLAST = 77, n = 254 EPLAST = 88, n = 254 EPLAST = 100, n = 254 EPLAST = 111, n = 254 EPLAST = 122, n = 254 EPLAST = 133, n = 254 EPLAST = 145, n = 254 EPLAST = 156, n = 254 EPLAST = 167, n = 254 EPLAST = 178, n = 254 EPLAST = 189, n = 254 EPLAST = 201, n = 254 EPLAST = 212, n = 254 EPLAST = 223, n = 254 EPLAST = 234, n = 254 EPLAST = 245, n = 254 EPLAST = 254, n = 254 DONE# IRQs during transfer: 1 [f3e70000] = 0xf3e70000 != [f3e72000] = 0x00000000 ?! [f3e70004] = 0xf3e70004 != [f3e72004] = 0x00000000 ?! [f3e70008] = 0xf3e70008 != [f3e72008] = 0x00000000 ?! [f3e7000c] = 0xf3e7000c != [f3e7200c] = 0x00000000 ?! [f3e70010] = 0xf3e70010 != [f3e72010] = 0x00000000 ?! [f3e70014] = 0xf3e70014 != [f3e72014] = 0x00000000 ?! [f3e70018] = 0xf3e70018 != [f3e72018] = 0x00000000 ?! [f3e7001c] = 0xf3e7001c != [f3e7201c] = 0x00000000 ?! [f3e70020] = 0xf3e70020 != [f3e72020] = 0x00000000 ?! ---more errors follow! not printed--- DMA loop back test FAILED. bar_tests() end, result -1 probe() successful. altpciechdma 0