Commit 2d9d3447 authored by Pavel Pisa's avatar Pavel Pisa

Merge branch 'pci-driver' into 'master'

Merge interfacing CAN FD core to PCI Express bus

Closes #216

See merge request illeondr/CAN_FD_IP_Core!179
parents 474daceb 7ccd991c
Pipeline #5835 passed with stages
in 13 minutes and 25 seconds
This diff is collapsed.
......@@ -55,12 +55,12 @@ void ctu_can_fd_write32_be(struct ctucanfd_priv *priv, enum ctu_can_fd_can_regis
u32 ctu_can_fd_read32(struct ctucanfd_priv *priv, enum ctu_can_fd_can_registers reg)
{
return ioread32((const char *)priv->mem_base + reg);
return ioread32((char *)priv->mem_base + reg);
}
u32 ctu_can_fd_read32_be(struct ctucanfd_priv *priv, enum ctu_can_fd_can_registers reg)
{
return ioread32be((const char *)priv->mem_base + reg);
return ioread32be((char *)priv->mem_base + reg);
}
/*
......@@ -208,6 +208,7 @@ void ctu_can_fd_enable(struct ctucanfd_priv *priv, bool enable)
void ctu_can_fd_reset(struct ctucanfd_priv *priv)
{
union ctu_can_fd_mode_command_status_settings mode;
mode.u32 = 0;
mode.s.rst = 1;
/* it does not matter that we overwrite the rest of the reg - we're resetting */
priv->write_reg(priv, CTU_CAN_FD_MODE, mode.u32);
......
......@@ -286,11 +286,28 @@ static inline union ctu_can_fd_mode_command_status_settings ctu_can_get_status(s
{
// MODE and STATUS are within the same word
union ctu_can_fd_mode_command_status_settings res;
res.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_MODE);
res.u32 = priv->read_reg(priv, CTU_CAN_FD_MODE);
return res;
}
/*
* Test if core is enabled..
*
* Arguments:
* priv Private info
* Returns:
* Return true if core is in enabled/active state..
*/
static inline bool ctu_can_fd_is_enabled(struct ctucanfd_priv *priv)
{
union ctu_can_fd_mode_command_status_settings reg;
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_MODE);
return reg.s.ena == ENABLED;
}
/*
* Reads the interrupt status vector from CTU CAN FD Core.
*
......@@ -303,7 +320,7 @@ static inline union ctu_can_fd_mode_command_status_settings ctu_can_get_status(s
static inline union ctu_can_fd_int_stat ctu_can_fd_int_sts(struct ctucanfd_priv *priv)
{
union ctu_can_fd_int_stat res;
res.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_INT_STAT);
res.u32 = priv->read_reg(priv, CTU_CAN_FD_INT_STAT);
return res;
}
......@@ -317,7 +334,33 @@ static inline union ctu_can_fd_int_stat ctu_can_fd_int_sts(struct ctucanfd_priv
*/
static inline void ctu_can_fd_int_clr(struct ctucanfd_priv *priv, union ctu_can_fd_int_stat mask)
{
ctu_can_fd_write32(priv, CTU_CAN_FD_INT_STAT, mask.u32);
priv->write_reg(priv, CTU_CAN_FD_INT_STAT, mask.u32);
}
/*
* Sets enable interrupt bits.
*
* Arguments:
* priv Private info
* mask Mask of interrupts which should be disabled.
*/
static inline void ctu_can_fd_int_ena_set(struct ctucanfd_priv *priv, union ctu_can_fd_int_stat mask)
{
priv->write_reg(priv, CTU_CAN_FD_INT_ENA_SET, mask.u32);
}
/*
* Clears enable interrupt bits.
*
* Arguments:
* priv Private info
* mask Mask of interrupts which should be disabled.
*/
static inline void ctu_can_fd_int_ena_clr(struct ctucanfd_priv *priv, union ctu_can_fd_int_stat mask)
{
priv->write_reg(priv, CTU_CAN_FD_INT_ENA_CLR, mask.u32);
}
......@@ -429,7 +472,7 @@ void ctu_can_fd_read_err_ctrs(struct ctucanfd_priv *priv, struct can_berr_counte
static inline u16 ctu_can_fd_read_nom_errs(struct ctucanfd_priv *priv)
{
union ctu_can_fd_err_norm_err_fd reg;
reg.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_ERR_NORM);
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_ERR_NORM);
return reg.s.err_norm_val;
}
......@@ -446,7 +489,7 @@ static inline void ctu_can_fd_erase_nom_errs(struct ctucanfd_priv *priv)
union ctu_can_fd_ctr_pres reg;
reg.u32 = 0;
reg.s.enorm = 1;
ctu_can_fd_write32(priv, CTU_CAN_FD_CTR_PRES, reg.u32);
priv->write_reg(priv, CTU_CAN_FD_CTR_PRES, reg.u32);
}
......@@ -462,7 +505,7 @@ static inline void ctu_can_fd_erase_nom_errs(struct ctucanfd_priv *priv)
static inline u16 ctu_can_fd_read_fd_errs(struct ctucanfd_priv *priv)
{
union ctu_can_fd_err_norm_err_fd reg;
reg.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_ERR_NORM);
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_ERR_NORM);
return reg.s.err_fd_val;
}
......@@ -478,7 +521,7 @@ static inline void ctu_can_fd_erase_fd_errs(struct ctucanfd_priv *priv)
union ctu_can_fd_ctr_pres reg;
reg.u32 = 0;
reg.s.efd = 1;
ctu_can_fd_write32(priv, CTU_CAN_FD_CTR_PRES, reg.u32);
priv->write_reg(priv, CTU_CAN_FD_CTR_PRES, reg.u32);
}
......@@ -567,7 +610,7 @@ void ctu_can_fd_set_range_filter(struct ctucanfd_priv *priv, canid_t low_th,
static inline u16 ctu_can_fd_get_rx_fifo_size(struct ctucanfd_priv *priv)
{
union ctu_can_fd_rx_mem_info reg;
reg.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_RX_MEM_INFO);
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_RX_MEM_INFO);
return reg.s.rx_buff_size;
}
......@@ -583,7 +626,7 @@ static inline u16 ctu_can_fd_get_rx_fifo_size(struct ctucanfd_priv *priv)
static inline u16 ctu_can_fd_get_rx_fifo_mem_free(struct ctucanfd_priv *priv)
{
union ctu_can_fd_rx_mem_info reg;
reg.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_RX_MEM_INFO);
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_RX_MEM_INFO);
return reg.s.rx_mem_free;
}
......@@ -599,7 +642,7 @@ static inline u16 ctu_can_fd_get_rx_fifo_mem_free(struct ctucanfd_priv *priv)
static inline bool ctu_can_fd_is_rx_fifo_empty(struct ctucanfd_priv *priv)
{
union ctu_can_fd_rx_status_rx_settings reg;
reg.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_RX_STATUS);
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_RX_STATUS);
return reg.s.rxe;
}
......@@ -615,7 +658,7 @@ static inline bool ctu_can_fd_is_rx_fifo_empty(struct ctucanfd_priv *priv)
static inline bool ctu_can_fd_is_rx_fifo_full(struct ctucanfd_priv *priv)
{
union ctu_can_fd_rx_status_rx_settings reg;
reg.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_RX_STATUS);
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_RX_STATUS);
return reg.s.rxf;
}
......@@ -631,7 +674,7 @@ static inline bool ctu_can_fd_is_rx_fifo_full(struct ctucanfd_priv *priv)
static inline u16 ctu_can_fd_get_rx_frame_count(struct ctucanfd_priv *priv)
{
union ctu_can_fd_rx_status_rx_settings reg;
reg.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_RX_STATUS);
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_RX_STATUS);
return reg.s.rxfrc;
}
......@@ -646,6 +689,37 @@ static inline u16 ctu_can_fd_get_rx_frame_count(struct ctucanfd_priv *priv)
void ctu_can_fd_set_rx_tsop(struct ctucanfd_priv *priv, enum ctu_can_fd_rx_settings_rtsop val);
/*
* Reads the first word of CAN Frame from RX FIFO Buffer.
*
* Arguments:
* priv Private info
*
* Returns:
* The firts word of received frame
*/
static inline union ctu_can_fd_frame_form_w ctu_can_fd_read_rx_ffw(struct ctucanfd_priv *priv)
{
union ctu_can_fd_frame_form_w ffw;
ffw.u32 = priv->read_reg(priv, CTU_CAN_FD_RX_DATA);
return ffw;
}
/*
* Reads one word of CAN Frame from RX FIFO Buffer.
*
* Arguments:
* priv Private info
*
* Returns:
* One wword of received frame
*/
static inline u32 ctu_can_fd_read_rx_word(struct ctucanfd_priv *priv)
{
return priv->read_reg(priv, CTU_CAN_FD_RX_DATA);
}
/*
* Reads CAN Frame from RX FIFO Buffer and stores it to a buffer.
*
......@@ -781,7 +855,7 @@ bool ctu_can_fd_insert_frame(struct ctucanfd_priv *priv, const struct canfd_fram
static inline u16 ctu_can_fd_get_tran_delay(struct ctucanfd_priv *priv)
{
union ctu_can_fd_trv_delay_ssp_cfg reg;
reg.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_TRV_DELAY);
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_TRV_DELAY);
return reg.s.trv_delay_value;
}
......@@ -797,7 +871,7 @@ static inline u16 ctu_can_fd_get_tran_delay(struct ctucanfd_priv *priv)
static inline u32 ctu_can_fd_get_tx_frame_ctr(struct ctucanfd_priv *priv)
{
union ctu_can_fd_tx_counter reg;
reg.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_TX_COUNTER);
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_TX_COUNTER);
return reg.s.tx_counter_val;
}
......@@ -813,7 +887,7 @@ static inline u32 ctu_can_fd_get_tx_frame_ctr(struct ctucanfd_priv *priv)
static inline u32 ctu_can_fd_get_rx_frame_ctr(struct ctucanfd_priv *priv)
{
union ctu_can_fd_rx_counter reg;
reg.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_RX_COUNTER);
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_RX_COUNTER);
return reg.s.rx_counter_val;
}
......@@ -829,7 +903,7 @@ static inline u32 ctu_can_fd_get_rx_frame_ctr(struct ctucanfd_priv *priv)
static inline union ctu_can_fd_debug_register ctu_can_fd_read_debug_info(struct ctucanfd_priv *priv)
{
union ctu_can_fd_debug_register reg;
reg.u32 = ctu_can_fd_read32(priv, CTU_CAN_FD_DEBUG_REGISTER);
reg.u32 = priv->read_reg(priv, CTU_CAN_FD_DEBUG_REGISTER);
return reg;
}
......
......@@ -41,13 +41,15 @@
#include <stdint.h>
#include <stdio.h>
#include <stddef.h>
//#include <linux/types.h>
#include <linux/types.h>
#include <linux/socket.h>
#include <arpa/inet.h>
#define likely(x) __builtin_expect(!!(x), 1)
#define unlikely(x) __builtin_expect(!!(x), 0)
#define __iomem volatile
#ifndef _ASM_GENERIC_INT_LL64_H
typedef uint8_t __u8;
typedef uint16_t __u16;
typedef uint32_t __u32;
......@@ -58,6 +60,8 @@ typedef int16_t __s16;
typedef int32_t __s32;
typedef int64_t __s64;
#endif
typedef __u8 u8;
typedef __u16 u16;
typedef __u32 u32;
......
......@@ -34,28 +34,210 @@
#include "userspace_utils.h"
#include <iostream>
#include <unistd.h>
#include <sys/types.h>
#include <dirent.h>
#include <stdio.h>
#include <string.h>
/*
/sys/devices/pci0000:00/0000:00:1c.4/0000:05:00.0
*/
typedef struct find_dir_chain {
char *dir_name;
DIR *dir;
struct find_dir_chain *parent;
} find_dir_chain_t;
int pci_find_dev(char **dev_dir, const char *dir_name, unsigned vid, unsigned pid, int inst)
{
unsigned vid_act, pid_act;
find_dir_chain_t *dir_stack = NULL;
find_dir_chain_t *dir_act = NULL;
char *entry_name = NULL;
FILE *f;
struct dirent *entry;
int level = 0;
int sz1, sz2 = 0;
char level0_prefix[] = "pci";
int clean_rest = 0;
*dev_dir = NULL;
while(1) {
if (dir_act != NULL) {
while (((entry = readdir(dir_act->dir)) == NULL) || (clean_rest)) {
closedir(dir_act->dir);
free(dir_act->dir_name);
dir_stack = dir_act->parent;
free(dir_act);
dir_act = dir_stack;
level--;
if (dir_stack == NULL)
break;
}
if (dir_act == NULL)
break;
if (entry->d_type != DT_DIR)
continue;
if (strcmp(entry->d_name, ".") == 0 || strcmp(entry->d_name, "..") == 0)
continue;
dir_name = dir_stack->dir_name;
entry_name = entry->d_name;
if ((level <= 1) && strncmp(entry_name, level0_prefix, strlen(level0_prefix)))
continue;
}
dir_act = (find_dir_chain_t *)malloc(sizeof(find_dir_chain_t));
if (dir_act == NULL)
err(1, "malloc failed");
dir_act->parent = dir_stack;
sz1 = strlen(dir_name);
if (entry_name != NULL)
sz2 = strlen(entry_name);
dir_act->dir_name = (char *)malloc(sz1 + sz2 + 2);
if (dir_act->dir_name == NULL)
err(1, "malloc failed");
memcpy(dir_act->dir_name, dir_name, sz1);
if (entry_name != NULL) {
dir_act->dir_name[sz1] = '/';
memcpy(dir_act->dir_name + sz1 + 1, entry_name, sz2);
dir_act->dir_name[sz1 + 1 + sz2] = 0;
} else {
dir_act->dir_name[sz1] = 0;
}
/*printf("level %d, name = %s\n", level, dir_act->dir_name);*/
dir_stack = dir_act;
dir_act->dir = opendir(dir_act->dir_name);
if (dir_act->dir == NULL)
err(1, "opendir failed");
level++;
if (level <= 2)
continue;
{
int sz1 = strlen(dir_act->dir_name);
char vid_fname[sz1 + strlen("/vendor") + 1];
char pid_fname[sz1 + strlen("/device") + 1];
memcpy(vid_fname, dir_act->dir_name, sz1);
memcpy(pid_fname, dir_act->dir_name, sz1);
strcpy(vid_fname + sz1, "/vendor");
strcpy(pid_fname + sz1, "/device");
f = fopen(vid_fname, "r");
if (f == NULL)
continue;
vid_act = -1;
fscanf(f, "%i", &vid_act);
fclose(f);
f = fopen(pid_fname, "r");
if (f == NULL)
continue;
pid_act = -1;
fscanf(f, "%i", &pid_act);
fclose(f);
}
if (vid != vid_act)
continue;
if (pid != pid_act)
continue;
if (inst-- > 0)
continue;
*dev_dir = strdup(dir_act->dir_name);
clean_rest = 1;
}
return clean_rest;
}
uintptr_t pci_find_bar(unsigned vid, unsigned pid, int inst, int barnr)
{
FILE *f;
char *dev_dir;
int sz1;
unsigned long long bar1_base;
if (!pci_find_dev(&dev_dir, "/sys/devices", vid, pid, inst)) {
return 0;
}
printf("found %s\n", dev_dir);
sz1 = strlen(dev_dir);
{
char buff[200];
char resource_fname[sz1 + strlen("/resource") + 1];
memcpy(resource_fname, dev_dir, sz1);
strcpy(resource_fname + sz1, "/resource");
f = fopen(resource_fname, "r");
if (f == NULL)
return 0;
while (barnr-- > 0)
fgets(buff, sizeof(buff) - 1, f);
fscanf(f, "%lli", &bar1_base);
fclose(f);
}
return bar1_base;
}
int main(int argc, char *argv[])
{
uint32_t addr_base;
uintptr_t addr_base = 0;
unsigned ifc = 0;
bool do_transmit = false;
int loop_cycle = 0;
int gap = 1000;
int bitrate = 1000000;
int dbitrate = 0;
bool do_periodic_transmit = false;
bool transmit_fdf = false;
bool loopback_mode = false;
//bool do_showhelp = false;
static uintptr_t addrs[] = {0x43C30000, 0x43C70000};
int c;
char *e;
const char *progname = argv[0];
while ((c = getopt(argc, argv, "i:th")) != -1) {
while ((c = getopt(argc, argv, "i:a:g:b:B:fltThp")) != -1) {
switch (c) {
case 'i':
ifc = strtoul(optarg, &e, 0);
if (*e != '\0')
err(1, "-i expects a number");
break;
case 'a':
addr_base = strtoul(optarg, &e, 0);
if (*e != '\0')
err(1, "-a expects a number");
break;
case 'g':
gap = strtoul(optarg, &e, 0);
if (*e != '\0')
err(1, "-g expects a number");
break;
case 'b':
bitrate = strtoul(optarg, &e, 0);
if (*e != '\0')
err(1, "-b expects a number");
break;
case 'B':
dbitrate = strtoul(optarg, &e, 0);
if (*e != '\0')
err(1, "-B expects a number");
break;
case 'l': loopback_mode = true; break;
case 't': do_transmit = true; break;
case 'T': do_periodic_transmit = true; break;
case 'f': transmit_fdf = true; break;
case 'p':
addrs[0] = pci_find_bar(0x1172, 0xcafd, 0, 1);
if (!addrs[0])
err(1, "-p PCI device not found");
addrs[1] = addrs[0] + 0x4000;
break;
case 'h':
printf("Usage: %s [-i ifc] [-t]\n\n"
printf("Usage: %s [-i ifc] [-a address] [-l] [-t] [-T]\n\n"
" -t: Transmit\n",
progname
);
......@@ -63,12 +245,12 @@ int main(int argc, char *argv[])
}
}
static const uint32_t addrs[] = {0x43C30000, 0x43C70000};
if (ifc >= 2) {
std::cerr << "Err: ifc number must be 0 or 1.\n";
exit(1);
}
addr_base = addrs[ifc];
if (addr_base == 0)
addr_base = addrs[ifc];
struct ctucanfd_priv *priv = ctucanfd_init(addr_base);
int res;
......@@ -105,7 +287,7 @@ int main(int argc, char *argv[])
nd.can.clock.freq = 100000000;
struct can_bittiming nom_timing = {
.bitrate = 1000000,
.bitrate = bitrate,
};
res = can_get_bittiming(&nd, &nom_timing,
&ctu_can_fd_bit_timing_max,
......@@ -124,18 +306,51 @@ int main(int argc, char *argv[])
nom_timing.bitrate
);
if (!dbitrate)
dbitrate = 10 * bitrate;
struct can_bittiming data_timing = {
.bitrate = dbitrate,
};
res = can_get_bittiming(&nd, &data_timing,
&ctu_can_fd_bit_timing_data_max,
NULL,
0);
if (res)
err(res, "can_get_bittiming data");
printf("data sample_point .%03d, tq %d, prop %d, seg1 %d, seg2 %d, sjw %d, brp %d, bitrate %d\n",
data_timing.sample_point,
data_timing.tq,
data_timing.prop_seg,
data_timing.phase_seg1,
data_timing.phase_seg2,
data_timing.sjw,
data_timing.brp,
data_timing.bitrate
);
//priv->write_reg(priv, CTU_CAN_FD_INT_MASK_CLR, 0xffff);
//priv->write_reg(priv, CTU_CAN_FD_INT_ENA_SET, 0xffff);
ctu_can_fd_set_nom_bittiming(priv, &nom_timing);
ctu_can_fd_set_data_bittiming(priv, &data_timing);
//ctu_can_fd_rel_rx_buf(priv);
//ctu_can_fd_set_ret_limit(priv, true, 1);
//ctu_can_fd_set_ret_limit(priv, false, 0);
//ctu_can_fd_abort_tx(priv);
//ctu_can_fd_txt_set_abort(priv, CTU_CAN_FD_TXT_BUFFER_1);
//ctu_can_fd_txt_set_empty(priv, CTU_CAN_FD_TXT_BUFFER_1);
if (loopback_mode) {
struct can_ctrlmode mode = {0, 0};
mode.mask = CAN_CTRLMODE_LOOPBACK | CAN_CTRLMODE_PRESUME_ACK;
mode.flags = CAN_CTRLMODE_LOOPBACK | CAN_CTRLMODE_PRESUME_ACK;
ctu_can_fd_set_mode(priv, &mode);
}
ctu_can_fd_enable(priv, true);
usleep(10000);
printf("MODE=0x%02x\n", priv->read_reg(priv, CTU_CAN_FD_MODE));
if (do_transmit) {
struct canfd_frame txf;
......@@ -163,11 +378,11 @@ int main(int argc, char *argv[])
printf(", status 0x%02hhx", ctu_can_fd_read8(priv, CTU_CAN_FD_STATUS));
printf(", settings 0x%02hhx", ctu_can_fd_read8(priv, CTU_CAN_FD_SETTINGS));
printf(", INT_STAT 0x%04hhx", ctu_can_fd_read16(priv, CTU_CAN_FD_INT_STAT));
printf(", CTU_CAN_FD_INT_ENA_SET 0x%04hx", priv->read_reg(priv, CTU_CAN_FD_INT_ENA_SET));
printf(", CTU_CAN_FD_INT_MASK_SET 0x%04hx", priv->read_reg(priv, CTU_CAN_FD_INT_MASK_SET));
printf(", CTU_CAN_FD_TX_STATUS 0x%04hx", priv->read_reg(priv, CTU_CAN_FD_TX_STATUS));
printf(", INT_ENA_SET 0x%04hx", priv->read_reg(priv, CTU_CAN_FD_INT_ENA_SET));
printf(", INT_MASK_SET 0x%04hx", priv->read_reg(priv, CTU_CAN_FD_INT_MASK_SET));
printf(", TX_STATUS 0x%04hx", priv->read_reg(priv, CTU_CAN_FD_TX_STATUS));
//printf(", CTU_CAN_FD_ERR_CAPT 0x%02hhx", ctu_can_fd_read8(priv, CTU_CAN_FD_ERR_CAPT));
printf(", TRV_DELAY 0x%0hx", priv->read_reg(priv, CTU_CAN_FD_TRV_DELAY));
printf("\n");
/*
......@@ -176,7 +391,7 @@ int main(int argc, char *argv[])
printf(" 0x%08x\n", data);
}
*/
if (nrxf || rxsz) {
while (nrxf || rxsz) {
struct canfd_frame cf;
u64 ts;
ctu_can_fd_read_rx_frame(priv, &cf, &ts);
......@@ -184,9 +399,37 @@ int main(int argc, char *argv[])
for (int i=0; i<cf.len; ++i)
printf(" %02x", cf.data[i]);
printf("\n");
rxsz = 0;
nrxf = ctu_can_fd_get_rx_frame_count(priv);
}
if (do_periodic_transmit && (loop_cycle & 1)) {
struct canfd_frame txf;
memset(&txf, 0, sizeof(txf));
txf.can_id = 0x1FF;
txf.flags = 0;
if (transmit_fdf) {
txf.flags |= CANFD_BRS;
u8 dfd[] = {0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88, 0x99, 0xaa, 0xbb, 0xcc, 0xdd, 0xee};
txf.can_id = 0x123;
memcpy(txf.data, dfd, sizeof(dfd));
txf.len = sizeof(dfd);
} else {
u8 d[] = {0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0xEE};
memcpy(txf.data, d, sizeof(d));
txf.len = sizeof(d);
}
res = ctu_can_fd_insert_frame(priv, &txf, 0, CTU_CAN_FD_TXT_BUFFER_1, transmit_fdf);
if (!res)
printf("TX failed\n");
ctu_can_fd_txt_set_rdy(priv, CTU_CAN_FD_TXT_BUFFER_1);