Skip to content
GitLab
Menu
Projects
Groups
Snippets
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
tapasco
tapasco
Commits
8a5068c7
Commit
8a5068c7
authored
Jun 01, 2017
by
Jens Korinth
Browse files
Backport new VC709 driver to Tapasco
parent
4f9d515b
Changes
11
Expand all
Hide whitespace changes
Inline
Side-by-side
platform/vc709/module/Makefile
View file @
8a5068c7
...
...
@@ -6,7 +6,7 @@ obj-m := ffLink.o
# composition of files needed to compile
# one can exchange dual_dma_ctrl with cdma_dma_ctrl, when dma engine from Xilinx is used
ffLink-objs
:=
pcie_device.o
dual
_dma_ctrl.o char_device_dma.o char_device_user.o ffLink_driver.o
ffLink-objs
:=
pcie_device.o
blue
_dma_ctrl.o char_device_dma.o char_device_user.o ffLink_driver.o
dual_dma_ctrl.o dma_ctrl.o
# Path to kernel headers for compilation (path to home can be specific to os)
LNX
=
$(
shell
uname
-r
)
...
...
platform/vc709/module/
cdma
_dma_ctrl.c
→
platform/vc709/module/
blue
_dma_ctrl.c
View file @
8a5068c7
//
// Copyright (C) 201
4 David de la Chevallerie
, TU Darmstadt
// Copyright (C) 201
7 Jaco A. Hofmann
, TU Darmstadt
//
// This file is part of Tapasco (TPC).
//
...
...
@@ -17,8 +17,8 @@
// along with Tapasco. If not, see <http://www.gnu.org/licenses/>.
//
/**
* @file
cdma
_dma_ctrl.c
* @brief Implementation of
Xilinx
dma engine specific code
* @file
dual
_dma_ctrl.c
* @brief Implementation of
custom
dma engine specific code
Strips the layout of the dma-registers and setup stuff to start a dma transfer
in addition calls to acknowledge the interrupt in hw is given
* */
...
...
@@ -30,21 +30,13 @@
/******************************************************************************/
/* Register Map and commands */
#define REG_CDMACR 0x00
/* slv_reg0 = CDMA Control */
#define REG_CDMASR 0x04
/* slv_reg1 = CDMA Status */
#define REG_CURDESC_PNTR 0x08
/* slv_reg2 = Current Descriptor Pointer */
#define REG_CURDESC_PNTR_MSB 0x0C
/* slv_reg3 = Current Descriptor Pointer (MSB 32 bits) */
#define REG_TAILDESC_PNTR 0x10
/* slv_reg4 = Tail Descriptor Pointer */
#define REG_TAILDESC_PNTR_MSB 0x14
/* slv_reg5 = Tail Descriptor Pointer (MSB 32 bits) */
#define REG_SA 0x18
/* slv_reg6 = Source Address */
#define REG_SA_MSB 0x1C
/* slv_reg7 = Source Address (MSB 32 bits) */
#define REG_DA 0x20
/* slv_reg8 = Destination Address */
#define REG_DA_MSB 0x24
/* slv_reg9 = Destination Address (MSB 32 bits) */
#define REG_BTT 0x28
/* slv_regA = Bytes to Transfer */
#define REG_HOST_ADDR 0x00
/* slv_reg0 = PCIe addr */
#define REG_FPGA_ADDR 0x08
/* slv_reg1 = FPGA addr */
#define REG_BTT 0x10
/* slv_reg2 = bytes to transfer */
#define REG_CMD 0x20
/* slv_reg3 = CMD */
#define CMD_IRQ_EN 0x00001000
/* enables interrupt for transfers in control register */
#define CMD_ACK 0x00001000
/* acknowledge data transfer to toggle interrupt in status register */
#define PCIE_OFF 0x00000008
/* offset to address pcie core */
#define CMD_READ 0x10001000
/* from m64 fpga memory to m64 host memory */
#define CMD_WRITE 0x10000001
/* from m64 host memory to m64 fpga memory */
/* mutex to sequentialize access to dma registers */
//static DEFINE_MUTEX(dma_regs_mutex);
...
...
@@ -52,73 +44,14 @@
/******************************************************************************/
/* functions for irq-handling */
/**
* @brief Acknowledge interrupt in hardware and wake up corresponding process
* @param i minor node corresponding to this irq
* @return none
* */
void
ack_irq
(
int
i
)
{
fflink_info
(
"Handle device number %d
\n
"
,
i
);
/* ack interrupt */
pcie_writel
(
CMD_ACK
,
get_dev_addr
(
i
)
+
REG_CDMASR
);
/* Set priv data for more minor nodes accordingly */
wake_up_queue
(
i
);
}
/**
* @brief Interrupt handler for dma engine 0
* @param irq Interrupt number of calling line
* @param dev_id magic number for interrupt sharing (not needed)
* @return Tells OS, that irq is handled properly
* */
irqreturn_t
intr_handler_dma_0
(
int
irq
,
void
*
dev_id
)
{
fflink_info
(
"Interrupt called with irq %d
\n
"
,
irq
);
ack_irq
(
0
);
return
IRQ_HANDLED
;
}
/**
* @brief Interrupt handler for dma engine 1
* @param irq Interrupt number of calling line
* @param dev_id magic number for interrupt sharing (not needed)
* @return Tells OS, that irq is handled properly
* */
irqreturn_t
intr_handler_dma_1
(
int
irq
,
void
*
dev_id
)
irqreturn_t
blue_dma_intr_handler
(
int
irq
,
void
*
dev_id
)
{
fflink_info
(
"Interrupt called with irq %d
\n
"
,
irq
);
ack_irq
(
1
);
return
IRQ_HANDLED
;
}
/**
* @brief Interrupt handler for dma engine 2
* @param irq Interrupt number of calling line
* @param dev_id magic number for interrupt sharing (not needed)
* @return Tells OS, that irq is handled properly
* */
irqreturn_t
intr_handler_dma_2
(
int
irq
,
void
*
dev_id
)
{
fflink_info
(
"Interrupt called with irq %d
\n
"
,
irq
);
ack_irq
(
2
);
return
IRQ_HANDLED
;
}
/**
* @brief Interrupt handler for dma engine 3
* @param irq Interrupt number of calling line
* @param dev_id magic number for interrupt sharing (not needed)
* @return Tells OS, that irq is handled properly
* */
irqreturn_t
intr_handler_dma_3
(
int
irq
,
void
*
dev_id
)
{
fflink_info
(
"Interrupt called with irq %d
\n
"
,
irq
);
ack_irq
(
3
);
return
IRQ_HANDLED
;
}
...
...
@@ -132,24 +65,22 @@ irqreturn_t intr_handler_dma_3(int irq, void * dev_id)
* @param device_base_addr Address of dma engine registers
* @return none
* */
void
transmit_from_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
)
void
blue_dma_
transmit_from_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
)
{
fflink_info
(
"dev_buf %lX dma_handle %lX
\n
size %d dev_base %lX
\n
"
,
(
unsigned
long
)
device_buffer
,
(
unsigned
long
)
host_handle
,
btt
,
(
unsigned
long
)
device_base_addr
);
//if(mutex_lock_interruptible(&dma_regs_mutex))
// fflink_warn("got killed while aquiring the mutex\n");
/* activate interrupts */
pcie_writel
(
CMD_IRQ_EN
,
device_base_addr
+
REG_CDMACR
);
/* SA */
pcie_writel
((
unsigned
long
)
device_buffer
,
device_base_addr
+
REG_SA
);
pcie_writel
(
0
,
device_base_addr
+
REG_SA_MSB
);
pcie_writel
((
unsigned
long
)
device_buffer
,
device_base_addr
+
REG_FPGA_ADDR
);
/* DA */
pcie_writel
(
host_handle
,
device_base_addr
+
REG_DA
);
pcie_writel
(
PCIE_OFF
,
device_base_addr
+
REG_DA_MSB
);
pcie_writel
(
host_handle
,
device_base_addr
+
REG_HOST_ADDR
);
/* btt */
pcie_writel
(
btt
,
device_base_addr
+
REG_BTT
);
/* presvious data have to be written first */
wmb
();
/*
btt and
start */
pcie_writel
(
btt
,
device_base_addr
+
REG_
BTT
);
/* start
cmd
*/
pcie_writel
(
CMD_READ
,
device_base_addr
+
REG_
CMD
);
//mutex_unlock(&dma_regs_mutex);
}
...
...
@@ -162,24 +93,22 @@ void transmit_from_device(void * device_buffer, dma_addr_t host_handle, int btt,
* @param device_base_addr Address of dma engine registers
* @return none
* */
void
transmit_to_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
)
void
blue_dma_
transmit_to_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
)
{
fflink_info
(
"dev_buf %lX dma_handle %lX
\n
size %d dev_base %lX
\n
"
,
(
unsigned
long
)
device_buffer
,
(
unsigned
long
)
host_handle
,
btt
,
(
unsigned
long
)
device_base_addr
);
//if(mutex_lock_interruptible(&dma_regs_mutex))
// fflink_warn("got killed while aquiring the mutex\n");
/* activate interrupts */
pcie_writel
(
CMD_IRQ_EN
,
device_base_addr
+
REG_CDMACR
);
/* SA */
pcie_writel
(
host_handle
,
device_base_addr
+
REG_SA
);
pcie_writel
(
PCIE_OFF
,
device_base_addr
+
REG_SA_MSB
);
pcie_writel
(
host_handle
,
device_base_addr
+
REG_HOST_ADDR
);
/* DA */
pcie_writel
((
unsigned
long
)
device_buffer
,
device_base_addr
+
REG_DA
);
pcie_writel
(
0
,
device_base_addr
+
REG_DA_MSB
);
pcie_writel
((
unsigned
long
)
device_buffer
,
device_base_addr
+
REG_FPGA_ADDR
);
/* btt */
pcie_writel
(
btt
,
device_base_addr
+
REG_BTT
);
/* presvious data have to be written first */
wmb
();
/*
btt and
start */
pcie_writel
(
btt
,
device_base_addr
+
REG_
BTT
);
/* start
cmd
*/
pcie_writel
(
CMD_WRITE
,
device_base_addr
+
REG_
CMD
);
//mutex_unlock(&dma_regs_mutex);
}
...
...
platform/vc709/module/char_device_dma.c
View file @
8a5068c7
This diff is collapsed.
Click to expand it.
platform/vc709/module/char_device_dma.h
View file @
8a5068c7
...
...
@@ -73,53 +73,31 @@
/******************************************************************************/
/* number of device, which will be created for dma engines */
#define FFLINK_DMA_NODES 1
/* activate double buffering ( == 1) */
#define FFLINK_DOUBLE_BUFFERING 2
/* physical address of dma core in register map from vivado */
#define DMA_BASE_ADDR_0 0x300000
#define DMA_BASE_ADDR_1 0x310000
#define DMA_BASE_ADDR_2 0x320000
#define DMA_BASE_ADDR_3 0x330000
#define AXI_CTRL_BASE_ADDR 0x100000
/* BRAM standard address */
#define RAM_BASE_ADDR_0 0x80000000
#define RAM_BASE_ADDR_1 0xA0000000
#define RAM_BASE_ADDR_2 0xC0000000
#define RAM_BASE_ADDR_3 0xE0000000
/* to change buffer_size increase or decrease the order of pages */
#define BUFFER_ORDER (MAX_ORDER -1)
#define BUFFER_SIZE (PAGE_SIZE * (1 << BUFFER_ORDER))
/* change size, when double buffering becomes activated */
#define DOUBLE_BUFFER_LIMIT 262144
#define BUFFER_SIZE_USED (PAGE_SIZE * (1 << (MAX_ORDER -3)))
/* device name to register fops with
* fops will append a number to name for multiple minor nodes */
#define FFLINK_DMA_NAME "FFLINK_DMA_DEVICE"
/* Count of buffers allocated for each device in each direction */
#define PBUF_SIZE 3
/******************************************************************************/
/* struct array to hold data over multiple fops-calls */
struct
priv_data_struct
{
unsigned
int
minor
;
struct
page
*
pbuf_h2l
[
PBUF_SIZE
];
struct
page
*
pbuf_l2h
[
PBUF_SIZE
];
void
*
kvirt_pbuf_h2l
[
PBUF_SIZE
];
void
*
kvirt_pbuf_l2h
[
PBUF_SIZE
];
dma_addr_t
dma_handle_h2l
[
PBUF_SIZE
];
dma_addr_t
dma_handle_l2h
[
PBUF_SIZE
];
void
*
kvirt_h2l
;
void
*
kvirt_l2h
;
dma_addr_t
dma_handle_h2l
;
dma_addr_t
dma_handle_l2h
;
void
*
mem_addr_l2h
;
void
*
mem_addr_h2l
;
...
...
@@ -133,9 +111,6 @@ struct priv_data_struct {
unsigned
int
cache_lsize
;
unsigned
int
cache_mask
;
struct
mutex
mmap_rbuf_mutex
;
struct
mutex
mmap_wbuf_mutex
;
};
/******************************************************************************/
...
...
@@ -146,28 +121,21 @@ static int dma_close(struct inode *, struct file *);
static
long
dma_ioctl
(
struct
file
*
,
unsigned
int
,
unsigned
long
);
static
ssize_t
dma_read
(
struct
file
*
,
char
__user
*
,
size_t
count
,
loff_t
*
);
static
ssize_t
dma_write
(
struct
file
*
,
const
char
__user
*
,
size_t
count
,
loff_t
*
);
static
int
dma_mmap
(
struct
file
*
filp
,
struct
vm_area_struct
*
vma
);
/******************************************************************************/
/* helper functions called for sys-calls */
static
void
dma_page_to_virt
(
struct
priv_data_struct
*
p
);
static
unsigned
int
dma_cache_fit
(
unsigned
int
btt
);
static
int
dma_alloc_pbufs
(
struct
page
*
p
[]
,
dma_addr_t
handle
[]
,
gfp_t
,
int
);
static
void
dma_free_pbufs
(
struct
page
*
p
[]
,
dma_addr_t
handle
[]
,
int
direction
);
static
int
dma_alloc_pbufs
(
void
*
*
p
,
dma_addr_t
*
handle
,
gfp_t
zone
,
int
direction
);
static
void
dma_free_pbufs
(
void
*
p
,
dma_addr_t
handle
,
int
direction
);
static
void
transmit_to_user
(
void
*
,
void
*
,
dma_addr_t
,
int
);
static
void
transmit_from_user
(
void
*
,
void
*
,
dma_addr_t
,
int
);
static
unsigned
int
calc_transfer_size
(
int
count
);
static
void
switch_index
(
unsigned
int
*
a
,
unsigned
int
*
b
);
/******************************************************************************/
/* overload function to exchange bounce-/double-buffering */
static
int
read_with_double
(
int
count
,
char
__user
*
buf
,
void
*
mem_addr
,
struct
priv_data_struct
*
p
);
static
int
read_with_bounce
(
int
count
,
char
__user
*
buf
,
void
*
mem_addr
,
struct
priv_data_struct
*
p
);
static
inline
int
read_device
(
int
count
,
char
__user
*
buf
,
void
*
mem_addr
,
struct
priv_data_struct
*
p
);
static
int
write_with_double
(
int
count
,
const
char
__user
*
buf
,
void
*
mem_addr
,
struct
priv_data_struct
*
p
);
static
int
write_with_bounce
(
int
count
,
const
char
__user
*
buf
,
void
*
mem_addr
,
struct
priv_data_struct
*
p
);
static
inline
int
write_device
(
int
count
,
const
char
__user
*
buf
,
void
*
mem_addr
,
struct
priv_data_struct
*
p
);
...
...
platform/vc709/module/common/device_pcie.h
View file @
8a5068c7
...
...
@@ -43,6 +43,9 @@ struct pci_dev* get_pcie_dev(void);
void
pcie_writel
(
unsigned
long
data
,
void
*
addr
);
unsigned
long
pcie_readl
(
void
*
addr
);
void
pcie_writel_bar2
(
unsigned
long
data
,
void
*
addr
);
unsigned
long
pcie_readl_bar2
(
void
*
addr
);
/******************************************************************************/
#endif // __DEVICE_PCIE_H
platform/vc709/module/common/dma_ctrl.h
View file @
8a5068c7
...
...
@@ -67,12 +67,10 @@
/******************************************************************************/
void
dma_ctrl_init
(
void
*
device_base_addr
);
/* interrupt handler used by dma engines registered in pcie_device.c */
void
ack_irq
(
int
i
);
irqreturn_t
intr_handler_dma_0
(
int
irq
,
void
*
dev_id
);
irqreturn_t
intr_handler_dma_1
(
int
irq
,
void
*
dev_id
);
irqreturn_t
intr_handler_dma_2
(
int
irq
,
void
*
dev_id
);
irqreturn_t
intr_handler_dma_3
(
int
irq
,
void
*
dev_id
);
irqreturn_t
intr_handler_dma
(
int
irq
,
void
*
dev_id
);
/* setting registers to start dma transfer specific to used engine (Xilinx, custom) */
void
transmit_from_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
);
...
...
@@ -80,4 +78,13 @@ void transmit_to_device(void * device_buffer, dma_addr_t host_handle, int btt, v
/******************************************************************************/
/* DMA Specific implementations */
irqreturn_t
blue_dma_intr_handler
(
int
irq
,
void
*
dev_id
);
void
blue_dma_transmit_from_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
);
void
blue_dma_transmit_to_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
);
irqreturn_t
dual_dma_intr_handler_dma
(
int
irq
,
void
*
dev_id
);
void
dual_dma_transmit_from_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
);
void
dual_dma_transmit_to_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
);
#endif // __DMA_CTRL_H
platform/vc709/module/dma_ctrl.c
0 → 100644
View file @
8a5068c7
//
// Copyright (C) 2017 Jaco A. Hofmann, TU Darmstadt
//
// This file is part of Tapasco (TPC).
//
// Tapasco is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Tapasco is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with Tapasco. If not, see <http://www.gnu.org/licenses/>.
//
/**
* @file dual_dma_ctrl.c
* @brief Implementation of custom dma engine specific code
Strips the layout of the dma-registers and setup stuff to start a dma transfer
in addition calls to acknowledge the interrupt in hw is given
* */
/******************************************************************************/
#include "common/dma_ctrl.h"
/******************************************************************************/
/******************************************************************************/
/* functions for irq-handling */
#define REG_ID 0x18
typedef
enum
{
DMA_USED_DUAL
=
0
,
DMA_USED_BLUE
=
1
}
dma_used_t
;
typedef
irqreturn_t
(
*
dma_intr_handler
)(
int
,
void
*
);
typedef
void
(
*
dma_from_device
)(
void
*
,
dma_addr_t
,
int
,
void
*
);
typedef
void
(
*
dma_to_device
)(
void
*
,
dma_addr_t
,
int
,
void
*
);
typedef
struct
{
dma_intr_handler
intr
;
dma_from_device
from_dev
;
dma_to_device
to_dev
;
}
fflink_dma_t
;
static
dma_used_t
dma_used
;
static
const
fflink_dma_t
fflink_dma
[]
=
{
[
DMA_USED_DUAL
]
=
{
dual_dma_intr_handler_dma
,
dual_dma_transmit_from_device
,
dual_dma_transmit_to_device
},
[
DMA_USED_BLUE
]
=
{
blue_dma_intr_handler
,
blue_dma_transmit_from_device
,
blue_dma_transmit_to_device
}
};
void
dma_ctrl_init
(
void
*
device_base_addr
)
{
if
(
pcie_readl
(
device_base_addr
+
REG_ID
)
==
0xE5A0023
)
{
dma_used
=
DMA_USED_BLUE
;
fflink_warn
(
"Detected BlueDMA
\n
"
);
}
else
{
dma_used
=
DMA_USED_DUAL
;
fflink_warn
(
"Detected DualDMA
\n
"
);
}
}
/**
* @brief Interrupt handler for dma engine 0
* @param irq Interrupt number of calling line
* @param dev_id magic number for interrupt sharing (not needed)
* @return Tells OS, that irq is handled properly
* */
irqreturn_t
intr_handler_dma
(
int
irq
,
void
*
dev_id
)
{
fflink_info
(
"Interrupt called with irq %d
\n
"
,
irq
);
fflink_dma
[
dma_used
].
intr
(
irq
,
dev_id
);
wake_up_queue
(
0
);
return
IRQ_HANDLED
;
}
/******************************************************************************/
/**
* @brief Sets register of dma_engine to start a transfer from FPGA to Main memory
* @param device_buffer FPGA memory address
* @param host_handle Handle for platform independent memory address
* @param btt Bytes to transfer
* @param device_base_addr Address of dma engine registers
* @return none
* */
void
transmit_from_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
)
{
fflink_dma
[
dma_used
].
from_dev
(
device_buffer
,
host_handle
,
btt
,
device_base_addr
);
}
/**
* @brief Sets register of dma_engine to start a transfer from Main memory to FPGA
* @param device_buffer FPGA memory address
* @param host_handle Handle for platform independent memory address
* @param btt Bytes to transfer
* @param device_base_addr Address of dma engine registers
* @return none
* */
void
transmit_to_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
)
{
fflink_dma
[
dma_used
].
to_dev
(
device_buffer
,
host_handle
,
btt
,
device_base_addr
);
}
/******************************************************************************/
platform/vc709/module/dual_dma_ctrl.c
View file @
8a5068c7
...
...
@@ -48,73 +48,15 @@
/******************************************************************************/
/* functions for irq-handling */
/**
* @brief Acknowledge interrupt in hardware and wake up corresponding process
* @param i minor node corresponding to this irq
* @return none
* */
void
ack_irq
(
int
i
)
{
fflink_info
(
"Handle device number %d
\n
"
,
i
);
/* ack interrupt */
pcie_writel
(
CMD_ACK
,
get_dev_addr
(
i
)
+
REG_CMD
);
/* Set priv data for more minor nodes accordingly */
wake_up_queue
(
i
);
}
/**
* @brief Interrupt handler for dma engine 0
* @param irq Interrupt number of calling line
* @param dev_id magic number for interrupt sharing (not needed)
* @return Tells OS, that irq is handled properly
* */
irqreturn_t
intr_handler_dma_0
(
int
irq
,
void
*
dev_id
)
{
fflink_info
(
"Interrupt called with irq %d
\n
"
,
irq
);
ack_irq
(
0
);
return
IRQ_HANDLED
;
}
/**
* @brief Interrupt handler for dma engine 1
* @param irq Interrupt number of calling line
* @param dev_id magic number for interrupt sharing (not needed)
* @return Tells OS, that irq is handled properly
* */
irqreturn_t
intr_handler_dma_1
(
int
irq
,
void
*
dev_id
)
irqreturn_t
dual_dma_intr_handler_dma
(
int
irq
,
void
*
dev_id
)
{
fflink_info
(
"Interrupt called with irq %d
\n
"
,
irq
);
ack_irq
(
1
);
return
IRQ_HANDLED
;
}
/**
* @brief Interrupt handler for dma engine 2
* @param irq Interrupt number of calling line
* @param dev_id magic number for interrupt sharing (not needed)
* @return Tells OS, that irq is handled properly
* */
irqreturn_t
intr_handler_dma_2
(
int
irq
,
void
*
dev_id
)
{
fflink_info
(
"Interrupt called with irq %d
\n
"
,
irq
);
ack_irq
(
2
);
return
IRQ_HANDLED
;
}
/**
* @brief Interrupt handler for dma engine 3
* @param irq Interrupt number of calling line
* @param dev_id magic number for interrupt sharing (not needed)
* @return Tells OS, that irq is handled properly
* */
irqreturn_t
intr_handler_dma_3
(
int
irq
,
void
*
dev_id
)
{
fflink_info
(
"Interrupt called with irq %d
\n
"
,
irq
);
ack_irq
(
3
);
pcie_writel
(
CMD_ACK
,
get_dev_addr
(
0
)
+
REG_CMD
);
return
IRQ_HANDLED
;
}
...
...
@@ -128,7 +70,7 @@ irqreturn_t intr_handler_dma_3(int irq, void * dev_id)
* @param device_base_addr Address of dma engine registers
* @return none
* */
void
transmit_from_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
)
void
dual_dma_
transmit_from_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
)
{
fflink_info
(
"dev_buf %lX dma_handle %lX
\n
size %d dev_base %lX
\n
"
,
(
unsigned
long
)
device_buffer
,
(
unsigned
long
)
host_handle
,
btt
,
(
unsigned
long
)
device_base_addr
);
//if(mutex_lock_interruptible(&dma_regs_mutex))
...
...
@@ -156,7 +98,7 @@ void transmit_from_device(void * device_buffer, dma_addr_t host_handle, int btt,
* @param device_base_addr Address of dma engine registers
* @return none
* */
void
transmit_to_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
)
void
dual_dma_
transmit_to_device
(
void
*
device_buffer
,
dma_addr_t
host_handle
,
int
btt
,
void
*
device_base_addr
)
{
fflink_info
(
"dev_buf %lX dma_handle %lX
\n
size %d dev_base %lX
\n
"
,
(
unsigned
long
)
device_buffer
,
(
unsigned
long
)
host_handle
,
btt
,
(
unsigned
long
)
device_base_addr
);
//if(mutex_lock_interruptible(&dma_regs_mutex))
...
...
@@ -172,7 +114,7 @@ void transmit_to_device(void * device_buffer, dma_addr_t host_handle, int btt, v
wmb
();
/* start cmd */
pcie_writel
(
CMD_WRITE
,
device_base_addr
+
REG_CMD
);
//mutex_unlock(&dma_regs_mutex);
}
...
...
platform/vc709/module/ffLink_driver.c
View file @
8a5068c7
...
...
@@ -45,6 +45,12 @@ static int __init fflink_init(void)
fflink_notice
(
"Init char-dev(s), dev-entries and register pci-device
\n
"
);
err
=
pcie_register
();
if
(
err
)
{
fflink_info
(
"Could not register pcie device
\n
"
);
goto
error_pcie_register
;
}
err
=
char_dma_register
();
if
(
err
)
{
fflink_info
(
"Could not register dma char device(s)
\n
"
);
...
...
@@ -56,13 +62,7 @@ static int __init fflink_init(void)
fflink_info
(
"Could not register user char device(s)
\n
"
);
goto
error_user_register
;
}
err
=
pcie_register
();
if
(
err
)
{
fflink_info
(
"Could not register pcie device
\n
"
);
goto
error_pcie_register
;
}
fflink_warn
(
"Successfully registered driver
\n
"
);
return
0
;
...
...
platform/vc709/module/pcie_device.c
View file @
8a5068c7
...
...
@@ -21,7 +21,7 @@
* @brief Implementation of all the pcie-device related functions - the code will lookup the dev_id on the pcie-bus
if a matching pcie-device is found, the pcie-device will probed and a basic configuration of the core is done
expects the device to provide a bar0 register space, which will be used for access to its registers afterwards
in addition
up to
8 msi interrupts will be allocated for the char-devices of ffLink
in addition
at least
8 msi interrupts will be allocated for the char-devices of ffLink
* */
/******************************************************************************/
...
...
@@ -75,8 +75,8 @@ static int claim_device(struct pci_dev *pdev)
fflink_warn
(
"Cannot remap Bar 0 address to kernel space
\n
"
);
goto
error_pci_remap
;
}
fflink_info
(
"Remapped Bar 0 Address is: %llx
\n
"
,
(
unsigned
long
long
int
)
pci_data
.
kvirt_addr_bar
0
);
fflink_info
(
"Remapped Bar 0 Address is: %llx
\n
"
,
(
unsigned
long
long
int
)
pci_data
.
kvirt_addr_bar
2
);
return
0
;
error_pci_remap:
...
...
@@ -94,28 +94,19 @@ error_pci_en:
* */
static
int
configure_device
(
struct
pci_dev
*
pdev
)
{
int
err
=
0
;
//
int err = 0;
u16
ctrl_reg
=
0
;