1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
|
#include <unistd.h>
#include <rte_config.h>
#include <rte_mbuf.h>
#include <rte_ethdev.h>
#include <rte_malloc.h>
#include <rte_errno.h>
#include "init.h"
#include "conf_file.h"
#include "dev.h"
#define TX_RING_SIZE 512
#define RX_RING_SIZE 512
struct ethdev {
int port;
};
static struct ethdev **dev_list;
static void ethdev_xmit(struct rte_mbuf *mbuf, struct net_device *dev)
{
struct ethdev *eth_dev = netdev_priv(dev);
mbuf->port = eth_dev->port;
}
int eth_dev_init(struct rte_mempool *mbuf_pool)
{
struct conf_sect *s = conf_get_sect("interface");
struct conf_opt *opt;
int i, cnt = rte_eth_dev_count();
struct rte_eth_dev_info info;
char busid[64];
const char *opt1;
int rxd, txd;
struct net_device *dev;
struct ethdev *eth_dev;
struct ether_addr addr;
struct rte_eth_link link;
struct rte_eth_conf conf = {
.rxmode = {
.mq_mode = ETH_MQ_RX_NONE,
.max_rx_pkt_len = ETHER_MAX_LEN + 8,
},
.txmode = {
.mq_mode = ETH_MQ_TX_NONE,
},
};
dev_list = rte_malloc(NULL, cnt * sizeof(void *), 0);
for (i = 0; i < cnt; i++) {
rte_eth_dev_info_get(i, &info);
sprintf(busid, "%04x:%02x:%02x.%i", info.pci_dev->addr.domain, info.pci_dev->addr.bus, info.pci_dev->addr.devid, info.pci_dev->addr.function);
for (opt = s->opt; opt; opt = opt->next) {
const char *opt_busid = conf_get_subopt(opt, "busid");
if (!strcmp(opt_busid, busid) || !strcmp(opt_busid, busid + 5))
break;
}
opt1 = conf_get_subopt(opt, "txd");
if (opt1)
txd = atoi(opt1);
else
txd = TX_RING_SIZE;
opt1 = conf_get_subopt(opt, "rxd");
if (opt1)
rxd = atoi(opt1);
else
rxd = RX_RING_SIZE;
if (rte_eth_dev_configure(i, 1, 1, &conf)) {
fprintf(stderr, "%s: %s\n", busid, rte_strerror(rte_errno));
return -1;
}
if (rte_eth_rx_queue_setup(i, 0, rxd, rte_eth_dev_socket_id(i), NULL, mbuf_pool)) {
fprintf(stderr, "%s: %s\n", busid, rte_strerror(rte_errno));
return -1;
}
if (rte_eth_tx_queue_setup(i, 0, txd, rte_eth_dev_socket_id(i), NULL)) {
fprintf(stderr, "%s: %s\n", busid, rte_strerror(rte_errno));
return -1;
}
if (rte_eth_dev_start(i)) {
fprintf(stderr, "%s: %s\n", busid, rte_strerror(rte_errno));
return -1;
}
rte_eth_link_get_nowait(i, &link);
if (!link.link_status) {
sleep(1);
rte_eth_link_get_nowait(i, &link);
}
if (!link.link_status)
printf("%s: link down\n", opt->name);
rte_eth_macaddr_get(i, &addr);
dev = netdev_alloc(opt->name, sizeof(*eth_dev), NULL);
dev->xmit = ethdev_xmit;
memcpy(dev->hwaddr, addr.addr_bytes, ETHER_ADDR_LEN);
eth_dev = netdev_priv(dev);
eth_dev->port = i;
dev_list[i] = eth_dev;
}
return 0;
}
|