rendered paste bodyOnly in ZWave/: ,
Only in ZWave/: a.txt
Only in ZWave/: a.txt~
Only in ZWave/: b.txt
Only in ZWave/: core
Only in ZWave/: log.txt
Only in ZWave/: log.txt~
Only in ZWave/: Main.d
Only in ZWave/: Main.o
diff -ur /code/ZWave/Makefile ZWave/Makefile
--- /code/ZWave/Makefile 2008-02-28 15:34:22.221387847 -0500
+++ ZWave/Makefile 2008-03-03 13:44:17.468127084 -0500
@@ -1,7 +1,7 @@
#<-dceag-mh-b->
GENDEV=../Gen_Devices
-SNR_CPPFLAGS ?= <-mkr_t_compile_defines->
+SNR_CPPFLAGS ?= -DKDE_LMCE -DDEBUG -DTHREAD_LOG -DLOG_ALL_QUERIES -I/opt/libxine1-pluto/include -I/opt/linphone-1.3.5/include
ROOT = ..
CXXFLAGS = -Wall -fPIC -ggdb3
@@ -14,9 +14,7 @@
LDFLAGS += -lmysqlclient_r
#<-mkr_B_use_mysql_wrapper_e->
-#<-mkr_b_use_mysql_wrapper_b->
-CPPFLAGS += -DUSE_MYSQL_WRAPPER
-#<-mkr_b_use_mysql_wrapper_e->
+#
MYNAME = ZWave
VERSION = 2.0.0
@@ -59,7 +57,7 @@
cp $@ ../bin
chmod +x post_make.sh
./post_make.sh $@
-
+
ZWave: $(sources:.cpp=.o)
$(CXX) -o $(MYNAME) $(call cpath,$+) $(LDFLAGS) $(LDLIBS)
cp $@ ../bin
Only in /code/ZWave/: Makefile~
diff -ur /code/ZWave/make_package.sh ZWave/make_package.sh
--- /code/ZWave/make_package.sh 2008-02-28 15:26:29.471873392 -0500
+++ ZWave/make_package.sh 2008-03-03 13:44:17.505125593 -0500
@@ -1,133 +1,133 @@
-#!/bin/bash
-
-#<-dceag-mp-b->
-#DCE_Package
-#DCE_TargetDir
-
-if [ "$#" != 3 ]; then
- echo "Syntax: $0 <application name> <version> <device template id>"
- exit 1
-fi
-
-PACK_LOC=../Packages
-ORIG_APPNAME="$1"
-APPNAME=pluto-`echo "$ORIG_APPNAME" | tr 'A-Z_' 'a-z\-'`
-APPVER="$2"
-DEVTMPL_ID="$3"
-
-PACK_NAME="$APPNAME-$APPVER"
-PACK_DIR="$PACK_LOC/$PACK_NAME"
-DISTRO=1 # 1=Debian
-
-GetMySQLResult()
-{
- local Q
-
- Q="$*"
- echo "$Q;" | mysql pluto_main | tail +2
- return "$?"
-}
-
-GetPackageDepends()
-{
- local Package_Number Package_Name
- local Q R
- local Row
-
- Package_Number="$1"
-
- Q="SELECT PK_Package, Name
-FROM Package_Package
-JOIN Package ON Package.PK_Package = FK_Package_DependsOn
-JOIN Package_Source ON Package_Source.FK_Package = PK_Package
-JOIN RepositorySource ON FK_RepositorySource = PK_RepositorySource
-JOIN Package_Source_Compat ON FK_Package_Source = PK_Package_Source
-WHERE Package_Package.FK_Package='$Package_Number' AND FK_RepositoryType=1 AND Package_Source_Compat.FK_Distro='$DISTRO' AND OnlyToBuild=0"
-
- R=$(GetMySQLResult "$Q") # TODO: test result
-
- echo "$R" |
- while read Row; do
- [ -z "$Row" ] && break # weird thing: we have to force an exit, else it loops forever
- Package_Number=$(echo "$Row" | cut -f1)
- Package_Name=$(echo "$Row" | cut -sf2)
- GetPackageDepends "$Package_Number"
- echo -n "$Package_Name "
- done
-}
-
-# return the packages needed by the device plus their dependencies
-GetDevicePackageList()
-{
- local Package_Number Package_Name
- local Q R
- local Row
-
- Device_Number="$1"
-
- Q="SELECT Package_Source.FK_Package,Name
-FROM DeviceTemplate
-JOIN Package_Source ON Package_Source.FK_Package=DeviceTemplate.FK_Package
-JOIN Package_Source_Compat ON FK_Package_Source=PK_Package_Source
-WHERE PK_DeviceTemplate='$Device_Number' AND FK_Distro='$DISTRO'"
-
- R=$(GetMySQLResult "$Q") # TODO: test result
-
- echo "$R" |
- while read Row; do
- [ -z "$Row" ] && break # weird thing: we have to force an exit, else it loops forever
- Package_Number=$(echo "$Row" | cut -f1)
- Package_Name=$(echo "$Row" | cut -sf2)
- GetPackageDepends "$Package_Number"
- echo -n "$Package_Name "
- done
-}
-
-#GetDevicePackageList "$DEVTMPL_ID"; echo
-PackageList=$(GetDevicePackageList "$DEVTMPL_ID")
-
-if [ ! -d "$PACK_LOC" ]; then
- mkdir -p "$PACK_LOC"
-fi
-
-if [ ! -d "$PACK_DIR" ]; then
- cp -a "$PACK_LOC/_Package_template" "$PACK_DIR"
-fi
-
-BIN_LOC="../../bin"
-LIB_LOC="../../lib"
-BIN_FILE="$BIN_LOC/$ORIG_APPNAME"
-PLUGIN_FILE="$BIN_LOC/$ORIG_APPNAME.so"
-LIB_FILE="$LIB_LOC/lib$ORIG_APPNAME.a"
-
-pushd "$PACK_DIR"
-
-mkdir -p root/usr/pluto/bin
-mkdir -p root/usr/pluto/lib
-
-echo "-- $BIN_FILE"
-if [ -f "$BIN_FILE" ]; then
- echo "Found bin file"
- cp "$BIN_FILE" root/usr/pluto/bin
-fi
-
-echo "-- $PLUGIN_FILE"
-if [ -f "$PLUGIN_FILE" ]; then
- echo "Found plugin file"
- cp "$PLUGIN_FILE" root/usr/pluto/bin
-fi
-
-echo "-- $LIB_FILE"
-if [ -f "$LIB_FILE" ]; then
- echo "Found lib file"
- cp "$LIB_FILE" root/usr/pluto/lib
-fi
-
-popd
-
-pushd "$PACK_LOC"
-./propagate.pl "$PACK_NAME" $PackageList
-popd
-
-#<-dceag-mp-e->
-
+#!/bin/bash
+
+#<-dceag-mp-b->
+#DCE_Package
+#DCE_TargetDir
+
+if [ "$#" != 3 ]; then
+ echo "Syntax: $0 <application name> <version> <device template id>"
+ exit 1
+fi
+
+PACK_LOC=../Packages
+ORIG_APPNAME="$1"
+APPNAME=pluto-`echo "$ORIG_APPNAME" | tr 'A-Z_' 'a-z\-'`
+APPVER="$2"
+DEVTMPL_ID="$3"
+
+PACK_NAME="$APPNAME-$APPVER"
+PACK_DIR="$PACK_LOC/$PACK_NAME"
+DISTRO=1 # 1=Debian
+
+GetMySQLResult()
+{
+ local Q
+
+ Q="$*"
+ echo "$Q;" | mysql pluto_main | tail +2
+ return "$?"
+}
+
+GetPackageDepends()
+{
+ local Package_Number Package_Name
+ local Q R
+ local Row
+
+ Package_Number="$1"
+
+ Q="SELECT PK_Package, Name
+FROM Package_Package
+JOIN Package ON Package.PK_Package = FK_Package_DependsOn
+JOIN Package_Source ON Package_Source.FK_Package = PK_Package
+JOIN RepositorySource ON FK_RepositorySource = PK_RepositorySource
+JOIN Package_Source_Compat ON FK_Package_Source = PK_Package_Source
+WHERE Package_Package.FK_Package='$Package_Number' AND FK_RepositoryType=1 AND Package_Source_Compat.FK_Distro='$DISTRO' AND OnlyToBuild=0"
+
+ R=$(GetMySQLResult "$Q") # TODO: test result
+
+ echo "$R" |
+ while read Row; do
+ [ -z "$Row" ] && break # weird thing: we have to force an exit, else it loops forever
+ Package_Number=$(echo "$Row" | cut -f1)
+ Package_Name=$(echo "$Row" | cut -sf2)
+ GetPackageDepends "$Package_Number"
+ echo -n "$Package_Name "
+ done
+}
+
+# return the packages needed by the device plus their dependencies
+GetDevicePackageList()
+{
+ local Package_Number Package_Name
+ local Q R
+ local Row
+
+ Device_Number="$1"
+
+ Q="SELECT Package_Source.FK_Package,Name
+FROM DeviceTemplate
+JOIN Package_Source ON Package_Source.FK_Package=DeviceTemplate.FK_Package
+JOIN Package_Source_Compat ON FK_Package_Source=PK_Package_Source
+WHERE PK_DeviceTemplate='$Device_Number' AND FK_Distro='$DISTRO'"
+
+ R=$(GetMySQLResult "$Q") # TODO: test result
+
+ echo "$R" |
+ while read Row; do
+ [ -z "$Row" ] && break # weird thing: we have to force an exit, else it loops forever
+ Package_Number=$(echo "$Row" | cut -f1)
+ Package_Name=$(echo "$Row" | cut -sf2)
+ GetPackageDepends "$Package_Number"
+ echo -n "$Package_Name "
+ done
+}
+
+#GetDevicePackageList "$DEVTMPL_ID"; echo
+PackageList=$(GetDevicePackageList "$DEVTMPL_ID")
+
+if [ ! -d "$PACK_LOC" ]; then
+ mkdir -p "$PACK_LOC"
+fi
+
+if [ ! -d "$PACK_DIR" ]; then
+ cp -a "$PACK_LOC/_Package_template" "$PACK_DIR"
+fi
+
+BIN_LOC="../../bin"
+LIB_LOC="../../lib"
+BIN_FILE="$BIN_LOC/$ORIG_APPNAME"
+PLUGIN_FILE="$BIN_LOC/$ORIG_APPNAME.so"
+LIB_FILE="$LIB_LOC/lib$ORIG_APPNAME.a"
+
+pushd "$PACK_DIR"
+
+mkdir -p root/usr/pluto/bin
+mkdir -p root/usr/pluto/lib
+
+echo "-- $BIN_FILE"
+if [ -f "$BIN_FILE" ]; then
+ echo "Found bin file"
+ cp "$BIN_FILE" root/usr/pluto/bin
+fi
+
+echo "-- $PLUGIN_FILE"
+if [ -f "$PLUGIN_FILE" ]; then
+ echo "Found plugin file"
+ cp "$PLUGIN_FILE" root/usr/pluto/bin
+fi
+
+echo "-- $LIB_FILE"
+if [ -f "$LIB_FILE" ]; then
+ echo "Found lib file"
+ cp "$LIB_FILE" root/usr/pluto/lib
+fi
+
+popd
+
+pushd "$PACK_LOC"
+./propagate.pl "$PACK_NAME" $PackageList
+popd
+
+#<-dceag-mp-e->
+
Only in ZWave/: make_package.sh.prep
diff -ur /code/ZWave/PlutoZWSerialAPI.cpp ZWave/PlutoZWSerialAPI.cpp
--- /code/ZWave/PlutoZWSerialAPI.cpp 2008-02-28 15:26:29.862859264 -0500
+++ ZWave/PlutoZWSerialAPI.cpp 2008-03-03 12:24:22.499785181 -0500
@@ -692,7 +692,7 @@
}
// check the timeout, idle and closed jobs
- if( d->connection->ack )
+ if( d->connection->isAcknowledged() )
{
iTry = 0;
PLUTO_SAFETY_LOCK(am, d->asynchMutex);
@@ -827,7 +827,7 @@
if( iTry > 3 )
{
// let's set it since we didn't get any ack in the last time
- d->connection->ack = true;
+ d->connection->setAcknowledged(true);
}
}
#ifdef _WIN32
Only in ZWave/: PlutoZWSerialAPI.cpp~
Only in ZWave/: PlutoZWSerialAPI.d
Only in ZWave/: PlutoZWSerialAPI.o
diff -ur /code/ZWave/SerialConnection.cpp ZWave/SerialConnection.cpp
--- /code/ZWave/SerialConnection.cpp 2008-02-28 15:26:29.718864402 -0500
+++ ZWave/SerialConnection.cpp 2008-03-03 15:13:54.811885641 -0500
@@ -12,13 +12,130 @@
// leave it bigger than 200 ms
#define SC_READ_TIMEOUT 100
+std::string toString(const char *data, int len)
+{
+ std::string out_buf;
+
+ char buf[5];
+ for (unsigned int i = 0; (int)i < len; i++)
+ {
+ sprintf(buf, "0x%02x ", (unsigned char) data[i]);
+ for (uint j = 0; j < 5; j++)
+ out_buf.push_back(buf[j]);
+ }
+
+ return out_buf;
+}
+
+int zwave_check(const char *buf, int len)
+{
+ int i;
+ char ret = (char) 0xff;
+
+ for (i = 0; buf && (i < len); i++)
+ ret ^= buf[i];
+
+ return ret & 0xff;
+}
+
+ZWaveResponse::ZWaveResponse(std::deque<char>::const_iterator begin,
+ std::deque<char>::const_iterator end)
+{
+ std::deque<char>::const_iterator it = begin;
+ for (; it != end; it++)
+ data.push_back(*it);
+}
+
+ZWaveResponse::ZWaveResponse(std::vector<char> thedata) : data(thedata)
+{
+}
+
+void ZWaveResponse::print(const char *prefice) const
+{
+ std::string out_buf_str = toString(&data[0], data.size());
+ cout << prefice << ": " << out_buf_str << endl;
+ if (hasStart())
+ {
+ cout << " data.size(): " << data.size();
+ cout << " getLength(): " << getLength();
+ cout << " getCHK(): " << getCHK();
+ cout << " calcCHK(): " << calcCHK();
+ cout << " isComplete(): " << isComplete();
+ cout << " isValid(): " << isValid();
+ cout << endl<<flush;
+ }
+}
+
+bool ZWaveResponse::isValid(void) const
+{
+ return isACK() || isNAK() || (hasStart() && (getCHK() == calcCHK()));
+}
+
+bool ZWaveResponse::isComplete(void) const
+{
+ return isACK() || isNAK() || ((size_t) (getLength() + 2)) == data.size();
+}
+
+int ZWaveResponse::getLength(void) const
+{
+ if (data.size() >= 2)
+ return (unsigned int) data[1] & 0xff;
+ return -99;
+}
+
+int ZWaveResponse::getCHK(void) const
+{
+ if (isComplete())
+ return (unsigned int) data.back() & 0xff;
+ return -1;
+}
+
+int ZWaveResponse::calcCHK(void) const
+{
+ if (isComplete())
+ return zwave_check(&data[1], data.size() - 2);
+ return -99;
+}
+
+bool ZWaveResponse::set(char *out, size_t &len) const
+{
+ if (!isValid())
+ {
+ cout<<"ZWaveResponse::set -- not valid"<<endl;
+ return false;
+ }
+
+ if (len + 2 < data.size())
+ {
+ cout<<"ZWaveResponse::set -- external buffer too small"<<endl;
+ return false;
+ }
+
+ if (data.size() <= 3)
+ {
+ cout<<"ZWaveResponse::set -- internal buffer too small"<<endl;
+ return false;
+ }
+
+ len = data.size() - 3;
+ memcpy(out, &data[2], len);
+
+ return true;
+}
+
+
SerialConnection* SerialConnection::instance = NULL;
-pthread_mutex_t SerialConnection::mutex_serial;
-pthread_mutex_t SerialConnection::mutex_buffer;
+pthread_mutex_t SerialConnection::mutex;
+//pthread_mutex_t SerialConnection::mutex_serial;
+//pthread_mutex_t SerialConnection::mutex_buffer;
pthread_t SerialConnection::write_thread;
-bool SerialConnection::ack = true;
+char SerialConnection::last_command_data[512];
+int SerialConnection::last_command_data_len = 0;
+bool SerialConnection::last_command_ack = true;
+size_t SerialConnection::last_buffer_size = 0;
+std::deque<ZWaveResponse> SerialConnection::responses;
SerialConnection::SerialConnection()
: serialPort(NULL)
@@ -50,14 +167,14 @@
{
try
{
- serialPort = new CSerialPort(port, 115200, epbsN81);
+ serialPort = new CSerialPort(port, 115200/*9600*//*38400*/, epbsN81);
#ifdef PLUTO_DEBUG
LoggerWrapper::GetInstance()->Write(LV_ZWAVE, "SerialConnection::connect init serial mutex");
#endif
- pthread_mutex_init(&mutex_serial, NULL);
- pthread_mutex_init(&mutex_buffer, NULL);
+ pthread_mutex_init(&mutex/*serial*/, NULL);
+ //pthread_mutex_init(&mutex/*buffer*/, NULL);
int stat = pthread_create(&write_thread, NULL, receiveFunction, (void*)this);
if( stat != 0)
{
@@ -111,10 +228,10 @@
#ifdef PLUTO_DEBUG
LoggerWrapper::GetInstance()->Write(LV_DEBUG, "SerialConnection ------------- asa 1");
#endif
- pthread_mutex_lock( &instance->mutex_serial );
+ pthread_mutex_lock( &instance->mutex/*serial*/ );
delete serialPort;
serialPort = NULL;
- pthread_mutex_unlock( &instance->mutex_serial );
+ pthread_mutex_unlock( &instance->mutex/*serial*/ );
#ifdef PLUTO_DEBUG
LoggerWrapper::GetInstance()->Write(LV_DEBUG, "SerialConnection ------------- asa 2");
LoggerWrapper::GetInstance()->Flush();
@@ -131,8 +248,8 @@
LoggerWrapper::GetInstance()->Flush();
#endif
- pthread_mutex_destroy(&mutex_serial);
- pthread_mutex_destroy(&mutex_buffer);
+ pthread_mutex_destroy(&mutex/*serial*/);
+ //pthread_mutex_destroy(&mutex/*buffer*/);
buffer.clear();
@@ -154,8 +271,7 @@
return serialPort != NULL;
}
-// TODO: use 'const char * buffer'
-int SerialConnection::send(char *b, size_t len)
+int SerialConnection::send_real(const char *b, size_t len, bool take_mutex)
{
if( !isConnected() )
{
@@ -170,7 +286,7 @@
#ifdef PLUTO_DEBUG
LoggerWrapper::GetInstance()->Write(LV_ZWAVE, "SerialConnection::send lock serial mutex");
#endif
- pthread_mutex_lock( &mutex_serial );
+ pthread_mutex_lock( &mutex/*serial*/ );
#ifdef PLUTO_DEBUG
printDataBuffer(b, len, "SerialConnection::send");
@@ -191,9 +307,13 @@
serialPort->Write(paddedBuffer, len);
serialPort->Flush();
- // this flag is set false, then we have to wait for this flag to be true to send another command
+ // the ack flag is set false,
+ // then we have to wait for this flag to
+ // be true to send another command
// important flag
- ack = false;
+ memcpy(last_command_data, b, len - 3);
+ last_command_data_len = len - 3;
+ last_command_ack = false;
}
catch(...)
{
@@ -202,7 +322,7 @@
}
}
else returnValue = -1;
- pthread_mutex_unlock( &mutex_serial );
+ pthread_mutex_unlock( &mutex/*serial*/ );
#ifdef PLUTO_DEBUG
LoggerWrapper::GetInstance()->Write(LV_ZWAVE, "SerialConnection::send unlock serial mutex");
#endif
@@ -215,73 +335,173 @@
int SerialConnection::receiveCommand(char *b, size_t *len)
{
#ifdef PLUTO_DEBUG
- LoggerWrapper::GetInstance()->Write(LV_DEBUG, "receiveCommand::begin");
+ LoggerWrapper::GetInstance()->Write(LV_DEBUG, "receiveCommand::begin");
#endif
- if(b == NULL || !isConnected())
- {
- *len = 0;
- return -1;
- }
-
- pthread_mutex_lock( &instance->mutex_buffer );
- if( !buffer.empty() )
- {
+ if (!b || !isConnected())
+ {
+ *len = 0;
#ifdef PLUTO_DEBUG
- LoggerWrapper::GetInstance()->Write(LV_DEBUG, "buffer.size()= %d", buffer.size());
+ LoggerWrapper::GetInstance()->Write(LV_DEBUG, "receiveCommand::end nok 1");
#endif
- //for(std::deque<char>::iterator it = buffer.begin(); it != buffer.end(); ++it)
- //{
- // LoggerWrapper::GetInstance()->Write(LV_WARNING, "HMM: 0x%02x ", (int)(*it));
- //}
-
- if( buffer.front() == SERIAL_ACK )
- buffer.pop_front();
- if( buffer.front() != SERIAL_SOF )
- {
- pthread_mutex_unlock( &instance->mutex_buffer );
- *len = 0;
- return -1;
- }
- unsigned int buffered_len = *(buffer.begin() + 1);
- if(buffer.size() < buffered_len + 2 || *len < buffered_len + 2)
- {
- pthread_mutex_unlock( &instance->mutex_buffer );
- *len = 0;
- return -1;
- }
-
- // SOF
- buffer.pop_front();
- // LEN
- buffer.pop_front();
-
- unsigned int i = 0;
- *len = buffered_len - 1;
- while(i < *len)
- {
-#ifdef PLUTO_DEBUG
- if( i == 0 )
- LoggerWrapper::GetInstance()->Write(LV_DEBUG, "receiveCommand: eat another command");
-#endif
- b[i++] = buffer.front();
- buffer.pop_front();
- }
-
- // CHECKSUM
- buffer.pop_front();
-
-#ifdef PLUTO_DEBUG
- printDataBuffer(b, *len, "SerialConnection : received command");
-#endif
- }
- else
- {
- *len = 0;
- }
+ return -1;
+ }
- pthread_mutex_unlock( &instance->mutex_buffer );
- return 0;
+ pthread_mutex_lock( &instance->mutex/*buffer*/ );
+ if (responses.empty())
+ {
+ pthread_mutex_unlock( &instance->mutex/*buffer*/ );
+ *len = 0;
+#ifdef PLUTO_DEBUG
+ LoggerWrapper::GetInstance()->Write(LV_DEBUG, "receiveCommand::end nok 2");
+#endif
+ return -1;
+ }
+
+ if (!responses.front().set(b, *len))
+ {
+ responses.pop_front();
+ pthread_mutex_unlock( &instance->mutex/*buffer*/ );
+ *len = 0;
+#ifdef PLUTO_DEBUG
+ LoggerWrapper::GetInstance()->Write(LV_DEBUG, "receiveCommand::end nok 3");
+#endif
+ return -1;
+ }
+
+ responses.pop_front();
+ pthread_mutex_unlock( &instance->mutex/*buffer*/ );
+
+#ifdef PLUTO_DEBUG
+ LoggerWrapper::GetInstance()->Write(LV_DEBUG, "receiveCommand::end ok");
+#endif
+
+ return 0;
+}
+
+std::vector<ZWaveResponse> getResponses(std::deque<char> &buffer)
+{
+ cout<<endl<<endl<<"getResponses() -- begin"<<endl;
+
+ std::vector<int> starts;
+ std::vector<int> len;
+ std::vector<bool> valid;
+ for (size_t i = 0; i < buffer.size(); i++)
+ {
+ if (SERIAL_SOF == buffer[i])
+ {
+ starts.push_back(i);
+ if (i + 1 < buffer.size())
+ {
+ len.push_back((unsigned int)(buffer[i+1]&0xff));
+ if (i + len.back() + 2 > buffer.size())
+ {
+ cout<<"SOF @"<<i<<" len("<<len.back()
+ <<") too long.."<<endl;
+ valid.push_back(false);
+ }
+ else
+ {
+ vector<char> data;
+ for (int j = i; j < (int)i + len.back() + 2; j++)
+ data.push_back(buffer[j]);
+ ZWaveResponse tmp(data);
+ valid.push_back(tmp.isValid());
+
+ cout<<"SOF @"<<i<<endl;
+ tmp.print("");
+ }
+ }
+ else
+ {
+ cout<<"SOF @"<<i<<" too short for len"<<endl;
+ len.push_back(-1);
+ valid.push_back(false);
+ }
+ }
+ else if (SERIAL_ACK == buffer[i])
+ {
+ cout<<"ACK @"<<i<<endl;
+ starts.push_back(i);
+ len.push_back(0);
+ valid.push_back(true);
+ }
+ else if (SERIAL_NAK == buffer[i])
+ {
+ cout<<"NAK @"<<i<<endl;
+ starts.push_back(i);
+ len.push_back(0);
+ valid.push_back(true);
+ }
+ }
+
+ std::vector<ZWaveResponse> responses;
+ vector<char> data;
+ size_t last_data = 0;
+ for (unsigned int i = 0; i < starts.size(); i++)
+ {
+ if (!valid[i])
+ continue;
+
+ cout<<"Found valid @"<<starts[i]<<endl;
+
+ // start contains a complete valid response..
+ data.clear();
+
+ // add any previous cruft as an [invalid] response
+ for (int j = last_data; j < starts[i]; j++)
+ data.push_back(buffer[j]);
+ if (data.size())
+ {
+ responses.push_back(ZWaveResponse(data));
+ responses.back().print("Added invalid");
+ }
+
+ // add valid response to responses to list
+ if (len[i] == 0)
+ {
+ last_data = starts[i] + 1;
+ data.push_back(buffer[starts[i]]);
+ responses.push_back(ZWaveResponse(data));
+ responses.back().print("Added valid 1");
+ }
+ else
+ {
+ last_data = starts[i] + len[i] + 2;
+ for (int j = starts[i]; j < starts[i] + len[i] + 2; j++)
+ data.push_back(buffer[j]);
+ responses.push_back(ZWaveResponse(data));
+ responses.back().print("Added valid 2");
+ }
+
+ // invalidate all other responses that start before we end.
+ for (size_t j = i; j < starts.size(); j++)
+ {
+ if (starts[j] < (int) last_data)
+ {
+ cout<<"invalidating #"<<j<<endl;
+ valid[j] = false;
+ }
+ }
+ }
+
+ // pop off all buffer data up until end of last complete valid response
+ if (responses.size() && responses.back().isValid())
+ {
+ for (unsigned int i = 0; i < last_data; i++)
+ buffer.pop_front();
+ }
+
+ // add any remaining cruft as response on the list
+ if (buffer.size())
+ responses.push_back(ZWaveResponse(buffer.begin(), buffer.end()));
+
+ for (uint i = 0; i < responses.size(); i++)
+ responses[i].print("Actual added response");
+
+ cout<<"getResponses() -- end"<<endl;
+
+ return responses;
}
/**
@@ -290,83 +510,106 @@
*/
int SerialConnection::hasCommand()
{
- if( !isConnected() )
- {
- LoggerWrapper::GetInstance()->Write(LV_ZWAVE, "SerialConnection::hasCommand() is not connected");
- return -1;
- }
-
- int returnValue = 0;
- pthread_mutex_lock( &instance->mutex_buffer );
- while( 0 < buffer.size() && buffer.front() == SERIAL_ACK )
- {
-#ifdef PLUTO_DEBUG
- LoggerWrapper::GetInstance()->Write(LV_DEBUG, "SerialConnection::hasCommand() popping ACK");
-#endif
- // we got a new ACK, we can send another command
- // it's an important flag
- ack = true;
-
- buffer.pop_front();
- }
-
- size_t bufferSize = buffer.size();
- if(bufferSize < 3)
- {
-#ifdef PLUTO_DEBUG
- if( 0 < bufferSize )
- LoggerWrapper::GetInstance()->Write(LV_DEBUG, "size too small %d", buffer.size());
-#endif
- pthread_mutex_unlock( &instance->mutex_buffer );
- return 0;
- }
-
- if( buffer.front() == SERIAL_SOF )
- {
-#ifdef PLUTO_DEBUG
- LoggerWrapper::GetInstance()->Write(LV_DEBUG, "SerialConnection::hasCommand() front is SOF");
-#endif
- std::deque<char>::iterator i = buffer.begin();
- unsigned int len = *(++i) ;
- if(bufferSize >= len + 2) //SOF+LEN+CHECK
- {
- i += len;
- char checkSum = *i;
- char tmpSum = (char)0xff;
- // checksum( Length_Byte + Command_Array_Bytes )
- std::deque<char>::iterator endPack = buffer.begin() + len + 1;
- for(i = buffer.begin() + 1; i != endPack; i++)
- tmpSum ^= *i;
- if(tmpSum == checkSum)
- {
- returnValue = 1;
- char ack = SERIAL_ACK;
-#ifdef PLUTO_DEBUG
- LoggerWrapper::GetInstance()->Write(LV_DEBUG, "SerialConnection::hasCommand lock serial mutex");
-#endif
- pthread_mutex_lock( &mutex_serial );
+ if( !isConnected() )
+ {
+ LoggerWrapper::GetInstance()->Write(
+ LV_ZWAVE, "SerialConnection::hasCommand() is not connected");
+ return -1;
+ }
+
+ pthread_mutex_lock( &instance->mutex/*buffer&serial*/ );
+ bool has_data = buffer.size();
+ if (!has_data)
+ {
+ pthread_mutex_unlock( &instance->mutex/*buffer&serial*/ );
+ return -1;
+ }
+
+ if (buffer.size() == last_buffer_size)
+ {
+ pthread_mutex_unlock( &instance->mutex/*buffer&serial*/ );
+ return -1;
+ }
+
+ // debugging
+ if (buffer.size())
+ {
+ cout<<"SerialConnection::hasCommand():";
+ for (unsigned int i = 0; i < buffer.size(); i++)
+ {
+ if (buffer[i] == SERIAL_ACK)
+ cout<<" ACK";
+ else if (buffer[i] == SERIAL_SOF && (i>0) &&
+ buffer[i-1] == SERIAL_ACK)
+ cout<<" SOF";
+ else
+ cout<<hex<<" x"<<((int)buffer[i]&0xff)<<dec;
+ }
+ cout<<endl<<flush;
+ }
+
+ std::vector<ZWaveResponse> resp = getResponses(buffer);
+
+ for (unsigned int i = 0; i < resp.size(); i++)
+ {
+ if (!resp[i].isComplete())
+ {
+ resp[i].print("Incomplete Response");
+ continue;
+ }
+
+ if (!resp[i].isValid())
+ {
+ resp[i].print("Invalid Response");
+ continue;
+ }
+
+ if (resp[i].isACK())
+ {
+ std::string tmp =
+ toString(last_command_data, last_command_data_len);
+ char log_buf[1024*10];
+ sprintf(log_buf, "Got ACK for %s", tmp.c_str());
+ resp[i].print(log_buf);
+ // we got a new ACK, we can send another command
+ // it's an important flag
+ last_command_ack = true;
+ continue;
+ }
+
+ if (resp[i].isNAK())
+ {
+ std::string tmp =
+ toString(last_command_data, last_command_data_len);
+ char log_buf[1024*10];
+ sprintf(log_buf, "Got NAK for %s", tmp.c_str());
+ resp[i].print(log_buf);
+
+ // resend last command
+ send_real(last_command_data, last_command_data_len, false);
+
+ continue;
+ }
+
+ // queue up response for receiveCommand
+ responses.push_back(resp[i]);
+
+ // acknowledge response
+ if (serialPort)
+ {
+ char ack = SERIAL_ACK;
+ serialPort->Write(&ack, 1);
+ serialPort->Flush();
+ }
+ }
- if( serialPort != NULL )
- {
- serialPort->Write(&ack, 1);
-#ifdef PLUTO_DEBUG
- LoggerWrapper::GetInstance()->Write(LV_DEBUG, "SerialConnection::hasCommand wrote ack");
-#endif
- }
- pthread_mutex_unlock( &mutex_serial );
-#ifdef PLUTO_DEBUG
- LoggerWrapper::GetInstance()->Write(LV_DEBUG, "SerialConnection::hasCommand unlock serial mutex");
-#endif
- }
- }
- else
- {
- }
- }
- else
- returnValue = -1;
- pthread_mutex_unlock( &instance->mutex_buffer );
- return returnValue;
+ int ret = responses.size() ? 1 : -1;
+
+ last_buffer_size = !responses.size() ? buffer.size() : 0;
+
+ pthread_mutex_unlock( &instance->mutex/*buffer&serial*/ );
+
+ return ret;
}
@@ -401,7 +644,7 @@
while( true )
{
len = sizeof(mybuf) + 1;
- pthread_mutex_lock( &instance->mutex_serial );
+ pthread_mutex_lock( &instance->mutex/*serial*/ );
if( instance != NULL && instance->isConnected() )
{
uRead++;
@@ -412,7 +655,7 @@
// THREAD MUST STOP
bDisconnect = true;
}
- pthread_mutex_unlock( &instance->mutex_serial );
+ pthread_mutex_unlock( &instance->mutex/*serial*/ );
// THREAD MUST STOP
if( bDisconnect )
@@ -422,13 +665,13 @@
if(len <= sizeof(mybuf) && len != 0 && instance != NULL)
{
- pthread_mutex_lock( &instance->mutex_buffer );
+ pthread_mutex_lock( &instance->mutex/*buffer*/ );
for(size_t i=0; i<len; i++)
{
instance->buffer.push_back(mybuf[i]);
}
//SerialConnection::printDataBuffer(mybuf, len, "Thread Read");
- pthread_mutex_unlock( &instance->mutex_buffer );
+ pthread_mutex_unlock( &instance->mutex/*buffer*/ );
}
#ifdef _WIN32
@@ -475,7 +718,7 @@
void SerialConnection::clearSerialBuffer()
{
- pthread_mutex_lock( &instance->mutex_buffer );
+ pthread_mutex_lock( &instance->mutex/*buffer*/ );
buffer.clear();
- pthread_mutex_unlock( &instance->mutex_buffer );
+ pthread_mutex_unlock( &instance->mutex/*buffer*/ );
}
Only in ZWave/: SerialConnection.cpp~
Only in ZWave/: SerialConnection.d
diff -ur /code/ZWave/SerialConnection.h ZWave/SerialConnection.h
--- /code/ZWave/SerialConnection.h 2008-02-28 15:26:29.494872609 -0500
+++ ZWave/SerialConnection.h 2008-03-03 15:13:32.240918140 -0500
@@ -17,8 +17,34 @@
#include <pthread.h>
#define SERIAL_ACK 0x06
+#define SERIAL_NAK 0x18
#define SERIAL_SOF 0x01
+class ZWaveResponse
+{
+ public:
+ ZWaveResponse(std::deque<char>::const_iterator begin,
+ std::deque<char>::const_iterator end);
+ ZWaveResponse(std::vector<char> thedata);
+
+ void print(const char *prefice) const;
+ bool empty(void) const { return data.empty(); }
+ bool isACK(void) const { return data.size() && (SERIAL_ACK == data[0]); }
+ bool isNAK(void) const { return data.size() && (SERIAL_NAK == data[0]); }
+ bool hasStart(void) const { return data.size() && (SERIAL_SOF == data[0]); }
+ bool isValid(void) const;
+ bool isComplete(void) const;
+
+ int getLength(void) const;
+ int getCHK(void) const;
+ int calcCHK(void) const;
+
+ bool set(char *out, size_t &len) const;
+
+ private:
+ std::vector<char> data;
+};
+
/**
* Singleton class that takes care of the serial connection interface.
*Send is single thread, receive is multi thread.
@@ -37,7 +63,11 @@
*@param buffer the buffer to be sent
*@param len the length of the buffer
*@return 0 if OK, else negative */
- virtual int send(char *buffer, size_t len);
+ virtual int send(char *buffer, size_t len)
+ { return send_real(buffer, len, true); }
+ virtual int send(const char *buffer, size_t len)
+ { return send_real(buffer, len, true); }
+ virtual int send_real(const char *buffer, size_t len, bool take_mutex);
/**try to get the specified len from the serial buffer
* @parameter buffer the buffer where the data should be found
@@ -75,12 +105,22 @@
static void printDataBuffer(const char *buffer, const size_t length, const char *classID);
- static pthread_mutex_t mutex_serial;
- static pthread_mutex_t mutex_buffer;
+ static pthread_mutex_t mutex;
+ //static pthread_mutex_t mutex_serial;
+ //static pthread_mutex_t mutex_buffer;
static pthread_t write_thread;
- static bool ack;
-
+ // these are protected by mutex_serial
+ static char last_command_data[512];
+ static int last_command_data_len;
+ static bool last_command_ack;
+ static size_t last_buffer_size;
+ static std::deque<ZWaveResponse> responses;
+
+ bool isAcknowledged(const char *command = NULL) { return last_command_ack; }
+ bool setAcknowledged(bool val = true, const char *command = NULL)
+ { return last_command_ack = val; }
+
private:
/**static instance of this class*/
static SerialConnection* instance;
Only in ZWave/: SerialConnection.h~
Only in ZWave/: SerialConnection.o
Only in /code/ZWave/: .svn
Only in ZWave/: tester
Only in ZWave/: tester.c
Only in ZWave/: tester.c~
Only in ZWave/: x
Only in ZWave/: ZWave
Only in ZWave/: ZWave.d
Only in ZWave/: ZWaveJob.d
Only in ZWave/: ZWaveJob.o
Only in ZWave/: ZWaveNode.d
Only in ZWave/: ZWaveNode.o
Only in ZWave/: ZWave.o
Only in ZWave/: ZWave.so
Only in ZWave/: ZWJobAddNode.d
Only in ZWave/: ZWJobAddNode.o
Only in ZWave/: ZWJobAssignReturnRoute.d
Only in ZWave/: ZWJobAssignReturnRoute.o
Only in ZWave/: ZWJobAssociationSet.d
Only in ZWave/: ZWJobAssociationSet.o
Only in ZWave/: ZWJobConfig.d
Only in ZWave/: ZWJobConfig.o
Only in ZWave/: ZWJobDeleteRoute.d
Only in ZWave/: ZWJobDeleteRoute.o
Only in ZWave/: ZWJobGetID.d
Only in ZWave/: ZWJobGetID.o
Only in ZWave/: ZWJobGetInitData.d
Only in ZWave/: ZWJobGetInitData.o
Only in ZWave/: ZWJobGetNodeProtocolInfo.d
Only in ZWave/: ZWJobGetNodeProtocolInfo.o
Only in ZWave/: ZWJobGetSUC.d
Only in ZWave/: ZWJobGetSUC.o
Only in ZWave/: ZWJobGetVersion.d
Only in ZWave/: ZWJobGetVersion.o
Only in ZWave/: ZWJobInitialize.d
Only in ZWave/: ZWJobInitialize.o
Only in ZWave/: ZWJobLightLevel.d
Only in ZWave/: ZWJobLightLevel.o
Only in ZWave/: ZWJobPool.d
Only in ZWave/: ZWJobPool.o
Only in ZWave/: ZWJobReceive.d
Only in ZWave/: ZWJobReceive.o
Only in ZWave/: ZWJobRemoveNode.d
Only in ZWave/: ZWJobRemoveNode.o
Only in ZWave/: ZWJobReset.d
Only in ZWave/: ZWJobReset.o
Only in ZWave/: ZWJobSendData.d
Only in ZWave/: ZWJobSendData.o
Only in ZWave/: ZWJobSetLearnMode.d
Only in ZWave/: ZWJobSetLearnMode.o
Only in ZWave/: ZWJobSetLearnNodeState.d
Only in ZWave/: ZWJobSetLearnNodeState.o
Only in ZWave/: ZWJobSwitchBinaryGet.d
Only in ZWave/: ZWJobSwitchBinaryGet.o
Only in ZWave/: ZWJobSwitchChangeLevel.d
Only in ZWave/: ZWJobSwitchChangeLevel.d.9839
Only in ZWave/: ZWJobSwitchChangeLevel.o
Only in ZWave/: ZWJobWakeUp.d
Only in ZWave/: ZWJobWakeUp.o