int cls_pkt_set_seq(odp_packet_t pkt) { static uint32_t seq; cls_test_packet_t data; uint32_t offset; odph_ipv4hdr_t *ip; odph_tcphdr_t *tcp; int status; data.magic = DATA_MAGIC; data.seq = ++seq; ip = (odph_ipv4hdr_t *)odp_packet_l3_ptr(pkt, NULL); offset = odp_packet_l4_offset(pkt); CU_ASSERT_FATAL(offset != 0); if (ip->proto == ODPH_IPPROTO_UDP) status = odp_packet_copydata_in(pkt, offset + ODPH_UDPHDR_LEN, sizeof(data), &data); else { tcp = (odph_tcphdr_t *)odp_packet_l4_ptr(pkt, NULL); status = odp_packet_copydata_in(pkt, offset + tcp->hl * 4, sizeof(data), &data); } return status; }
uint32_t cls_pkt_get_seq(odp_packet_t pkt) { uint32_t offset; cls_test_packet_t data; odph_ipv4hdr_t *ip; odph_tcphdr_t *tcp; ip = (odph_ipv4hdr_t *)odp_packet_l3_ptr(pkt, NULL); offset = odp_packet_l4_offset(pkt); if (!offset && !ip) return TEST_SEQ_INVALID; if (ip->proto == ODPH_IPPROTO_UDP) odp_packet_copydata_out(pkt, offset + ODPH_UDPHDR_LEN, sizeof(data), &data); else { tcp = (odph_tcphdr_t *)odp_packet_l4_ptr(pkt, NULL); odp_packet_copydata_out(pkt, offset + tcp->hl * 4, sizeof(data), &data); } if (data.magic == DATA_MAGIC) return data.seq; return TEST_SEQ_INVALID; }
static uint32_t pktio_pkt_seq(odp_packet_t pkt) { size_t off; uint32_t seq = TEST_SEQ_INVALID; pkt_head_t head; pkt_tail_t tail; if (pkt == ODP_PACKET_INVALID) return TEST_SEQ_INVALID; off = odp_packet_l4_offset(pkt); if (off == ODP_PACKET_OFFSET_INVALID) return TEST_SEQ_INVALID; off += ODPH_UDPHDR_LEN; if (odp_packet_copydata_out(pkt, off, sizeof(head), &head) != 0) return TEST_SEQ_INVALID; if (head.magic != TEST_SEQ_MAGIC) return TEST_SEQ_INVALID; if (odp_packet_len(pkt) == packet_len) { off = packet_len - sizeof(tail); if (odp_packet_copydata_out(pkt, off, sizeof(tail), &tail) != 0) return TEST_SEQ_INVALID; if (tail.magic == TEST_SEQ_MAGIC) { seq = head.seq; CU_ASSERT(seq != TEST_SEQ_INVALID); } } return seq; }
static uint32_t pktio_pkt_set_seq(odp_packet_t pkt) { static uint32_t tstseq; size_t off; pkt_head_t head; pkt_tail_t tail; off = odp_packet_l4_offset(pkt); if (off == ODP_PACKET_OFFSET_INVALID) { CU_FAIL("packet L4 offset not set"); return TEST_SEQ_INVALID; } head.magic = TEST_SEQ_MAGIC; head.seq = tstseq; off += ODPH_UDPHDR_LEN; if (odp_packet_copydata_in(pkt, off, sizeof(head), &head) != 0) return TEST_SEQ_INVALID; tail.magic = TEST_SEQ_MAGIC; off = odp_packet_len(pkt) - sizeof(pkt_tail_t); if (odp_packet_copydata_in(pkt, off, sizeof(tail), &tail) != 0) return TEST_SEQ_INVALID; tstseq++; return head.seq; }
/** * Print odp packets * * @param thr worker id * @param pkt_tbl packets to be print * @param len packet number */ static void print_pkts(int thr, odp_packet_t pkt_tbl[], unsigned len) { odp_packet_t pkt; char *buf; odph_ipv4hdr_t *ip; odph_icmphdr_t *icmp; struct timeval tvrecv; struct timeval tvsend; double rtt; unsigned i; size_t offset; char msg[1024]; int rlen; for (i = 0; i < len; ++i) { pkt = pkt_tbl[i]; rlen = 0; /* only ip pkts */ if (!odp_packet_has_ipv4(pkt)) continue; odp_atomic_inc_u64(&counters.ip); buf = odp_packet_data(pkt); ip = (odph_ipv4hdr_t *)(buf + odp_packet_l3_offset(pkt)); offset = odp_packet_l4_offset(pkt); /* udp */ if (ip->proto == ODPH_IPPROTO_UDP) { odp_atomic_inc_u64(&counters.udp); } /* icmp */ if (ip->proto == ODPH_IPPROTO_ICMP) { icmp = (odph_icmphdr_t *)(buf + offset); /* echo reply */ if (icmp->type == ICMP_ECHOREPLY) { odp_atomic_inc_u64(&counters.icmp); memcpy(&tvsend, buf + offset + ODPH_ICMPHDR_LEN, sizeof(struct timeval)); /* TODO This should be changed to use an * ODP timer API once one exists. */ gettimeofday(&tvrecv, NULL); tv_sub(&tvrecv, &tvsend); rtt = tvrecv.tv_sec*1000 + tvrecv.tv_usec/1000; rlen += sprintf(msg + rlen, "ICMP Echo Reply seq %d time %.1f ", odp_be_to_cpu_16(icmp->un.echo.sequence) , rtt); } else if (icmp->type == ICMP_ECHO) { rlen += sprintf(msg + rlen, "Icmp Echo Request"); } msg[rlen] = '\0'; printf(" [%02i] %s\n", thr, msg); } } }
uint8_t *odp_packet_l4(odp_packet_t pkt) { const size_t offset = odp_packet_l4_offset(pkt); if (odp_unlikely(offset == ODP_PACKET_OFFSET_INVALID)) return NULL; return odp_packet_buf_addr(pkt) + offset; }
static uint32_t cls_pkt_get_seq(odp_packet_t pkt) { uint32_t offset; cls_test_packet_t data; offset = odp_packet_l4_offset(pkt); if (offset) { odp_packet_copydata_out(pkt, offset + ODPH_UDPHDR_LEN, sizeof(data), &data); if (data.magic == DATA_MAGIC) return data.seq; } return TEST_SEQ_INVALID; }
static int cls_pkt_set_seq(odp_packet_t pkt) { static uint32_t seq; cls_test_packet_t data; uint32_t offset; int status; data.magic = DATA_MAGIC; data.seq = ++seq; offset = odp_packet_l4_offset(pkt); CU_ASSERT_FATAL(offset != 0); status = odp_packet_copydata_in(pkt, offset + ODPH_UDPHDR_LEN, sizeof(data), &data); return status; }
/* * Check if a packet payload contains test payload magic number. */ static int pktio_pkt_has_magic(odp_packet_t pkt) { size_t l4_off; pkt_head_t pkt_hdr; l4_off = odp_packet_l4_offset(pkt); if (l4_off) { int ret = odp_packet_copydata_out(pkt, l4_off+ODPH_UDPHDR_LEN, sizeof(pkt_hdr), &pkt_hdr); if (ret != 0) return 0; if (pkt_hdr.magic == TEST_HDR_MAGIC) return 1; } return 0; }
static int ipc_second_process(void) { odp_pktio_t ipc_pktio; odp_pool_param_t params; odp_pool_t pool; odp_packet_t pkt_tbl[MAX_PKT_BURST]; odp_packet_t alloc_pkt; int pkts; int ret; int i; odp_time_t start_cycle; odp_time_t cycle; odp_time_t diff; odp_time_t wait; uint64_t stat_pkts = 0; odp_pktin_queue_t pktin; /* Create packet pool */ memset(¶ms, 0, sizeof(params)); params.pkt.seg_len = SHM_PKT_POOL_BUF_SIZE; params.pkt.len = SHM_PKT_POOL_BUF_SIZE; params.pkt.num = SHM_PKT_POOL_SIZE; params.type = ODP_POOL_PACKET; pool = odp_pool_create("packet_pool2", ¶ms); if (pool == ODP_POOL_INVALID) { EXAMPLE_ERR("Error: packet pool create failed.\n"); exit(EXIT_FAILURE); } ipc_pktio = create_pktio(pool); wait = odp_time_local_from_ns(run_time_sec * ODP_TIME_SEC_IN_NS); start_cycle = odp_time_local(); if (odp_pktin_queue(ipc_pktio, &pktin, 1) != 1) { EXAMPLE_ERR("no input queue\n"); return -1; } /* start ipc pktio, i.e. wait until other process connects */ for (;;) { /* 1. exit loop if time specified */ if (run_time_sec) { cycle = odp_time_local(); diff = odp_time_diff(cycle, start_cycle); if (odp_time_cmp(wait, diff) < 0) { printf("timeout exit, run_time_sec %d\n", run_time_sec); goto not_started; } } ret = odp_pktio_start(ipc_pktio); if (!ret) break; } for (;;) { /* exit loop if time specified */ if (run_time_sec) { cycle = odp_time_local(); diff = odp_time_diff(cycle, start_cycle); if (odp_time_cmp(wait, diff) < 0) { EXAMPLE_DBG("exit after %d seconds\n", run_time_sec); break; } } /* recv some packets and change MAGIC to MAGIC_2 */ pkts = odp_pktin_recv(pktin, pkt_tbl, MAX_PKT_BURST); if (pkts <= 0) continue; for (i = 0; i < pkts; i++) { odp_packet_t pkt = pkt_tbl[i]; pkt_head_t head; size_t off; off = odp_packet_l4_offset(pkt); if (off == ODP_PACKET_OFFSET_INVALID) EXAMPLE_ABORT("invalid l4 offset\n"); off += ODPH_UDPHDR_LEN; ret = odp_packet_copy_to_mem(pkt, off, sizeof(head), &head); if (ret) EXAMPLE_ABORT("unable copy out head data"); if (head.magic != TEST_SEQ_MAGIC) EXAMPLE_ABORT("Wrong head magic!"); /* Modify magic number in packet */ head.magic = TEST_SEQ_MAGIC_2; ret = odp_packet_copy_from_mem(pkt, off, sizeof(head), &head); if (ret) EXAMPLE_ABORT("unable to copy in head data"); } /* send all packets back */ ret = ipc_odp_packet_send_or_free(ipc_pktio, pkt_tbl, pkts); if (ret < 0) EXAMPLE_ABORT("can not send packets\n"); stat_pkts += ret; /* alloc packet from local pool, set magic to ALLOC_MAGIC, * and send it.*/ alloc_pkt = odp_packet_alloc(pool, SHM_PKT_POOL_BUF_SIZE); if (alloc_pkt != ODP_PACKET_INVALID) { pkt_head_t head; size_t off; odp_packet_l4_offset_set(alloc_pkt, 30); head.magic = TEST_ALLOC_MAGIC; off = odp_packet_l4_offset(alloc_pkt); off += ODPH_UDPHDR_LEN; ret = odp_packet_copy_from_mem(alloc_pkt, off, sizeof(head), &head); if (ret) EXAMPLE_ABORT("unable to copy in head data"); pkt_tbl[0] = alloc_pkt; ret = ipc_odp_packet_send_or_free(ipc_pktio, pkt_tbl, 1); if (ret < 0) EXAMPLE_ABORT("can not send packets\n"); stat_pkts += 1; } } /* cleanup and exit */ ret = odp_pktio_stop(ipc_pktio); if (ret) { EXAMPLE_DBG("ipc2: odp_pktio_stop error %d\n", ret); return -1; } not_started: ret = odp_pktio_close(ipc_pktio); if (ret) { EXAMPLE_DBG("ipc2: odp_pktio_close error %d\n", ret); return -1; } ret = odp_pool_destroy(pool); if (ret) EXAMPLE_DBG("ipc2: pool_destroy error %d\n", ret); return stat_pkts > 1000 ? 0 : -1; }