liquidio: moved liquidio_push_packet to lio_core.c
Moving common liquidio_push_packet to lio_core.c Signed-off-by: Intiyaz Basha <intiyaz.basha@cavium.com> Signed-off-by: Felix Manlunas <felix.manlunas@cavium.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
69f9c60e83
commit
21f0888b5a
@ -432,3 +432,152 @@ int octeon_setup_droq(struct octeon_device *oct, int q_no, int num_descs,
|
||||
|
||||
return ret_val;
|
||||
}
|
||||
|
||||
/** Routine to push packets arriving on Octeon interface upto network layer.
|
||||
* @param oct_id - octeon device id.
|
||||
* @param skbuff - skbuff struct to be passed to network layer.
|
||||
* @param len - size of total data received.
|
||||
* @param rh - Control header associated with the packet
|
||||
* @param param - additional control data with the packet
|
||||
* @param arg - farg registered in droq_ops
|
||||
*/
|
||||
void
|
||||
liquidio_push_packet(u32 octeon_id __attribute__((unused)),
|
||||
void *skbuff,
|
||||
u32 len,
|
||||
union octeon_rh *rh,
|
||||
void *param,
|
||||
void *arg)
|
||||
{
|
||||
struct net_device *netdev = (struct net_device *)arg;
|
||||
struct octeon_droq *droq =
|
||||
container_of(param, struct octeon_droq, napi);
|
||||
struct sk_buff *skb = (struct sk_buff *)skbuff;
|
||||
struct skb_shared_hwtstamps *shhwtstamps;
|
||||
struct napi_struct *napi = param;
|
||||
u16 vtag = 0;
|
||||
u32 r_dh_off;
|
||||
u64 ns;
|
||||
|
||||
if (netdev) {
|
||||
struct lio *lio = GET_LIO(netdev);
|
||||
struct octeon_device *oct = lio->oct_dev;
|
||||
int packet_was_received;
|
||||
|
||||
/* Do not proceed if the interface is not in RUNNING state. */
|
||||
if (!ifstate_check(lio, LIO_IFSTATE_RUNNING)) {
|
||||
recv_buffer_free(skb);
|
||||
droq->stats.rx_dropped++;
|
||||
return;
|
||||
}
|
||||
|
||||
skb->dev = netdev;
|
||||
|
||||
skb_record_rx_queue(skb, droq->q_no);
|
||||
if (likely(len > MIN_SKB_SIZE)) {
|
||||
struct octeon_skb_page_info *pg_info;
|
||||
unsigned char *va;
|
||||
|
||||
pg_info = ((struct octeon_skb_page_info *)(skb->cb));
|
||||
if (pg_info->page) {
|
||||
/* For Paged allocation use the frags */
|
||||
va = page_address(pg_info->page) +
|
||||
pg_info->page_offset;
|
||||
memcpy(skb->data, va, MIN_SKB_SIZE);
|
||||
skb_put(skb, MIN_SKB_SIZE);
|
||||
skb_add_rx_frag(skb, skb_shinfo(skb)->nr_frags,
|
||||
pg_info->page,
|
||||
pg_info->page_offset +
|
||||
MIN_SKB_SIZE,
|
||||
len - MIN_SKB_SIZE,
|
||||
LIO_RXBUFFER_SZ);
|
||||
}
|
||||
} else {
|
||||
struct octeon_skb_page_info *pg_info =
|
||||
((struct octeon_skb_page_info *)(skb->cb));
|
||||
skb_copy_to_linear_data(skb, page_address(pg_info->page)
|
||||
+ pg_info->page_offset, len);
|
||||
skb_put(skb, len);
|
||||
put_page(pg_info->page);
|
||||
}
|
||||
|
||||
r_dh_off = (rh->r_dh.len - 1) * BYTES_PER_DHLEN_UNIT;
|
||||
|
||||
if (oct->ptp_enable) {
|
||||
if (rh->r_dh.has_hwtstamp) {
|
||||
/* timestamp is included from the hardware at
|
||||
* the beginning of the packet.
|
||||
*/
|
||||
if (ifstate_check
|
||||
(lio,
|
||||
LIO_IFSTATE_RX_TIMESTAMP_ENABLED)) {
|
||||
/* Nanoseconds are in the first 64-bits
|
||||
* of the packet.
|
||||
*/
|
||||
memcpy(&ns, (skb->data + r_dh_off),
|
||||
sizeof(ns));
|
||||
r_dh_off -= BYTES_PER_DHLEN_UNIT;
|
||||
shhwtstamps = skb_hwtstamps(skb);
|
||||
shhwtstamps->hwtstamp =
|
||||
ns_to_ktime(ns +
|
||||
lio->ptp_adjust);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (rh->r_dh.has_hash) {
|
||||
__be32 *hash_be = (__be32 *)(skb->data + r_dh_off);
|
||||
u32 hash = be32_to_cpu(*hash_be);
|
||||
|
||||
skb_set_hash(skb, hash, PKT_HASH_TYPE_L4);
|
||||
r_dh_off -= BYTES_PER_DHLEN_UNIT;
|
||||
}
|
||||
|
||||
skb_pull(skb, rh->r_dh.len * BYTES_PER_DHLEN_UNIT);
|
||||
skb->protocol = eth_type_trans(skb, skb->dev);
|
||||
|
||||
if ((netdev->features & NETIF_F_RXCSUM) &&
|
||||
(((rh->r_dh.encap_on) &&
|
||||
(rh->r_dh.csum_verified & CNNIC_TUN_CSUM_VERIFIED)) ||
|
||||
(!(rh->r_dh.encap_on) &&
|
||||
(rh->r_dh.csum_verified & CNNIC_CSUM_VERIFIED))))
|
||||
/* checksum has already been verified */
|
||||
skb->ip_summed = CHECKSUM_UNNECESSARY;
|
||||
else
|
||||
skb->ip_summed = CHECKSUM_NONE;
|
||||
|
||||
/* Setting Encapsulation field on basis of status received
|
||||
* from the firmware
|
||||
*/
|
||||
if (rh->r_dh.encap_on) {
|
||||
skb->encapsulation = 1;
|
||||
skb->csum_level = 1;
|
||||
droq->stats.rx_vxlan++;
|
||||
}
|
||||
|
||||
/* inbound VLAN tag */
|
||||
if ((netdev->features & NETIF_F_HW_VLAN_CTAG_RX) &&
|
||||
rh->r_dh.vlan) {
|
||||
u16 priority = rh->r_dh.priority;
|
||||
u16 vid = rh->r_dh.vlan;
|
||||
|
||||
vtag = (priority << VLAN_PRIO_SHIFT) | vid;
|
||||
__vlan_hwaccel_put_tag(skb, htons(ETH_P_8021Q), vtag);
|
||||
}
|
||||
|
||||
packet_was_received = (napi_gro_receive(napi, skb) != GRO_DROP);
|
||||
|
||||
if (packet_was_received) {
|
||||
droq->stats.rx_bytes_received += len;
|
||||
droq->stats.rx_pkts_received++;
|
||||
} else {
|
||||
droq->stats.rx_dropped++;
|
||||
netif_info(lio, rx_err, lio->netdev,
|
||||
"droq:%d error rx_dropped:%llu\n",
|
||||
droq->q_no, droq->stats.rx_dropped);
|
||||
}
|
||||
|
||||
} else {
|
||||
recv_buffer_free(skb);
|
||||
}
|
||||
}
|
||||
|
@ -2231,153 +2231,6 @@ static void if_cfg_callback(struct octeon_device *oct,
|
||||
wake_up_interruptible(&ctx->wc);
|
||||
}
|
||||
|
||||
/** Routine to push packets arriving on Octeon interface upto network layer.
|
||||
* @param oct_id - octeon device id.
|
||||
* @param skbuff - skbuff struct to be passed to network layer.
|
||||
* @param len - size of total data received.
|
||||
* @param rh - Control header associated with the packet
|
||||
* @param param - additional control data with the packet
|
||||
* @param arg - farg registered in droq_ops
|
||||
*/
|
||||
static void
|
||||
liquidio_push_packet(u32 octeon_id __attribute__((unused)),
|
||||
void *skbuff,
|
||||
u32 len,
|
||||
union octeon_rh *rh,
|
||||
void *param,
|
||||
void *arg)
|
||||
{
|
||||
struct napi_struct *napi = param;
|
||||
struct sk_buff *skb = (struct sk_buff *)skbuff;
|
||||
struct skb_shared_hwtstamps *shhwtstamps;
|
||||
u64 ns;
|
||||
u16 vtag = 0;
|
||||
u32 r_dh_off;
|
||||
struct net_device *netdev = (struct net_device *)arg;
|
||||
struct octeon_droq *droq = container_of(param, struct octeon_droq,
|
||||
napi);
|
||||
if (netdev) {
|
||||
int packet_was_received;
|
||||
struct lio *lio = GET_LIO(netdev);
|
||||
struct octeon_device *oct = lio->oct_dev;
|
||||
|
||||
/* Do not proceed if the interface is not in RUNNING state. */
|
||||
if (!ifstate_check(lio, LIO_IFSTATE_RUNNING)) {
|
||||
recv_buffer_free(skb);
|
||||
droq->stats.rx_dropped++;
|
||||
return;
|
||||
}
|
||||
|
||||
skb->dev = netdev;
|
||||
|
||||
skb_record_rx_queue(skb, droq->q_no);
|
||||
if (likely(len > MIN_SKB_SIZE)) {
|
||||
struct octeon_skb_page_info *pg_info;
|
||||
unsigned char *va;
|
||||
|
||||
pg_info = ((struct octeon_skb_page_info *)(skb->cb));
|
||||
if (pg_info->page) {
|
||||
/* For Paged allocation use the frags */
|
||||
va = page_address(pg_info->page) +
|
||||
pg_info->page_offset;
|
||||
memcpy(skb->data, va, MIN_SKB_SIZE);
|
||||
skb_put(skb, MIN_SKB_SIZE);
|
||||
skb_add_rx_frag(skb, skb_shinfo(skb)->nr_frags,
|
||||
pg_info->page,
|
||||
pg_info->page_offset +
|
||||
MIN_SKB_SIZE,
|
||||
len - MIN_SKB_SIZE,
|
||||
LIO_RXBUFFER_SZ);
|
||||
}
|
||||
} else {
|
||||
struct octeon_skb_page_info *pg_info =
|
||||
((struct octeon_skb_page_info *)(skb->cb));
|
||||
skb_copy_to_linear_data(skb, page_address(pg_info->page)
|
||||
+ pg_info->page_offset, len);
|
||||
skb_put(skb, len);
|
||||
put_page(pg_info->page);
|
||||
}
|
||||
|
||||
r_dh_off = (rh->r_dh.len - 1) * BYTES_PER_DHLEN_UNIT;
|
||||
|
||||
if (oct->ptp_enable) {
|
||||
if (rh->r_dh.has_hwtstamp) {
|
||||
/* timestamp is included from the hardware at
|
||||
* the beginning of the packet.
|
||||
*/
|
||||
if (ifstate_check
|
||||
(lio, LIO_IFSTATE_RX_TIMESTAMP_ENABLED)) {
|
||||
/* Nanoseconds are in the first 64-bits
|
||||
* of the packet.
|
||||
*/
|
||||
memcpy(&ns, (skb->data + r_dh_off),
|
||||
sizeof(ns));
|
||||
r_dh_off -= BYTES_PER_DHLEN_UNIT;
|
||||
shhwtstamps = skb_hwtstamps(skb);
|
||||
shhwtstamps->hwtstamp =
|
||||
ns_to_ktime(ns +
|
||||
lio->ptp_adjust);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (rh->r_dh.has_hash) {
|
||||
__be32 *hash_be = (__be32 *)(skb->data + r_dh_off);
|
||||
u32 hash = be32_to_cpu(*hash_be);
|
||||
|
||||
skb_set_hash(skb, hash, PKT_HASH_TYPE_L4);
|
||||
r_dh_off -= BYTES_PER_DHLEN_UNIT;
|
||||
}
|
||||
|
||||
skb_pull(skb, rh->r_dh.len * BYTES_PER_DHLEN_UNIT);
|
||||
|
||||
skb->protocol = eth_type_trans(skb, skb->dev);
|
||||
if ((netdev->features & NETIF_F_RXCSUM) &&
|
||||
(((rh->r_dh.encap_on) &&
|
||||
(rh->r_dh.csum_verified & CNNIC_TUN_CSUM_VERIFIED)) ||
|
||||
(!(rh->r_dh.encap_on) &&
|
||||
(rh->r_dh.csum_verified & CNNIC_CSUM_VERIFIED))))
|
||||
/* checksum has already been verified */
|
||||
skb->ip_summed = CHECKSUM_UNNECESSARY;
|
||||
else
|
||||
skb->ip_summed = CHECKSUM_NONE;
|
||||
|
||||
/* Setting Encapsulation field on basis of status received
|
||||
* from the firmware
|
||||
*/
|
||||
if (rh->r_dh.encap_on) {
|
||||
skb->encapsulation = 1;
|
||||
skb->csum_level = 1;
|
||||
droq->stats.rx_vxlan++;
|
||||
}
|
||||
|
||||
/* inbound VLAN tag */
|
||||
if ((netdev->features & NETIF_F_HW_VLAN_CTAG_RX) &&
|
||||
(rh->r_dh.vlan != 0)) {
|
||||
u16 vid = rh->r_dh.vlan;
|
||||
u16 priority = rh->r_dh.priority;
|
||||
|
||||
vtag = priority << 13 | vid;
|
||||
__vlan_hwaccel_put_tag(skb, htons(ETH_P_8021Q), vtag);
|
||||
}
|
||||
|
||||
packet_was_received = napi_gro_receive(napi, skb) != GRO_DROP;
|
||||
|
||||
if (packet_was_received) {
|
||||
droq->stats.rx_bytes_received += len;
|
||||
droq->stats.rx_pkts_received++;
|
||||
} else {
|
||||
droq->stats.rx_dropped++;
|
||||
netif_info(lio, rx_err, lio->netdev,
|
||||
"droq:%d error rx_dropped:%llu\n",
|
||||
droq->q_no, droq->stats.rx_dropped);
|
||||
}
|
||||
|
||||
} else {
|
||||
recv_buffer_free(skb);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief wrapper for calling napi_schedule
|
||||
* @param param parameters to pass to napi_schedule
|
||||
|
@ -1376,134 +1376,6 @@ static void if_cfg_callback(struct octeon_device *oct,
|
||||
wake_up_interruptible(&ctx->wc);
|
||||
}
|
||||
|
||||
/** Routine to push packets arriving on Octeon interface upto network layer.
|
||||
* @param oct_id - octeon device id.
|
||||
* @param skbuff - skbuff struct to be passed to network layer.
|
||||
* @param len - size of total data received.
|
||||
* @param rh - Control header associated with the packet
|
||||
* @param param - additional control data with the packet
|
||||
* @param arg - farg registered in droq_ops
|
||||
*/
|
||||
static void
|
||||
liquidio_push_packet(u32 octeon_id __attribute__((unused)),
|
||||
void *skbuff,
|
||||
u32 len,
|
||||
union octeon_rh *rh,
|
||||
void *param,
|
||||
void *arg)
|
||||
{
|
||||
struct napi_struct *napi = param;
|
||||
struct octeon_droq *droq =
|
||||
container_of(param, struct octeon_droq, napi);
|
||||
struct net_device *netdev = (struct net_device *)arg;
|
||||
struct sk_buff *skb = (struct sk_buff *)skbuff;
|
||||
u16 vtag = 0;
|
||||
u32 r_dh_off;
|
||||
|
||||
if (netdev) {
|
||||
struct lio *lio = GET_LIO(netdev);
|
||||
int packet_was_received;
|
||||
|
||||
/* Do not proceed if the interface is not in RUNNING state. */
|
||||
if (!ifstate_check(lio, LIO_IFSTATE_RUNNING)) {
|
||||
recv_buffer_free(skb);
|
||||
droq->stats.rx_dropped++;
|
||||
return;
|
||||
}
|
||||
|
||||
skb->dev = netdev;
|
||||
|
||||
skb_record_rx_queue(skb, droq->q_no);
|
||||
if (likely(len > MIN_SKB_SIZE)) {
|
||||
struct octeon_skb_page_info *pg_info;
|
||||
unsigned char *va;
|
||||
|
||||
pg_info = ((struct octeon_skb_page_info *)(skb->cb));
|
||||
if (pg_info->page) {
|
||||
/* For Paged allocation use the frags */
|
||||
va = page_address(pg_info->page) +
|
||||
pg_info->page_offset;
|
||||
memcpy(skb->data, va, MIN_SKB_SIZE);
|
||||
skb_put(skb, MIN_SKB_SIZE);
|
||||
skb_add_rx_frag(skb, skb_shinfo(skb)->nr_frags,
|
||||
pg_info->page,
|
||||
pg_info->page_offset +
|
||||
MIN_SKB_SIZE,
|
||||
len - MIN_SKB_SIZE,
|
||||
LIO_RXBUFFER_SZ);
|
||||
}
|
||||
} else {
|
||||
struct octeon_skb_page_info *pg_info =
|
||||
((struct octeon_skb_page_info *)(skb->cb));
|
||||
skb_copy_to_linear_data(skb,
|
||||
page_address(pg_info->page) +
|
||||
pg_info->page_offset, len);
|
||||
skb_put(skb, len);
|
||||
put_page(pg_info->page);
|
||||
}
|
||||
|
||||
r_dh_off = (rh->r_dh.len - 1) * BYTES_PER_DHLEN_UNIT;
|
||||
|
||||
if (rh->r_dh.has_hwtstamp)
|
||||
r_dh_off -= BYTES_PER_DHLEN_UNIT;
|
||||
|
||||
if (rh->r_dh.has_hash) {
|
||||
__be32 *hash_be = (__be32 *)(skb->data + r_dh_off);
|
||||
u32 hash = be32_to_cpu(*hash_be);
|
||||
|
||||
skb_set_hash(skb, hash, PKT_HASH_TYPE_L4);
|
||||
r_dh_off -= BYTES_PER_DHLEN_UNIT;
|
||||
}
|
||||
|
||||
skb_pull(skb, rh->r_dh.len * BYTES_PER_DHLEN_UNIT);
|
||||
skb->protocol = eth_type_trans(skb, skb->dev);
|
||||
|
||||
if ((netdev->features & NETIF_F_RXCSUM) &&
|
||||
(((rh->r_dh.encap_on) &&
|
||||
(rh->r_dh.csum_verified & CNNIC_TUN_CSUM_VERIFIED)) ||
|
||||
(!(rh->r_dh.encap_on) &&
|
||||
(rh->r_dh.csum_verified & CNNIC_CSUM_VERIFIED))))
|
||||
/* checksum has already been verified */
|
||||
skb->ip_summed = CHECKSUM_UNNECESSARY;
|
||||
else
|
||||
skb->ip_summed = CHECKSUM_NONE;
|
||||
|
||||
/* Setting Encapsulation field on basis of status received
|
||||
* from the firmware
|
||||
*/
|
||||
if (rh->r_dh.encap_on) {
|
||||
skb->encapsulation = 1;
|
||||
skb->csum_level = 1;
|
||||
droq->stats.rx_vxlan++;
|
||||
}
|
||||
|
||||
/* inbound VLAN tag */
|
||||
if ((netdev->features & NETIF_F_HW_VLAN_CTAG_RX) &&
|
||||
rh->r_dh.vlan) {
|
||||
u16 priority = rh->r_dh.priority;
|
||||
u16 vid = rh->r_dh.vlan;
|
||||
|
||||
vtag = (priority << VLAN_PRIO_SHIFT) | vid;
|
||||
__vlan_hwaccel_put_tag(skb, htons(ETH_P_8021Q), vtag);
|
||||
}
|
||||
|
||||
packet_was_received = (napi_gro_receive(napi, skb) != GRO_DROP);
|
||||
|
||||
if (packet_was_received) {
|
||||
droq->stats.rx_bytes_received += len;
|
||||
droq->stats.rx_pkts_received++;
|
||||
} else {
|
||||
droq->stats.rx_dropped++;
|
||||
netif_info(lio, rx_err, lio->netdev,
|
||||
"droq:%d error rx_dropped:%llu\n",
|
||||
droq->q_no, droq->stats.rx_dropped);
|
||||
}
|
||||
|
||||
} else {
|
||||
recv_buffer_free(skb);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief callback when receive interrupt occurs and we are in NAPI mode
|
||||
* @param arg pointer to octeon output queue
|
||||
|
@ -477,4 +477,11 @@ static inline int wait_for_pending_requests(struct octeon_device *oct)
|
||||
void lio_update_txq_status(struct octeon_device *oct, int iq_num);
|
||||
int octeon_setup_droq(struct octeon_device *oct, int q_no, int num_descs,
|
||||
int desc_size, void *app_ctx);
|
||||
void
|
||||
liquidio_push_packet(u32 octeon_id __attribute__((unused)),
|
||||
void *skbuff,
|
||||
u32 len,
|
||||
union octeon_rh *rh,
|
||||
void *param,
|
||||
void *arg);
|
||||
#endif
|
||||
|
Loading…
x
Reference in New Issue
Block a user