summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorimarom <imarom@cisco.com>2016-09-04 15:25:42 +0300
committerimarom <imarom@cisco.com>2016-09-07 14:02:55 +0300
commit04eae221e7c0089ae974f86e3f6fe156d4cb56ce (patch)
tree53b378e86f8173a8cc1f4bf2107ce6f797a91760 /src
parent873e398fe2a52655b4d683acbcd05ef726cd97fa (diff)
DUAL mode - phase #1
Diffstat (limited to 'src')
-rwxr-xr-xsrc/common/erf.cpp17
-rw-r--r--src/rpc-server/commands/trex_rpc_cmd_general.cpp22
-rw-r--r--src/stateless/cp/trex_stateless_port.cpp30
-rw-r--r--src/stateless/cp/trex_stateless_port.h11
-rw-r--r--src/stateless/dp/trex_stateless_dp_core.cpp17
-rw-r--r--src/stateless/dp/trex_stateless_dp_core.h6
-rw-r--r--src/stateless/dp/trex_stream_node.h15
-rw-r--r--src/stateless/messaging/trex_stateless_messaging.cpp6
-rw-r--r--src/stateless/messaging/trex_stateless_messaging.h6
9 files changed, 87 insertions, 43 deletions
diff --git a/src/common/erf.cpp b/src/common/erf.cpp
index 304f758b..c4c14998 100755
--- a/src/common/erf.cpp
+++ b/src/common/erf.cpp
@@ -108,7 +108,7 @@ int erf_open(wtap *wth, int *err)
memset(&prevts, 0, sizeof(prevts));
- int records_for_erf_check = 10;
+ long records_for_erf_check = 10;
/* ERF is a little hard because there's no magic number */
@@ -166,7 +166,7 @@ int erf_open(wtap *wth, int *err)
}
-int erf_read(wtap *wth,char *p,uint32_t *sec,uint32_t *nsec)
+int erf_read(wtap *wth,char *p,uint32_t *sec,uint32_t *nsec, uint8_t *interface)
{
erf_header_t header;
int common_type = 0;
@@ -214,6 +214,7 @@ int erf_read(wtap *wth,char *p,uint32_t *sec,uint32_t *nsec)
uint32_t frac =(ts &0xffffffff);
double usec_frac =(double)frac*(1000000000.0/(4294967296.0));
*nsec = (uint32_t) (usec_frac);
+ *interface = header.flags & 0x3;
return (g_ntohs(header.wlen));
}else{
return (-1);
@@ -438,15 +439,19 @@ void CErfFileReader::Delete(){
bool CErfFileReader::ReadPacket(CCapPktRaw * lpPacket){
+ uint8_t interface;
wtap wth;
+
wth.fh = m_handle;
- int length;
- length=erf_read(&wth,lpPacket->raw,&lpPacket->time_sec,
- &lpPacket->time_nsec
- );
+ int length = erf_read(&wth,
+ lpPacket->raw,
+ &lpPacket->time_sec,
+ &lpPacket->time_nsec,
+ &interface);
if ( length >0 ) {
lpPacket->pkt_len =(uint16_t)length;
lpPacket->pkt_cnt++;
+ lpPacket->setInterface(interface);
return (true);
}
return (false);
diff --git a/src/rpc-server/commands/trex_rpc_cmd_general.cpp b/src/rpc-server/commands/trex_rpc_cmd_general.cpp
index cd845fca..ba3c1658 100644
--- a/src/rpc-server/commands/trex_rpc_cmd_general.cpp
+++ b/src/rpc-server/commands/trex_rpc_cmd_general.cpp
@@ -509,16 +509,26 @@ trex_rpc_cmd_rc_e
TrexRpcCmdPushRemote::_run(const Json::Value &params, Json::Value &result) {
uint8_t port_id = parse_port(params, result);
- std::string pcap_filename = parse_string(params, "pcap_filename", result);
- double ipg_usec = parse_double(params, "ipg_usec", result);
- double speedup = parse_double(params, "speedup", result);
- uint32_t count = parse_uint32(params, "count", result);
- double duration = parse_double(params, "duration", result);
+ std::string pcap_filename = parse_string(params, "pcap_filename", result);
+ double ipg_usec = parse_double(params, "ipg_usec", result);
+ double speedup = parse_double(params, "speedup", result);
+ uint32_t count = parse_uint32(params, "count", result);
+ double duration = parse_double(params, "duration", result);
+ bool is_dual = parse_bool(params, "is_dual", result, false);
+ std::string slave_handler = parse_string(params, "slave_handler", result, "");
TrexStatelessPort *port = get_stateless_obj()->get_port_by_id(port_id);
+ if (is_dual) {
+ TrexStatelessPort *slave = get_stateless_obj()->get_port_by_id(port_id ^ 0x1);
+
+ if (!slave->get_owner().verify(slave_handler)) {
+ generate_execute_err(result, "incorrect or missing slave port handler");
+ }
+ }
+
try {
- port->push_remote(pcap_filename, ipg_usec, speedup, count, duration);
+ port->push_remote(pcap_filename, ipg_usec, speedup, count, duration, is_dual);
} catch (const TrexException &ex) {
generate_execute_err(result, ex.what());
}
diff --git a/src/stateless/cp/trex_stateless_port.cpp b/src/stateless/cp/trex_stateless_port.cpp
index 2a545c5f..df50d3e2 100644
--- a/src/stateless/cp/trex_stateless_port.cpp
+++ b/src/stateless/cp/trex_stateless_port.cpp
@@ -244,7 +244,7 @@ void
TrexStatelessPort::start_traffic(const TrexPortMultiplier &mul, double duration, bool force, uint64_t core_mask) {
/* command allowed only on state stream */
- verify_state(PORT_STATE_STREAMS);
+ verify_state(PORT_STATE_STREAMS, "start");
/* just making sure no leftovers... */
delete_streams_graph();
@@ -370,7 +370,7 @@ TrexStatelessPort::stop_traffic(void) {
void
TrexStatelessPort::remove_rx_filters(void) {
/* only valid when IDLE or with streams and not TXing */
- verify_state(PORT_STATE_STREAMS);
+ verify_state(PORT_STATE_STREAMS, "remove_rx_filters");
for (auto entry : m_stream_table) {
get_stateless_obj()->m_rx_flow_stat.stop_stream(entry.second);
@@ -410,7 +410,7 @@ TrexStatelessPort::is_core_active(int core_id) {
void
TrexStatelessPort::pause_traffic(void) {
- verify_state(PORT_STATE_TX);
+ verify_state(PORT_STATE_TX, "pause");
if (m_last_all_streams_continues == false) {
throw TrexException(" pause is supported when all streams are in continues mode ");
@@ -441,7 +441,7 @@ TrexStatelessPort::pause_traffic(void) {
void
TrexStatelessPort::resume_traffic(void) {
- verify_state(PORT_STATE_PAUSE);
+ verify_state(PORT_STATE_PAUSE, "resume");
/* generate a message to all the relevant DP cores to start transmitting */
TrexStatelessCpToDpMsgBase *resume_msg = new TrexStatelessDpResume(m_port_id);
@@ -459,7 +459,7 @@ TrexStatelessPort::update_traffic(const TrexPortMultiplier &mul, bool force) {
double factor;
- verify_state(PORT_STATE_TX | PORT_STATE_PAUSE);
+ verify_state(PORT_STATE_TX | PORT_STATE_PAUSE, "update");
/* generate a message to all the relevant DP cores to start transmitting */
double new_factor = calculate_effective_factor(mul, force);
@@ -497,10 +497,11 @@ TrexStatelessPort::push_remote(const std::string &pcap_filename,
double ipg_usec,
double speedup,
uint32_t count,
- double duration) {
+ double duration,
+ bool is_dual) {
/* command allowed only on state stream */
- verify_state(PORT_STATE_IDLE | PORT_STATE_STREAMS);
+ verify_state(PORT_STATE_IDLE | PORT_STATE_STREAMS, "push_remote");
/* check that file exists */
CCapReaderBase *reader;
@@ -532,7 +533,8 @@ TrexStatelessPort::push_remote(const std::string &pcap_filename,
ipg_usec,
speedup,
count,
- duration);
+ duration,
+ is_dual);
send_message_to_dp(tx_core, push_msg);
/* update subscribers */
@@ -580,10 +582,12 @@ TrexStatelessPort::get_properties(std::string &driver, uint32_t &speed) {
}
bool
-TrexStatelessPort::verify_state(int state, bool should_throw) const {
+TrexStatelessPort::verify_state(int state, const char *cmd_name, bool should_throw) const {
if ( (state & m_port_state) == 0 ) {
if (should_throw) {
- throw TrexException("command cannot be executed on current state: '" + get_state_as_string() + "'");
+ std::stringstream ss;
+ ss << "command '" << cmd_name << "' cannot be executed on current state: '" << get_state_as_string() << "'";
+ throw TrexException(ss.str());
} else {
return false;
}
@@ -893,7 +897,7 @@ TrexStatelessPort::get_pci_info(std::string &pci_addr, int &numa_node) {
void
TrexStatelessPort::add_stream(TrexStream *stream) {
- verify_state(PORT_STATE_IDLE | PORT_STATE_STREAMS);
+ verify_state(PORT_STATE_IDLE | PORT_STATE_STREAMS, "add_stream");
get_stateless_obj()->m_rx_flow_stat.add_stream(stream);
@@ -906,7 +910,7 @@ TrexStatelessPort::add_stream(TrexStream *stream) {
void
TrexStatelessPort::remove_stream(TrexStream *stream) {
- verify_state(PORT_STATE_STREAMS);
+ verify_state(PORT_STATE_STREAMS, "remove_stream");
get_stateless_obj()->m_rx_flow_stat.del_stream(stream);
@@ -920,7 +924,7 @@ TrexStatelessPort::remove_stream(TrexStream *stream) {
void
TrexStatelessPort::remove_and_delete_all_streams() {
- verify_state(PORT_STATE_IDLE | PORT_STATE_STREAMS);
+ verify_state(PORT_STATE_IDLE | PORT_STATE_STREAMS, "remove_and_delete_all_streams");
vector<TrexStream *> streams;
get_object_list(streams);
diff --git a/src/stateless/cp/trex_stateless_port.h b/src/stateless/cp/trex_stateless_port.h
index ba86a279..147efc70 100644
--- a/src/stateless/cp/trex_stateless_port.h
+++ b/src/stateless/cp/trex_stateless_port.h
@@ -217,10 +217,11 @@ public:
*
*/
void push_remote(const std::string &pcap_filename,
- double ipg_usec,
- double speedup,
- uint32_t count,
- double duration);
+ double ipg_usec,
+ double speedup,
+ uint32_t count,
+ double duration,
+ bool is_dual);
/**
* get the port state
@@ -385,7 +386,7 @@ private:
return m_cores_id_list;
}
- bool verify_state(int state, bool should_throw = true) const;
+ bool verify_state(int state, const char *cmd_name, bool should_throw = true) const;
void change_state(port_state_e new_state);
diff --git a/src/stateless/dp/trex_stateless_dp_core.cpp b/src/stateless/dp/trex_stateless_dp_core.cpp
index 4d9137f1..e5679590 100644
--- a/src/stateless/dp/trex_stateless_dp_core.cpp
+++ b/src/stateless/dp/trex_stateless_dp_core.cpp
@@ -478,7 +478,8 @@ bool TrexStatelessDpPerPort::push_pcap(uint8_t port_id,
const std::string &pcap_filename,
double ipg_usec,
double speedup,
- uint32_t count) {
+ uint32_t count,
+ bool is_dual) {
/* push pcap can only happen on an idle port from the core prespective */
assert(m_state == TrexStatelessDpPerPort::ppSTATE_IDLE);
@@ -501,7 +502,8 @@ bool TrexStatelessDpPerPort::push_pcap(uint8_t port_id,
pcap_filename,
ipg_usec,
speedup,
- count);
+ count,
+ is_dual);
if (!rc) {
m_core->free_node((CGenNode *)pcap_node);
return (false);
@@ -1162,14 +1164,15 @@ TrexStatelessDpCore::push_pcap(uint8_t port_id,
double ipg_usec,
double speedup,
uint32_t count,
- double duration) {
+ double duration,
+ bool is_dual) {
TrexStatelessDpPerPort * lp_port = get_port_db(port_id);
lp_port->set_event_id(event_id);
/* delegate the command to the port */
- bool rc = lp_port->push_pcap(port_id, pcap_filename, ipg_usec, speedup, count);
+ bool rc = lp_port->push_pcap(port_id, pcap_filename, ipg_usec, speedup, count, is_dual);
if (!rc) {
/* report back that we stopped */
CNodeRing *ring = CMsgIns::Ins()->getCpDp()->getRingDpToCp(m_core->m_thread_id);
@@ -1253,7 +1256,8 @@ bool CGenNodePCAP::create(uint8_t port_id,
const std::string &pcap_filename,
double ipg_usec,
double speedup,
- uint32_t count) {
+ uint32_t count,
+ bool is_dual) {
std::stringstream ss;
m_type = CGenNode::PCAP_PKT;
@@ -1261,7 +1265,8 @@ bool CGenNodePCAP::create(uint8_t port_id,
m_src_port = 0;
m_port_id = port_id;
m_count = count;
-
+ m_is_dual = is_dual;
+
/* mark this node as slow path */
set_slow_path(true);
diff --git a/src/stateless/dp/trex_stateless_dp_core.h b/src/stateless/dp/trex_stateless_dp_core.h
index 9babb172..b386daf7 100644
--- a/src/stateless/dp/trex_stateless_dp_core.h
+++ b/src/stateless/dp/trex_stateless_dp_core.h
@@ -75,7 +75,8 @@ public:
const std::string &pcap_filename,
double ipg_usec,
double speedup,
- uint32_t count);
+ uint32_t count,
+ bool is_dual);
bool stop_traffic(uint8_t port_id,
bool stop_on_id,
@@ -184,7 +185,8 @@ public:
double ipg_usec,
double speedup,
uint32_t count,
- double duration);
+ double duration,
+ bool is_dual);
/**
diff --git a/src/stateless/dp/trex_stream_node.h b/src/stateless/dp/trex_stream_node.h
index 8a68625c..b4910fce 100644
--- a/src/stateless/dp/trex_stream_node.h
+++ b/src/stateless/dp/trex_stream_node.h
@@ -468,7 +468,8 @@ public:
const std::string &pcap_filename,
double ipg_usec,
double speedup,
- uint32_t count);
+ uint32_t count,
+ bool is_dual);
/**
* destroy the node cleaning up any data
@@ -476,6 +477,10 @@ public:
*/
void destroy();
+ bool is_dual() const {
+ return m_is_dual;
+ }
+
/**
* advance - will read the next packet
*
@@ -505,6 +510,10 @@ public:
}
}
+ if (is_dual()) {
+ uint8_t dir = m_raw_packet->getInterface() & 0x1;
+ set_mbuf_dir(dir);
+ }
}
/**
@@ -615,8 +624,10 @@ private:
uint8_t m_port_id;
+ bool m_is_dual;
+
/* pad to match the size of CGenNode */
- uint8_t m_pad_end[33];
+ uint8_t m_pad_end[32];
} __rte_cache_aligned;
diff --git a/src/stateless/messaging/trex_stateless_messaging.cpp b/src/stateless/messaging/trex_stateless_messaging.cpp
index 1cbacb6f..95613b41 100644
--- a/src/stateless/messaging/trex_stateless_messaging.cpp
+++ b/src/stateless/messaging/trex_stateless_messaging.cpp
@@ -193,7 +193,8 @@ TrexStatelessDpPushPCAP::handle(TrexStatelessDpCore *dp_core) {
m_ipg_usec,
m_speedup,
m_count,
- m_duration);
+ m_duration,
+ m_is_dual);
return true;
}
@@ -205,7 +206,8 @@ TrexStatelessDpPushPCAP::clone() {
m_ipg_usec,
m_speedup,
m_count,
- m_duration);
+ m_duration,
+ m_is_dual);
return new_msg;
}
diff --git a/src/stateless/messaging/trex_stateless_messaging.h b/src/stateless/messaging/trex_stateless_messaging.h
index 9b1f2e31..fb2c27ab 100644
--- a/src/stateless/messaging/trex_stateless_messaging.h
+++ b/src/stateless/messaging/trex_stateless_messaging.h
@@ -259,13 +259,16 @@ public:
double ipg_usec,
double speedup,
uint32_t count,
- double duration) : m_pcap_filename(pcap_filename) {
+ double duration,
+ bool is_dual) : m_pcap_filename(pcap_filename) {
+
m_port_id = port_id;
m_event_id = event_id;
m_ipg_usec = ipg_usec;
m_speedup = speedup;
m_count = count;
m_duration = duration;
+ m_is_dual = is_dual;
}
virtual bool handle(TrexStatelessDpCore *dp_core);
@@ -280,6 +283,7 @@ private:
double m_duration;
uint32_t m_count;
uint8_t m_port_id;
+ bool m_is_dual;
};