#include <simgear/misc/stdint.hxx>
#include <simgear/props/props.hxx>
#include <simgear/props/props_io.hxx>
+#include <simgear/math/SGMath.hxx>
#include <Main/globals.hxx>
#include <Main/fg_props.hxx>
#include <Main/util.hxx>
#include "generic.hxx"
-FGGeneric::FGGeneric(vector<string> tokens) : exitOnError(false)
+FGGeneric::FGGeneric(vector<string> tokens) : exitOnError(false), initOk(false)
{
size_t configToken;
if (tokens[1] == "socket") {
configToken = 6;
}
- if (configToken >= tokens.size()) {
+ if ((configToken >= tokens.size())||(tokens[ configToken ] == "")) {
SG_LOG(SG_NETWORK, SG_ALERT,
- "Not enough tokens passed for generic protocol");
+ "Not enough tokens passed for generic '" << tokens[1] << "' protocol. ");
return;
}
if (direction != "in" && direction != "out" && direction != "bi") {
SG_LOG(SG_NETWORK, SG_ALERT, "Unsuported protocol direction: "
<< direction);
+ return;
}
reinit();
}
bool FGGeneric::parse_message_ascii(int length) {
- char *p2, *p1 = buf;
+ char *p1 = buf;
int i = -1;
int chunks = _in_message.size();
int line_separator_size = line_separator.size();
buf[length - line_separator_size] = 0;
}
+ size_t varsep_len = var_separator.length();
while ((++i < chunks) && p1) {
- p2 = strstr(p1, var_separator.c_str());
- if (p2) {
- *p2 = 0;
- p2 += var_separator.length();
+ char* p2 = NULL;
+
+ if (varsep_len > 0)
+ {
+ p2 = strstr(p1, var_separator.c_str());
+ if (p2) {
+ *p2 = 0;
+ p2 += varsep_len;
+ }
}
switch (_in_message[i].type) {
return true;
}
-bool FGGeneric::parse_message(int length) {
+bool FGGeneric::parse_message_len(int length) {
if (binary_mode) {
return parse_message_binary(length);
} else {
if (!binary_mode) {
length = io->readline( buf, FG_MAX_MSG_SIZE );
if ( length > 0 ) {
- parse_message( length );
+ parse_message_len( length );
} else {
SG_LOG( SG_IO, SG_ALERT, "Error reading data." );
return false;
} else {
length = io->read( buf, binary_record_length );
if ( length == binary_record_length ) {
- parse_message( length );
+ parse_message_len( length );
} else {
SG_LOG( SG_IO, SG_ALERT,
"Generic protocol: Received binary "
} else {
if (!binary_mode) {
while ((length = io->readline( buf, FG_MAX_MSG_SIZE )) > 0 ) {
- parse_message( length );
+ parse_message_len( length );
}
} else {
while ((length = io->read( buf, binary_record_length ))
== binary_record_length ) {
- parse_message( length );
+ parse_message_len( length );
}
if ( length > 0 ) {
SGPropertyNode *output = root.getNode("generic/output");
if (output) {
_out_message.clear();
- read_config(output, _out_message);
+ if (!read_config(output, _out_message))
+ {
+ // bad configuration
+ return;
+ }
}
} else if (direction == "in") {
SGPropertyNode *input = root.getNode("generic/input");
if (input) {
_in_message.clear();
- read_config(input, _in_message);
+ if (!read_config(input, _in_message))
+ {
+ // bad configuration
+ return;
+ }
if (!binary_mode && (line_separator.size() == 0 ||
*line_separator.rbegin() != '\n')) {
}
}
}
+
+ initOk = true;
}
-void
+bool
FGGeneric::read_config(SGPropertyNode *root, vector<_serial_prot> &msg)
{
binary_mode = root->getBoolValue("binary_mode");
int record_length = 0; // Only used for binary protocols.
vector<SGPropertyNode_ptr> chunks = root->getChildren("chunk");
+
for (unsigned int i = 0; i < chunks.size(); i++) {
_serial_prot chunk;
}
- if( binary_mode ) {
+ if( !binary_mode )
+ {
+ if ((chunks.size() > 1)&&(var_sep_string.length() == 0))
+ {
+ // ASCII protocols really need a separator when there is more than one chunk per line
+ SG_LOG(SG_IO, SG_ALERT,
+ "generic protocol: Invalid configuration. "
+ "'var_separator' must not be empty for protocols which have more than one chunk per line.");
+ return false;
+ }
+ }
+ else
+ {
if (binary_record_length == -1) {
binary_record_length = record_length;
} else if (binary_record_length < record_length) {
binary_record_length = record_length;
}
}
+
+ return true;
}
void FGGeneric::updateValue(FGGeneric::_serial_prot& prot, bool val)