From 8d37dc453e0ca773e31c9984a5f20cf2a6e38f72 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9F=D0=B5=D0=BB=D0=B8=D0=BF=D0=B5=D0=BD=D0=BA=D0=BE=20?= =?UTF-8?q?=D0=98=D0=B2=D0=B0=D0=BD?= Date: Tue, 18 Dec 2018 19:13:09 +0000 Subject: [PATCH] git-svn-id: svn://db.shs.com.ru/pip@673 12ceb7fc-bf1f-11e4-8940-5bc7170c53b5 --- main.cpp | 8 +++- src_main/core/pivariant.h | 1 + src_main/core/pivarianttypes.cpp | 32 +++++++++++++++ src_main/core/pivarianttypes.h | 19 ++++++--- src_main/io_devices/piiodevice.cpp | 66 +++++++++++++++++++++++++----- src_main/io_devices/piiodevice.h | 29 +++++++++---- src_main/io_devices/piserial.cpp | 23 +++++++++++ src_main/io_devices/piserial.h | 2 + src_main/piversion.h | 6 +-- 9 files changed, 157 insertions(+), 29 deletions(-) diff --git a/main.cpp b/main.cpp index a64ae67d..b1cf781e 100644 --- a/main.cpp +++ b/main.cpp @@ -2,12 +2,16 @@ int main() { - PIByteArray msg = PIByteArray::fromHex("0110f0f00001020001"); + /*PIByteArray msg = PIByteArray::fromHex("0110f0f00001020001"); PIByteArray src = PIByteArray::fromHex("836f"); ushort s; memcpy(&s, src.data(), 2); //CRC_16 crc = standardCRC_16(); CRC_16 crc = CRC_16(0x8005, 0xFFFF, 0xFFFF, false); piCout << PICoutManipulators::Hex << s; - piCout << PICoutManipulators::Hex << crc.calculate(msg); + piCout << PICoutManipulators::Hex << crc.calculate(msg);*/ + PIIODevice * ser = PIIODevice::createFromFullPath("ser://COM3:9600:9:o:2 (wo,bwr)"); + piCout << ser << ser->constructVariant() << ser->constructFullPath(); + ser = PIIODevice::createFromVariant(ser->constructVariant()); + piCout << ser << ser->constructVariant() << ser->constructFullPath(); return 0; } diff --git a/src_main/core/pivariant.h b/src_main/core/pivariant.h index 636d5f5c..67a2b744 100755 --- a/src_main/core/pivariant.h +++ b/src_main/core/pivariant.h @@ -741,6 +741,7 @@ REGISTER_NS_VARIANT(PIVariantTypes, Enum) REGISTER_NS_VARIANT(PIVariantTypes, File) REGISTER_NS_VARIANT(PIVariantTypes, Dir) REGISTER_NS_VARIANT(PIVariantTypes, Color) +REGISTER_NS_VARIANT(PIVariantTypes, IODevice) REGISTER_VARIANT(PIPointd) REGISTER_VARIANT(PIRectd) diff --git a/src_main/core/pivarianttypes.cpp b/src_main/core/pivarianttypes.cpp index bfdbcc98..823004f6 100644 --- a/src_main/core/pivarianttypes.cpp +++ b/src_main/core/pivarianttypes.cpp @@ -19,6 +19,7 @@ #include "pivarianttypes.h" #include "pipropertystorage.h" +#include "piiodevice.h" int PIVariantTypes::Enum::selectedValue() const { @@ -83,6 +84,12 @@ PIStringList PIVariantTypes::Enum::names() const { +PIVariantTypes::IODevice::IODevice() { + mode = PIIODevice::ReadWrite; + options = 0; +} + + void PIVariantTypes::IODevice::set(const PIPropertyStorage & ps) { props.clear(); props << ps; @@ -116,3 +123,28 @@ PIVariantTypes::Enum & PIVariantTypes::Enum::operator <<(const PIStringList & v) (*this) << s.trimmed(); return *this; } + + + + +PICout operator <<(PICout s, const PIVariantTypes::IODevice & v) { + s.setControl(0, true); + s << "IODevice(" << v.prefix << ", "; + int rwc = 0; + if (v.mode & 1) {s << "r"; ++rwc;} + if (v.mode & 2) {s << "w"; ++rwc;} + if (rwc == 1) s << "o"; + if (v.options != 0) { + if (((PIIODevice::DeviceOptions)v.options)[PIIODevice::BlockingRead]) + s << " br"; + if (((PIIODevice::DeviceOptions)v.options)[PIIODevice::BlockingWrite]) + s << " bw"; + } + PIPropertyStorage ps = v.get(); + piForeachC (PIPropertyStorage::Property & p, ps) { + s << ", " << p.name << "=\"" << p.value.toString() << "\""; + } + s << ")"; + s.restoreControl(); + return s; +} diff --git a/src_main/core/pivarianttypes.h b/src_main/core/pivarianttypes.h index db2d2af4..50294a0d 100644 --- a/src_main/core/pivarianttypes.h +++ b/src_main/core/pivarianttypes.h @@ -78,33 +78,40 @@ namespace PIVariantTypes { }; struct PIP_EXPORT IODevice { - IODevice() {} + IODevice(); void set(const PIPropertyStorage & ps); PIPropertyStorage get() const; + PIString prefix; + int mode; // PIIODevice::DeviceMode + int options; // PIIODevice::DeviceOptions PIByteArray props; }; } inline PIByteArray & operator <<(PIByteArray & s, const PIVariantTypes::Enumerator & v) {s << v.value << v.name; return s;} -inline PIByteArray & operator >>(PIByteArray & s, PIVariantTypes::Enumerator & v) {s >> v.value >> v.name; return s;} +inline PIByteArray & operator >>(PIByteArray & s, PIVariantTypes::Enumerator & v) {s >> v.value >> v.name; return s;} inline PICout operator <<(PICout s, const PIVariantTypes::Enumerator & v) {s << v.name << "(" << v.value << ")"; return s;} inline PIByteArray & operator <<(PIByteArray & s, const PIVariantTypes::Enum & v) {s << v.enum_name << v.selected << v.enum_list; return s;} -inline PIByteArray & operator >>(PIByteArray & s, PIVariantTypes::Enum & v) {s >> v.enum_name >> v.selected >> v.enum_list; return s;} +inline PIByteArray & operator >>(PIByteArray & s, PIVariantTypes::Enum & v) {s >> v.enum_name >> v.selected >> v.enum_list; return s;} inline PICout operator <<(PICout s, const PIVariantTypes::Enum & v) {s << "Enum(" << v.selectedValue() << "=" << v.selectedName() << ")"; return s;} inline PIByteArray & operator <<(PIByteArray & s, const PIVariantTypes::File & v) {s << v.file << v.filter << v.is_abs; return s;} -inline PIByteArray & operator >>(PIByteArray & s, PIVariantTypes::File & v) {s >> v.file >> v.filter >> v.is_abs; return s;} +inline PIByteArray & operator >>(PIByteArray & s, PIVariantTypes::File & v) {s >> v.file >> v.filter >> v.is_abs; return s;} inline PICout operator <<(PICout s, const PIVariantTypes::File & v) {s << "File(\"" << v.file << "\")"; return s;} inline PIByteArray & operator <<(PIByteArray & s, const PIVariantTypes::Dir & v) {s << v.dir << v.is_abs; return s;} -inline PIByteArray & operator >>(PIByteArray & s, PIVariantTypes::Dir & v) {s >> v.dir >> v.is_abs; return s;} +inline PIByteArray & operator >>(PIByteArray & s, PIVariantTypes::Dir & v) {s >> v.dir >> v.is_abs; return s;} inline PICout operator <<(PICout s, const PIVariantTypes::Dir & v) {s << "Dir(\"" << v.dir << "\")"; return s;} inline PIByteArray & operator <<(PIByteArray & s, const PIVariantTypes::Color & v) {s << v.rgba; return s;} -inline PIByteArray & operator >>(PIByteArray & s, PIVariantTypes::Color & v) {s >> v.rgba; return s;} +inline PIByteArray & operator >>(PIByteArray & s, PIVariantTypes::Color & v) {s >> v.rgba; return s;} inline PICout operator <<(PICout s, const PIVariantTypes::Color & v) {s.saveControl(); s << PICoutManipulators::Hex << "Color(#" << v.rgba << ")"; s.restoreControl(); return s;} +inline PIByteArray & operator <<(PIByteArray & s, const PIVariantTypes::IODevice & v) {s << v.prefix << v.mode << v.options << v.props; return s;} +inline PIByteArray & operator >>(PIByteArray & s, PIVariantTypes::IODevice & v) {s >> v.prefix >> v.mode >> v.options >> v.props; return s;} + PICout operator <<(PICout s, const PIVariantTypes::IODevice & v); + #endif // PIVARIANTYPES_H diff --git a/src_main/io_devices/piiodevice.cpp b/src_main/io_devices/piiodevice.cpp index e90da9a1..646f40e4 100755 --- a/src_main/io_devices/piiodevice.cpp +++ b/src_main/io_devices/piiodevice.cpp @@ -20,6 +20,7 @@ #include "piiodevice.h" #include "piconfig.h" #include "piconnection.h" +#include "pipropertystorage.h" /*! \class PIIODevice @@ -199,6 +200,18 @@ void PIIODevice::write_func() { } +PIIODevice * PIIODevice::newDeviceByPrefix(const PIString & prefix) { + if (prefix.isEmpty()) return 0; + PIVector rd(PICollection::groupElements("__PIIODevices__")); + piForeachC (PIObject * d, rd) { + if (prefix == ((const PIIODevice * )d)->fullPathPrefix()) { + return ((const PIIODevice * )d)->copy(); + } + } + return 0; +} + + void PIIODevice::terminate() { timer.stop(); thread_started_ = false; @@ -321,6 +334,23 @@ void PIIODevice::configureFromFullPath(const PIString & full_path) { } +PIVariantTypes::IODevice PIIODevice::constructVariant() const { + PIVariantTypes::IODevice ret; + ret.prefix = fullPathPrefix(); + ret.mode = mode(); + ret.options = options(); + ret.set(constructVariantDevice()); + return ret; +} + + +void PIIODevice::configureFromVariant(const PIVariantTypes::IODevice & d) { + setMode((DeviceMode)d.mode); + setOptions((DeviceOptions)d.options); + configureFromVariantDevice(d.get()); +} + + void PIIODevice::splitFullPath(PIString fpwm, PIString * full_path, DeviceMode * mode, DeviceOptions * opts) { int dm = 0; DeviceOptions op = 0; @@ -363,17 +393,19 @@ PIString PIIODevice::fullPathOptions() const { PIIODevice * PIIODevice::createFromFullPath(const PIString & full_path) { PIString prefix = full_path.left(full_path.find(":")); - if (prefix.isEmpty()) return 0; - PIVector rd(PICollection::groupElements("__PIIODevices__")); - piForeachC (PIObject * d, rd) { - if (prefix == ((const PIIODevice * )d)->fullPathPrefix()) { - PIIODevice * nd = ((const PIIODevice * )d)->copy(); - if (nd) nd->configureFromFullPath(full_path.mid(prefix.length() + 3)); - cacheFullPath(full_path, nd); - return nd; - } - } - return 0; + PIIODevice * nd = newDeviceByPrefix(prefix); + if (!nd) return 0; + nd->configureFromFullPath(full_path.mid(prefix.length() + 3)); + cacheFullPath(full_path, nd); + return nd; +} + + +PIIODevice * PIIODevice::createFromVariant(const PIVariantTypes::IODevice & d) { + PIIODevice * nd = newDeviceByPrefix(d.prefix); + if (!nd) return 0; + nd->configureFromVariant(d); + return nd; } @@ -405,3 +437,15 @@ bool PIIODevice::threadedRead(uchar *readed, int size) { if (ret_func_ != 0) return ret_func_(ret_data_, readed, size); return true; } + + +PIPropertyStorage PIIODevice::constructVariantDevice() const { + PIPropertyStorage ret; + ret.addProperty("path", path()); + return ret; +} + + +void PIIODevice::configureFromVariantDevice(const PIPropertyStorage & d) { + setPath(d.propertyValueByName("path").toString()); +} diff --git a/src_main/io_devices/piiodevice.h b/src_main/io_devices/piiodevice.h index ae842022..b152feb5 100755 --- a/src_main/io_devices/piiodevice.h +++ b/src_main/io_devices/piiodevice.h @@ -32,6 +32,7 @@ // function executed from threaded read, pass ThreadedReadData, readedData, sizeOfData typedef bool (*ReadRetFunc)(void * , uchar * , int ); + #ifdef DOXYGEN //! \relatesalso PIIODevice \brief Use this macro to enable automatic creation instances of your class with \a createFromFullPath() function @@ -229,16 +230,27 @@ public: //! Reimplement to construct full unambiguous string prefix. \ref PIIODevice_sec7 virtual PIString fullPathPrefix() const {return PIString();} - //! Reimplement to construct full unambiguous string, describes this device, default returns \a fullPathPrefix() + "://" + \a path() + //! Returns full unambiguous string, describes this device, \a fullPathPrefix() + "://" PIString constructFullPath() const; - //! Reimplement to configure your device with parameters of full unambiguous string. Default implementation does nothing + //! Configure device with parameters of full unambiguous string void configureFromFullPath(const PIString & full_path); + //! Returns PIVariantTypes::IODevice, describes this device + PIVariantTypes::IODevice constructVariant() const; + + //! Configure device from PIVariantTypes::IODevice + void configureFromVariant(const PIVariantTypes::IODevice & d); + //! \brief Try to determine suitable device, create new one, configure it with \a configureFromFullPath() and returns it. //! \details To function \a configureFromFullPath() "full_path" passed without \a fullPathPrefix() + "://". //! See \ref PIIODevice_sec7 static PIIODevice * createFromFullPath(const PIString & full_path); + + //! \brief Try to determine suitable device, create new one, configure it with \a configureFromVariant() and returns it. + //! \details To function \a configureFromFullPath() "full_path" passed without \a fullPathPrefix() + "://". + //! See \ref PIIODevice_sec7 + static PIIODevice * createFromVariant(const PIVariantTypes::IODevice & d); static PIString normalizeFullPath(const PIString & full_path); @@ -347,11 +359,13 @@ protected: //! Reimplement to configure your device with parameters of full unambiguous string. Default implementation does nothing virtual void configureFromFullPathDevice(const PIString & full_path) {setPath(full_path);} - //! Reimplement to construct full unambiguous string, describes this device. Default implementation returns \a path() - virtual PIVariantTypes::IODevice constructPropertyStorage() const {return PIVariantTypes::IODevice();} + //! Reimplement to construct device properties. + //! Default implementation return PIPropertyStorage with \"path\" entry + virtual PIPropertyStorage constructVariantDevice() const; - //! Reimplement to configure your device with parameters of full unambiguous string. Default implementation does nothing - virtual void configureFromPropertyStorage(const PIVariantTypes::IODevice & d) {} + //! Reimplement to configure your device from PIPropertyStorage. Options and mode already applied. + //! Default implementation apply \"path\" entry + virtual void configureFromVariantDevice(const PIPropertyStorage & d); //! Reimplement to apply new device options virtual void optionsChanged() {;} @@ -362,7 +376,8 @@ protected: //! Reimplement to apply new \a threadedReadBufferSize() virtual void threadedReadBufferSizeChanged() {;} - + static PIIODevice * newDeviceByPrefix(const PIString & prefix); + void terminate(); diff --git a/src_main/io_devices/piserial.cpp b/src_main/io_devices/piserial.cpp index 46c947da..76e316c5 100755 --- a/src_main/io_devices/piserial.cpp +++ b/src_main/io_devices/piserial.cpp @@ -20,6 +20,7 @@ #include "piserial.h" #include "piconfig.h" #include "pidir.h" +#include "pipropertystorage.h" #include #ifdef WINDOWS # include @@ -716,6 +717,28 @@ void PISerial::configureFromFullPathDevice(const PIString & full_path) { } +PIPropertyStorage PISerial::constructVariantDevice() const { + PIPropertyStorage ret; + ret.addProperty("path", path()); + ret.addProperty("speed", (int)inSpeed()); + ret.addProperty("bits", dataBitsCount()); + ret.addProperty("parity", parameters()[ParityControl]); + ret.addProperty("parityEven", !parameters()[ParityOdd]); + ret.addProperty("twoStopBits", parameters()[TwoStopBits]); + return ret; +} + + +void PISerial::configureFromVariantDevice(const PIPropertyStorage & d) { + setPath(d.propertyValueByName("path").toString()); + setSpeed((Speed)d.propertyValueByName("speed").toInt()); + setDataBitsCount(d.propertyValueByName("bits").toInt()); + setParameter(ParityControl, d.propertyValueByName("parity").toBool()); + setParameter(ParityOdd , !d.propertyValueByName("parityEven").toBool()); + setParameter(TwoStopBits , d.propertyValueByName("twoStopBits").toBool()); +} + + PIVector PISerial::availableSpeeds() { PIVector spds; spds << 50 << 75 << 110 << 300 << 600 << 1200 << 2400 << 4800 << diff --git a/src_main/io_devices/piserial.h b/src_main/io_devices/piserial.h index a2b291d2..d49bde05 100755 --- a/src_main/io_devices/piserial.h +++ b/src_main/io_devices/piserial.h @@ -203,6 +203,8 @@ protected: PIString fullPathPrefix() const {return PIStringAscii("ser");} PIString constructFullPathDevice() const; void configureFromFullPathDevice(const PIString & full_path); + PIPropertyStorage constructVariantDevice() const; + void configureFromVariantDevice(const PIPropertyStorage & d); bool configureDevice(const void * e_main, const void * e_parent = 0); void optionsChanged(); void threadedReadBufferSizeChanged(); diff --git a/src_main/piversion.h b/src_main/piversion.h index 5fd2e2e0..8d44bc39 100644 --- a/src_main/piversion.h +++ b/src_main/piversion.h @@ -3,8 +3,8 @@ #define PIVERSION_H #define PIP_VERSION_MAJOR 1 -#define PIP_VERSION_MINOR 8 -#define PIP_VERSION_REVISION 1 -#define PIP_VERSION_SUFFIX "" +#define PIP_VERSION_MINOR 9 +#define PIP_VERSION_REVISION 0 +#define PIP_VERSION_SUFFIX "_alpha" #endif // PIVERSION_H