summaryrefslogtreecommitdiffstats
path: root/src/rpc-server
diff options
context:
space:
mode:
Diffstat (limited to 'src/rpc-server')
-rw-r--r--src/rpc-server/commands/trex_rpc_cmd_general.cpp17
-rw-r--r--src/rpc-server/commands/trex_rpc_cmd_stream.cpp160
-rw-r--r--src/rpc-server/commands/trex_rpc_cmd_test.cpp10
-rw-r--r--src/rpc-server/trex_rpc_cmd.cpp115
-rw-r--r--src/rpc-server/trex_rpc_cmd_api.h33
5 files changed, 210 insertions, 125 deletions
diff --git a/src/rpc-server/commands/trex_rpc_cmd_general.cpp b/src/rpc-server/commands/trex_rpc_cmd_general.cpp
index ac35babf..484cd2b9 100644
--- a/src/rpc-server/commands/trex_rpc_cmd_general.cpp
+++ b/src/rpc-server/commands/trex_rpc_cmd_general.cpp
@@ -19,9 +19,12 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
#include "trex_rpc_cmds.h"
-#include <../linux_dpdk/version.h>
#include <trex_rpc_server_api.h>
+#ifndef TREX_RPC_MOCK_SERVER
+ #include <../linux_dpdk/version.h>
+#endif
+
using namespace std;
/**
@@ -36,12 +39,24 @@ TrexRpcCmdGetStatus::_run(const Json::Value &params, Json::Value &result) {
Json::Value &section = result["result"];
+ #ifndef TREX_RPC_MOCK_SERVER
+
section["general"]["version"] = VERSION_BUILD_NUM;
section["general"]["build_date"] = get_build_date();
section["general"]["build_time"] = get_build_time();
section["general"]["version_user"] = VERSION_USER;
section["general"]["uptime"] = TrexRpcServer::get_server_uptime();
+ #else
+
+ section["general"]["version"] = "v0.0";
+ section["general"]["build_date"] = __DATE__;
+ section["general"]["build_time"] = __TIME__;
+ section["general"]["version_user"] = "MOCK";
+ section["general"]["uptime"] = TrexRpcServer::get_server_uptime();
+
+ #endif
+
return (TREX_RPC_CMD_OK);
}
diff --git a/src/rpc-server/commands/trex_rpc_cmd_stream.cpp b/src/rpc-server/commands/trex_rpc_cmd_stream.cpp
index 58226a6b..fcd91ab7 100644
--- a/src/rpc-server/commands/trex_rpc_cmd_stream.cpp
+++ b/src/rpc-server/commands/trex_rpc_cmd_stream.cpp
@@ -21,134 +21,78 @@ limitations under the License.
#include "trex_rpc_cmds.h"
#include <../linux_dpdk/version.h>
#include <trex_rpc_server_api.h>
+#include <trex_stream_api.h>
+#include <trex_stateless_api.h>
-using namespace std;
+#include <iostream>
-/**
- * Stateless stream mode
- * abstract class
- */
-class TrexStreamMode {
-public:
- enum mode_e {
- CONTINUOUS,
- SINGLE_BURST,
- MULTI_BURST
- };
-
- virtual mode_e get_runtime_type() = 0;
- virtual ~TrexStreamMode() {}
-};
+using namespace std;
/**
- * stream mode continuous
+ * add new stream
*
- * @author imarom (30-Aug-15)
*/
-class TrexStreamModeContinuous : public TrexStreamMode {
-public:
- mode_e get_runtime_type() {
- return (CONTINUOUS);
- }
-private:
- uint32_t pps;
-};
+trex_rpc_cmd_rc_e
+TrexRpcCmdAddStream::_run(const Json::Value &params, Json::Value &result) {
-/**
- * single burst mode
- *
- */
-class TrexStreamModeSingleBurst : public TrexStreamMode {
-public:
- mode_e get_runtime_type() {
- return (SINGLE_BURST);
- }
-private:
+ TrexStream *stream;
- uint32_t packets;
- uint32_t pps;
-};
+ check_param_count(params, 1, result);
+
+ const Json::Value &section = parse_object(params, "stream", result);
-class TrexStreamModeMultiBurst : public TrexStreamMode {
-public:
+ /* get the type of the stream */
+ const Json::Value &mode = parse_object(section, "mode", result);
+ string type = parse_string(mode, "type", result);
+
+ if (type == "continuous") {
+ stream = new TrexStreamContinuous();
+ } else if (type == "single_burst") {
+ stream = new TrexStreamSingleBurst();
+ } else if (type == "multi_burst") {
+ stream = new TrexStreamMultiBurst();
+ } else {
+ generate_err(result, "bad stream type provided: '" + type + "'");
+ }
- mode_e get_runtime_type() {
- return (MULTI_BURST);
+ if (!stream) {
+ generate_internal_err(result, "unable to allocate memory");
}
-private:
+ /* create a new steram and populate it */
+ stream->stream_id = parse_int(section, "stream_id", result);
+ stream->port_id = parse_int(section, "port_id", result);
+ stream->isg_usec = parse_double(section, "Is", result);
- uint32_t pps;
- double ibg_usec;
- uint32_t number_of_bursts;
- uint32_t pkts_per_burst;
-};
+ stream->next_stream_id = parse_int(section, "next_stream_id", result);
+ stream->loop_count = parse_int(section, "loop_count", result);
+ const Json::Value &pkt = parse_array(section, "packet", result);
-/**
- * Stateless Stream
- *
- */
-class TrexStatelessStream {
- friend class TrexRpcCmdAddStream;
-
-public:
-
-private:
- /* config */
- uint32_t stream_id;
- uint8_t port_id;
- double isg_usec;
- uint32_t next_stream_id;
- uint32_t loop_count;
-
- /* indicators */
- bool enable;
- bool start;
-
- /* pkt */
- uint8_t *pkt;
- uint16_t pkt_len;
-
- /* stream mode */
- TrexStreamMode *mode;
-
- /* VM */
-
- /* RX check */
- struct {
- bool enable;
- bool seq_enable;
- bool latency;
- uint32_t stream_id;
-
- } rx_check;
-
-};
-/**
- * add new stream
- *
- */
-trex_rpc_cmd_rc_e
-TrexRpcCmdAddStream::_run(const Json::Value &params, Json::Value &result) {
+ if ( (pkt.size() < TrexStream::MIN_PKT_SIZE_BYTES) || (pkt.size() > TrexStream::MAX_PKT_SIZE_BYTES) ) {
+ generate_err(result, "bad packet size provided: should be between 64B and 9K");
+ }
- TrexStatelessStream stream;
+ stream->pkt = new uint8_t[pkt.size()];
+ if (!stream->pkt) {
+ generate_internal_err(result, "unable to allocate memory");
+ }
- check_param_count(params, 1, result);
- check_field_type(params, "stream", FIELD_TYPE_OBJ, result);
+ for (int i = 0; i < pkt.size(); i++) {
+ stream->pkt[i] = parse_byte(pkt, i, result);
+ }
- Json::Value &section = result["stream"];
-
- /* create a new steram and populate it */
-
- check_field_type(section, "stream_id", FIELD_TYPE_INT, result);
- stream.stream_id = section["stream_id"].asInt();
+ /* register the stream to the port */
- check_field_type(section, "port_id", FIELD_TYPE_INT, result);
- stream.port_id = section["port_id"].asInt();
+ /* port id should be between 0 and count - 1 */
+ if (stream->port_id >= get_trex_stateless()->get_port_count()) {
+ std::stringstream ss;
+ ss << "invalid port id - should be between 0 and " << get_trex_stateless()->get_port_count();
+ generate_err(result, ss.str());
+ }
- check_field_type(section, "Is", FIELD_TYPE_DOUBLE, result);
- stream.isg_usec = section["Is"].asDouble();
+ TrexStatelessPort * port = get_trex_stateless()->get_port_by_id(stream->port_id);
+ port->get_stream_table()->add_stream(stream);
return (TREX_RPC_CMD_OK);
}
diff --git a/src/rpc-server/commands/trex_rpc_cmd_test.cpp b/src/rpc-server/commands/trex_rpc_cmd_test.cpp
index e67de286..473cbb70 100644
--- a/src/rpc-server/commands/trex_rpc_cmd_test.cpp
+++ b/src/rpc-server/commands/trex_rpc_cmd_test.cpp
@@ -36,10 +36,9 @@ TrexRpcCmdTestAdd::_run(const Json::Value &params, Json::Value &result) {
const Json::Value &y = params["y"];
check_param_count(params, 2, result);
- check_field_type(params, "x", FIELD_TYPE_INT, result);
- check_field_type(params, "y", FIELD_TYPE_INT, result);
- result["result"] = x.asInt() + y.asInt();
+ result["result"] = parse_int(params, "x", result) + parse_int(params, "y", result);
+
return (TREX_RPC_CMD_OK);
}
@@ -55,10 +54,9 @@ TrexRpcCmdTestSub::_run(const Json::Value &params, Json::Value &result) {
const Json::Value &y = params["y"];
check_param_count(params, 2, result);
- check_field_type(params, "x", TrexRpcCommand::FIELD_TYPE_INT, result);
- check_field_type(params, "y", TrexRpcCommand::FIELD_TYPE_INT, result);
- result["result"] = x.asInt() - y.asInt();
+ result["result"] = parse_int(params, "x", result) - parse_int(params, "y", result);
+
return (TREX_RPC_CMD_OK);
}
diff --git a/src/rpc-server/trex_rpc_cmd.cpp b/src/rpc-server/trex_rpc_cmd.cpp
index 1ad94fb5..1ba36e32 100644
--- a/src/rpc-server/trex_rpc_cmd.cpp
+++ b/src/rpc-server/trex_rpc_cmd.cpp
@@ -41,13 +41,14 @@ TrexRpcCommand::check_param_count(const Json::Value &params, int expected, Json:
std::stringstream ss;
ss << "method expects '" << expected << "' paramteres, '" << params.size() << "' provided";
generate_err(result, ss.str());
- throw TrexRpcCommandException(TREX_RPC_CMD_PARAM_COUNT_ERR);
}
}
const char *
TrexRpcCommand::type_to_str(field_type_e type) {
switch (type) {
+ case FIELD_TYPE_BYTE:
+ return "byte";
case FIELD_TYPE_BOOL:
return "bool";
case FIELD_TYPE_INT:
@@ -58,7 +59,7 @@ TrexRpcCommand::type_to_str(field_type_e type) {
return "object";
case FIELD_TYPE_STR:
return "string";
- case FILED_TYPE_ARRAY:
+ case FIELD_TYPE_ARRAY:
return "array";
default:
@@ -72,6 +73,8 @@ TrexRpcCommand::json_type_to_name(const Json::Value &value) {
switch(value.type()) {
case Json::nullValue:
return "null";
+ case Json::intValue:
+ return "int";
case Json::uintValue:
return "uint";
case Json::realValue:
@@ -90,23 +93,102 @@ TrexRpcCommand::json_type_to_name(const Json::Value &value) {
}
}
+
+uint8_t
+TrexRpcCommand::parse_byte(const Json::Value &parent, const std::string &name, Json::Value &result) {
+ check_field_type(parent, name, FIELD_TYPE_BYTE, result);
+ return parent[name].asUInt();
+}
+
+uint8_t
+TrexRpcCommand::parse_byte(const Json::Value &parent, int index, Json::Value &result) {
+ check_field_type(parent, index, FIELD_TYPE_BYTE, result);
+ return parent[index].asUInt();
+}
+
+int
+TrexRpcCommand::parse_int(const Json::Value &parent, const std::string &name, Json::Value &result) {
+ check_field_type(parent, name, FIELD_TYPE_INT, result);
+ return parent[name].asInt();
+}
+
+bool
+TrexRpcCommand::parse_bool(const Json::Value &parent, const std::string &name, Json::Value &result) {
+ check_field_type(parent, name, FIELD_TYPE_BOOL, result);
+ return parent[name].asBool();
+}
+
+double
+TrexRpcCommand::parse_double(const Json::Value &parent, const std::string &name, Json::Value &result) {
+ check_field_type(parent, name, FIELD_TYPE_DOUBLE, result);
+ return parent[name].asDouble();
+}
+
+const std::string
+TrexRpcCommand::parse_string(const Json::Value &parent, const std::string &name, Json::Value &result) {
+ check_field_type(parent, name, FIELD_TYPE_STR, result);
+ return parent[name].asString();
+}
+
+const Json::Value &
+TrexRpcCommand::parse_object(const Json::Value &parent, const std::string &name, Json::Value &result) {
+ check_field_type(parent, name, FIELD_TYPE_OBJ, result);
+ return parent[name];
+}
+
+const Json::Value &
+TrexRpcCommand::parse_array(const Json::Value &parent, const std::string &name, Json::Value &result) {
+ check_field_type(parent, name, FIELD_TYPE_ARRAY, result);
+ return parent[name];
+}
+
+/**
+ * for index element (array)
+ */
void
-TrexRpcCommand::check_field_type(const Json::Value &parent, const std::string &name, field_type_e type, Json::Value &result) {
+TrexRpcCommand::check_field_type(const Json::Value &parent, int index, field_type_e type, Json::Value &result) {
+
+ /* should never get here without parent being array */
+ if (!parent.isArray()) {
+ throw TrexRpcException("internal parsing error");
+ }
+
+ const Json::Value &field = parent[index];
+
std::stringstream ss;
+ ss << "array element: " << (index + 1) << " ";
+ check_field_type_common(field, ss.str(), type, result);
+}
+
+void
+TrexRpcCommand::check_field_type(const Json::Value &parent, const std::string &name, field_type_e type, Json::Value &result) {
+ /* should never get here without parent being object */
+ if (!parent.isObject()) {
+ throw TrexRpcException("internal parsing error");
+ }
- /* check if field exists , does not add the field because its const */
const Json::Value &field = parent[name];
+ check_field_type_common(field, name, type, result);
+}
+void
+TrexRpcCommand::check_field_type_common(const Json::Value &field, const std::string &name, field_type_e type, Json::Value &result) {
+ std::stringstream ss;
/* first check if field exists */
if (field == Json::Value::null) {
- ss << "field '" << name << "' missing";
+ ss << "field '" << name << "' is missing";
generate_err(result, ss.str());
- throw (TrexRpcCommandException(TREX_RPC_CMD_PARAM_PARSE_ERR));
}
bool rc = true;
switch (type) {
+ case FIELD_TYPE_BYTE:
+ if ( (!field.isUInt()) || (field.asInt() > 0xFF)) {
+ rc = false;
+ }
+ break;
+
case FIELD_TYPE_BOOL:
if (!field.isBool()) {
rc = false;
@@ -136,12 +218,21 @@ TrexRpcCommand::check_field_type(const Json::Value &parent, const std::string &n
rc = false;
}
break;
- }
+ case FIELD_TYPE_ARRAY:
+ if (!field.isArray()) {
+ rc = false;
+ }
+ break;
+
+ default:
+ throw TrexRpcException("unhandled type");
+ break;
+
+ }
if (!rc) {
ss << "error at offset: " << field.getOffsetStart() << " - '" << name << "' is '" << json_type_to_name(field) << "', expecting '" << type_to_str(type) << "'";
generate_err(result, ss.str());
- throw (TrexRpcCommandException(TREX_RPC_CMD_PARAM_PARSE_ERR));
}
}
@@ -149,4 +240,12 @@ TrexRpcCommand::check_field_type(const Json::Value &parent, const std::string &n
void
TrexRpcCommand::generate_err(Json::Value &result, const std::string &msg) {
result["specific_err"] = msg;
+ throw (TrexRpcCommandException(TREX_RPC_CMD_PARAM_PARSE_ERR));
+}
+
+void
+TrexRpcCommand::generate_internal_err(Json::Value &result, const std::string &msg) {
+ result["specific_err"] = msg;
+ throw (TrexRpcCommandException(TREX_RPC_CMD_INTERNAL_ERR));
}
+
diff --git a/src/rpc-server/trex_rpc_cmd_api.h b/src/rpc-server/trex_rpc_cmd_api.h
index 34e6ba0a..40f839df 100644
--- a/src/rpc-server/trex_rpc_cmd_api.h
+++ b/src/rpc-server/trex_rpc_cmd_api.h
@@ -90,12 +90,13 @@ protected:
* different types of fields
*/
enum field_type_e {
+ FIELD_TYPE_BYTE,
FIELD_TYPE_INT,
FIELD_TYPE_DOUBLE,
FIELD_TYPE_BOOL,
FIELD_TYPE_STR,
FIELD_TYPE_OBJ,
- FILED_TYPE_ARRAY
+ FIELD_TYPE_ARRAY
};
/**
@@ -110,11 +111,32 @@ protected:
void check_param_count(const Json::Value &params, int expected, Json::Value &result);
/**
+ * parse functions
+ *
+ */
+ uint8_t parse_byte(const Json::Value &parent, const std::string &name, Json::Value &result);
+ int parse_int(const Json::Value &parent, const std::string &name, Json::Value &result);
+ double parse_double(const Json::Value &parent, const std::string &name, Json::Value &result);
+ bool parse_bool(const Json::Value &parent, const std::string &name, Json::Value &result);
+ const std::string parse_string(const Json::Value &parent, const std::string &name, Json::Value &result);
+ const Json::Value & parse_object(const Json::Value &parent, const std::string &name, Json::Value &result);
+ const Json::Value & parse_array(const Json::Value &parent, const std::string &name, Json::Value &result);
+
+ uint8_t parse_byte(const Json::Value &parent, int index, Json::Value &result);
+ int parse_int(const Json::Value &parent, int index, Json::Value &result);
+ double parse_double(const Json::Value &parent, int index, Json::Value &result);
+ bool parse_bool(const Json::Value &parent, int index, Json::Value &result);
+ const std::string parse_string(const Json::Value &parent, int index, Json::Value &result);
+ const Json::Value & parse_object(const Json::Value &parent, int index, Json::Value &result);
+ const Json::Value & parse_array(const Json::Value &parent, int index, Json::Value &result);
+
+ /**
* check field type
*
*/
- //void check_field_type(const Json::Value &field, field_type_e type, Json::Value &result);
void check_field_type(const Json::Value &parent, const std::string &name, field_type_e type, Json::Value &result);
+ void check_field_type(const Json::Value &parent, int index, field_type_e type, Json::Value &result);
+ void check_field_type_common(const Json::Value &field, const std::string &name, field_type_e type, Json::Value &result);
/**
* error generating functions
@@ -122,6 +144,13 @@ protected:
*/
void generate_err(Json::Value &result, const std::string &msg);
+
+ /**
+ * internal error
+ *
+ */
+ void generate_internal_err(Json::Value &result, const std::string &msg);
+
/**
* translate enum to string
*