From 28ce6e8f3f9a5d7197daeeb441a7e01a1623fd72 Mon Sep 17 00:00:00 2001 From: peri4 Date: Tue, 3 May 2022 18:44:00 +0300 Subject: [PATCH] version 2.39.0 PIString works with PIConstChars picodeinfo optimizations PIIODevice::availableClasses --- CMakeLists.txt | 2 +- libs/main/code/picodeinfo.cpp | 18 +++++----- libs/main/code/picodeinfo.h | 53 +++++++++++++++-------------- libs/main/core/pistring.cpp | 18 ++++++++-- libs/main/core/pistring.h | 18 ++++++++++ libs/main/io_devices/pifile.cpp | 2 +- libs/main/io_devices/piiodevice.cpp | 33 ++++++++++++------ libs/main/io_devices/piiodevice.h | 15 ++++++-- utils/code_model_generator/main.cpp | 2 +- 9 files changed, 106 insertions(+), 55 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 90b2ed34..1944b766 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -2,7 +2,7 @@ cmake_minimum_required(VERSION 3.0) cmake_policy(SET CMP0017 NEW) # need include() with .cmake project(pip) set(pip_MAJOR 2) -set(pip_MINOR 38) +set(pip_MINOR 39) set(pip_REVISION 0) set(pip_SUFFIX ) set(pip_COMPANY SHS) diff --git a/libs/main/code/picodeinfo.cpp b/libs/main/code/picodeinfo.cpp index 01d8cc89..65932054 100644 --- a/libs/main/code/picodeinfo.cpp +++ b/libs/main/code/picodeinfo.cpp @@ -24,39 +24,39 @@ PIString PICodeInfo::EnumInfo::memberName(int value_) const { piForeachC (PICodeInfo::EnumeratorInfo & e, members) if (e.value == value_) - return e.name; + return e.name.toString(); return PIString(); } int PICodeInfo::EnumInfo::memberValue(const PIString & name_) const { piForeachC (PICodeInfo::EnumeratorInfo & e, members) - if (e.name == name_) + if (e.name.toString() == name_) return e.value; return -1; } PIVariantTypes::Enum PICodeInfo::EnumInfo::toPIVariantEnum() { - PIVariantTypes::Enum en(name); + PIVariantTypes::Enum en(name.toString()); for (auto m: members) en << m.toPIVariantEnumerator(); if (!en.isEmpty()) en.selectValue(members.front().value); return en; } -PIMap * PICodeInfo::classesInfo; -PIMap * PICodeInfo::enumsInfo; -PIMap * PICodeInfo::accessValueFunctions; -PIMap * PICodeInfo::accessTypeFunctions; +PIMap * PICodeInfo::classesInfo; +PIMap * PICodeInfo::enumsInfo; +PIMap * PICodeInfo::accessValueFunctions; +PIMap * PICodeInfo::accessTypeFunctions; bool __PICodeInfoInitializer__::_inited_ = false; PIVariant PICodeInfo::getMemberAsVariant(const void * p, const char * class_name, const char * member_name) { if (!p || !class_name || !member_name || !accessTypeFunctions || !accessValueFunctions) return PIVariant(); - AccessTypeFunction atf = accessTypeFunctions->value(PIStringAscii(class_name), (AccessTypeFunction)0); - AccessValueFunction avf = accessValueFunctions->value(PIStringAscii(class_name), (AccessValueFunction)0); + AccessTypeFunction atf = accessTypeFunctions->value(class_name, (AccessTypeFunction)0); + AccessValueFunction avf = accessValueFunctions->value(class_name, (AccessValueFunction)0); if (!atf || !avf) return PIVariant(); return PIVariant::fromValue(avf(p, member_name), PIStringAscii(atf(member_name))); } diff --git a/libs/main/code/picodeinfo.h b/libs/main/code/picodeinfo.h index 8329983e..7e576c40 100644 --- a/libs/main/code/picodeinfo.h +++ b/libs/main/code/picodeinfo.h @@ -27,6 +27,7 @@ #ifndef PICODEINFO_H #define PICODEINFO_H +#include "piconstchars.h" #include "pistringlist.h" #include "pivarianttypes.h" @@ -52,18 +53,18 @@ typedef PIByteArray(*AccessValueFunction)(const void *, const char *); typedef const char*(*AccessTypeFunction)(const char *); struct PIP_EXPORT TypeInfo { - TypeInfo(const PIString & n = PIString(), const PIString & t = PIString(), PICodeInfo::TypeFlags f = 0, int b = -1) {name = n; type = t; flags = f; bits = b;} + TypeInfo(const PIConstChars & n = PIConstChars(), const PIConstChars & t = PIConstChars(), PICodeInfo::TypeFlags f = 0, int b = -1) {name = n; type = t; flags = f; bits = b;} bool isBitfield() const {return bits > 0;} MetaMap meta; - PIString name; - PIString type; + PIConstChars name; + PIConstChars type; PICodeInfo::TypeFlags flags; int bits; }; struct PIP_EXPORT FunctionInfo { MetaMap meta; - PIString name; + PIConstChars name; TypeInfo return_type; PIVector arguments; }; @@ -72,19 +73,19 @@ struct PIP_EXPORT ClassInfo { ClassInfo() {has_name = true;} MetaMap meta; bool has_name; - PIString type; - PIString name; - PIStringList parents; + PIConstChars type; + PIConstChars name; + PIVector parents; PIVector variables; PIVector functions; PIVector children_info; }; struct PIP_EXPORT EnumeratorInfo { - EnumeratorInfo(const PIString & n = PIString(), int v = 0) {name = n; value = v;} - PIVariantTypes::Enumerator toPIVariantEnumerator() {return PIVariantTypes::Enumerator(value, name);} + EnumeratorInfo(const PIConstChars & n = PIConstChars(), int v = 0) {name = n; value = v;} + PIVariantTypes::Enumerator toPIVariantEnumerator() {return PIVariantTypes::Enumerator(value, name.toString());} MetaMap meta; - PIString name; + PIConstChars name; int value; }; @@ -93,7 +94,7 @@ struct PIP_EXPORT EnumInfo { int memberValue(const PIString & name) const; PIVariantTypes::Enum toPIVariantEnum(); MetaMap meta; - PIString name; + PIConstChars name; PIVector members; }; @@ -119,17 +120,17 @@ inline PICout operator <<(PICout s, const PICodeInfo::ClassInfo & v) { if (!v.parents.isEmpty()) { s << ": "; bool first = true; - piForeachC (PIString & i, v.parents) { + for (const auto & i: v.parents) { if (first) first = false; else s << ", "; s << i; } } s << " Meta" << v.meta << " {\n"; - piForeachC (FunctionInfo & i, v.functions) { + for (const auto & i: v.functions) { s << PICoutManipulators::Tab << i.return_type << " " << i.name << "("; bool fa = true; - piForeachC (TypeInfo & a, i.arguments) { + for (const auto & a: i.arguments) { if (fa) fa = false; else s << ", "; s << a; @@ -138,7 +139,7 @@ inline PICout operator <<(PICout s, const PICodeInfo::ClassInfo & v) { } if (!v.functions.isEmpty() && !v.variables.isEmpty()) s << "\n"; - piForeachC (TypeInfo & i, v.variables) { + for (const auto & i: v.variables) { s << PICoutManipulators::Tab << i << " Meta" << i.meta << ";\n"; } s << "}\n"; @@ -149,7 +150,7 @@ inline PICout operator <<(PICout s, const PICodeInfo::ClassInfo & v) { inline PICout operator <<(PICout s, const PICodeInfo::EnumInfo & v) { s.setControl(0, true); s << "enum " << v.name << " Meta" << v.meta << " {\n"; - piForeachC (EnumeratorInfo & i, v.members) { + for (const auto & i: v.members) { bool f = true; if (f) f = false; else s << ", "; @@ -160,21 +161,21 @@ inline PICout operator <<(PICout s, const PICodeInfo::EnumInfo & v) { return s; } -extern PIP_EXPORT PIMap * classesInfo; -extern PIP_EXPORT PIMap * enumsInfo; -extern PIP_EXPORT PIMap * accessValueFunctions; -extern PIP_EXPORT PIMap * accessTypeFunctions; +extern PIP_EXPORT PIMap * classesInfo; +extern PIP_EXPORT PIMap * enumsInfo; +extern PIP_EXPORT PIMap * accessValueFunctions; +extern PIP_EXPORT PIMap * accessTypeFunctions; inline PIByteArray getMemberValue(const void * p, const char * class_name, const char * member_name) { if (!p || !class_name || !member_name || !accessValueFunctions) return PIByteArray(); - AccessValueFunction af = accessValueFunctions->value(PIStringAscii(class_name), (AccessValueFunction)0); + AccessValueFunction af = accessValueFunctions->value(class_name, (AccessValueFunction)0); if (!af) return PIByteArray(); return af(p, member_name); } inline const char * getMemberType(const char * class_name, const char * member_name) { if (!class_name || !member_name || !accessTypeFunctions) return ""; - AccessTypeFunction af = accessTypeFunctions->value(PIStringAscii(class_name), (AccessTypeFunction)0); + AccessTypeFunction af = accessTypeFunctions->value(class_name, (AccessTypeFunction)0); if (!af) return ""; return af(member_name); } @@ -195,10 +196,10 @@ public: __PICodeInfoInitializer__() { if (_inited_) return; _inited_ = true; - PICodeInfo::classesInfo = new PIMap; - PICodeInfo::enumsInfo = new PIMap; - PICodeInfo::accessValueFunctions = new PIMap; - PICodeInfo::accessTypeFunctions = new PIMap; + PICodeInfo::classesInfo = new PIMap; + PICodeInfo::enumsInfo = new PIMap; + PICodeInfo::accessValueFunctions = new PIMap; + PICodeInfo::accessTypeFunctions = new PIMap; } static bool _inited_; }; diff --git a/libs/main/core/pistring.cpp b/libs/main/core/pistring.cpp index bfced926..90808881 100644 --- a/libs/main/core/pistring.cpp +++ b/libs/main/core/pistring.cpp @@ -263,7 +263,7 @@ PIString PIString::fromAscii(const char * s, int len) { PIString ret; ret.resize(len); for (int l = 0; l < len; ++l) { - ret[l] = s[l]; + ret[l] = s[l]; } return ret; } @@ -369,14 +369,14 @@ uint PIString::hash() const { PIByteArray PIString::toUTF8() const { - if (isEmpty()) return PIByteArray(1,'\0'); + if (isEmpty()) return PIByteArray(); buildData(__utf8name__); return PIByteArray(data_, strlen(data_)); } PIByteArray PIString::toCharset(const char * c) const { - if (isEmpty()) return PIByteArray(1,'\0'); + if (isEmpty()) return PIByteArray(); buildData( #ifdef PIP_ICU c @@ -418,6 +418,18 @@ PIString & PIString::operator +=(const PIString & str) { } +PIString & PIString::operator +=(const PIConstChars & str) { + if (!str.isEmpty()) { + size_t os = d.size(); + d.enlarge(str.size()); + for (size_t l = 0; l < d.size(); ++l) { + d[os + l] = str[l]; + } + } + return *this; +} + + bool PIString::operator ==(const PIString & str) const { return d == str.d; } diff --git a/libs/main/core/pistring.h b/libs/main/core/pistring.h index 6231519d..b270e3f9 100644 --- a/libs/main/core/pistring.h +++ b/libs/main/core/pistring.h @@ -27,6 +27,7 @@ #define PISTRING_H #include "pibytearray.h" +#include "piconstchars.h" #define PIStringAscii PIString::fromAscii @@ -71,6 +72,7 @@ public: PIString & operator +=(const wchar_t * str); PIString & operator +=(const PIByteArray & ba) {appendFromChars((const char * )ba.data(), ba.size_s(), __utf8name__); return *this;} PIString & operator +=(const PIString & str); + PIString & operator +=(const PIConstChars & str); //! \~english Contructs a copy of string. //! \~russian Создает копию строки. @@ -143,6 +145,8 @@ public: //! PIString s(5, "№"); // s = "№№№№№" //! \endcode PIString(const int len, const PIChar c) {for (int i = 0; i < len; ++i) d.push_back(c);} + + PIString(const PIConstChars & c) {*this += c;} ~PIString(); @@ -154,6 +158,14 @@ public: //! \~russian Оператор перемещающего присваивания. PIString & operator =(PIString && o) {d.swap(o.d); piSwap(data_, o.data_); return *this;} + //! \~english Assign operator. + //! \~russian Оператор присваивания. + PIString & operator =(const PIConstChars & o) {d.clear(); *this += o; return *this;} + + //! \~english Assign operator. + //! \~russian Оператор присваивания. + PIString & operator =(const char * o) {d.clear(); *this += o; return *this;} + //! \~english Compare operator. //! \~russian Оператор сравнения. bool operator ==(const PIString & str) const; @@ -271,6 +283,8 @@ public: //! \endcode PIString & operator <<(const wchar_t * str) {*this += str; return *this;} + PIString & operator <<(const PIConstChars & str) {*this += str; return *this;} + //! \~english Append string representation of "num" at the end of string. //! \~russian Добавляет в конец строковое представление "num". //! \~\details @@ -453,6 +467,8 @@ public: //! \~russian Вставляет "str" в конец строки. PIString & append(const PIString & str) {d.append(str.d); return *this;} + PIString & append(const PIConstChars & str) {*this += str; return *this;} + //! \~english Insert character `c` at the end of string. //! \~russian Вставляет символ `c` в конец строки. PIString & append(const PIChar c) {d.append(c); return *this;} @@ -469,6 +485,8 @@ public: //! \~russian Вставляет "str" в конец строки. PIString & push_back(const PIString & str) {d.push_back(str.d); return *this;} + PIString & push_back(const PIConstChars & str) {*this += str; return *this;} + //! \~english Insert character `c` at the end of string. //! \~russian Вставляет символ `c` в конец строки. PIString & push_back(const PIChar c) {d.push_back(c); return *this;} diff --git a/libs/main/io_devices/pifile.cpp b/libs/main/io_devices/pifile.cpp index 05fd459d..c08fbf32 100644 --- a/libs/main/io_devices/pifile.cpp +++ b/libs/main/io_devices/pifile.cpp @@ -614,7 +614,7 @@ int PIFile::writeDevice(const void * data, int max_size) { PIFile &PIFile::operator <<(const PIString & v) { - if (canWrite() && PRIVATE->fd != 0) + if (canWrite() && v.isNotEmpty() && PRIVATE->fd != 0) *this << v.toCharset(defaultCharset()); return *this; } diff --git a/libs/main/io_devices/piiodevice.cpp b/libs/main/io_devices/piiodevice.cpp index 28d1bc4b..389cd84d 100644 --- a/libs/main/io_devices/piiodevice.cpp +++ b/libs/main/io_devices/piiodevice.cpp @@ -266,11 +266,9 @@ void PIIODevice::write_func() { PIIODevice * PIIODevice::newDeviceByPrefix(const char * prefix) { if (!prefix) return nullptr; - PIConstChars p(prefix); - for (const auto & i: fabrics()) { - if (i.first == p) - return i.second(); - } + auto fi = fabrics().value(prefix); + if (fi.fabricator) + return fi.fabricator(); return nullptr; } @@ -488,17 +486,30 @@ void PIIODevice::splitFullPath(PIString fpwm, PIString * full_path, DeviceMode * PIStringList PIIODevice::availablePrefixes() { PIStringList ret; for (const auto & i: fabrics()) - ret << i.first.toString(); + ret << i.second.prefix.toString(); return ret; } -void PIIODevice::registerDevice(const char * prefix, PIIODevice * (*fabric)()) { +PIStringList PIIODevice::availableClasses() { + PIStringList ret; + for (const auto & i: fabrics()) + ret << i.second.classname.toString(); + return ret; +} + + +void PIIODevice::registerDevice(const char * prefix, const char * classname, PIIODevice * (*fabric)()) { PIConstChars p(prefix); if (p.isEmpty()) return; //printf("registerDevice %s %d %d\n", prefix, p.isEmpty(), fabrics().size()); - if (!fabrics().contains(p)) - fabrics()[p] = fabric; + if (!fabrics().contains(p)) { + FabricInfo fi; + fi.prefix = prefix; + fi.classname = classname; + fi.fabricator = fabric; + fabrics()[p] = fi; + } } @@ -555,8 +566,8 @@ void PIIODevice::cacheFullPath(const PIString & full_path, const PIIODevice * d) } -PIMap & PIIODevice::fabrics() { - static PIMap ret; +PIMap & PIIODevice::fabrics() { + static PIMap ret; return ret; } diff --git a/libs/main/io_devices/piiodevice.h b/libs/main/io_devices/piiodevice.h index ff47ccc6..301d70b2 100644 --- a/libs/main/io_devices/piiodevice.h +++ b/libs/main/io_devices/piiodevice.h @@ -47,7 +47,7 @@ typedef bool (*ReadRetFunc)(void * , uchar * , int ); # define REGISTER_DEVICE(name) \ STATIC_INITIALIZER_BEGIN \ - PIIODevice::registerDevice(name::fullPathPrefixS(), []()->PIIODevice*{return new name();});\ + PIIODevice::registerDevice(name::fullPathPrefixS(), #name, []()->PIIODevice*{return new name();});\ STATIC_INITIALIZER_END # define PIIODEVICE(name, prefix) \ @@ -90,6 +90,12 @@ public: Reliable /*! Channel without data errors / corruptions */ = 0x02 }; + struct FabricInfo { + PIConstChars prefix; + PIConstChars classname; + PIIODevice*(*fabricator)() = nullptr; + }; + typedef PIFlags DeviceOptions; typedef PIFlags DeviceInfoFlags; @@ -271,7 +277,10 @@ public: //! Returns fullPath prefixes of all registered devices static PIStringList availablePrefixes(); - static void registerDevice(const char * prefix, PIIODevice*(*fabric)()); + //! Returns class names of all registered devices + static PIStringList availableClasses(); + + static void registerDevice(const char * prefix, const char * classname, PIIODevice*(*fabric)()); EVENT_HANDLER(bool, open); @@ -421,7 +430,7 @@ private: void run(); void end() {terminate();} static void cacheFullPath(const PIString & full_path, const PIIODevice * d); - static PIMap & fabrics(); + static PIMap & fabrics(); PITimer timer; PITimeMeasurer tm; diff --git a/utils/code_model_generator/main.cpp b/utils/code_model_generator/main.cpp index 1a473200..7adbdf41 100755 --- a/utils/code_model_generator/main.cpp +++ b/utils/code_model_generator/main.cpp @@ -428,7 +428,7 @@ void writeModel(PICodeParser & parser, PICLI & cli, const PIString out, bool met PIString inc_string; PIVector incf = inc_files.toVector(); piForeachC (PIString & i, incf) { - if (i != parser.mainFile()) + if ((i != parser.mainFile()) && (streams || texts || getters)) inc_string << "\n#include \"" << i << "\""; }