diff options
-rw-r--r-- | cpp/demo/Ice/invoke/Client.cpp | 14 | ||||
-rw-r--r-- | cpp/demo/Ice/invoke/PrinterI.cpp | 12 | ||||
-rw-r--r-- | cpp/include/Ice/Stream.h | 540 | ||||
-rw-r--r-- | cpp/src/Slice/CPlusPlusUtil.cpp | 412 | ||||
-rw-r--r-- | cpp/src/slice2cpp/Gen.cpp | 354 | ||||
-rw-r--r-- | cpp/src/slice2cpp/Gen.h | 18 | ||||
-rw-r--r-- | cpp/test/Ice/objects/TestI.cpp | 2 | ||||
-rw-r--r-- | cpp/test/Ice/stream/Client.cpp | 447 |
8 files changed, 1343 insertions, 456 deletions
diff --git a/cpp/demo/Ice/invoke/Client.cpp b/cpp/demo/Ice/invoke/Client.cpp index ad92664a007..4226899e60a 100644 --- a/cpp/demo/Ice/invoke/Client.cpp +++ b/cpp/demo/Ice/invoke/Client.cpp @@ -74,7 +74,7 @@ public: // Ice::InputStreamPtr in = Ice::createInputStream(_communicator, outParams); Demo::CPtr c; - Demo::ice_readC(in, c); + in->read(c); string str = in->readString(); in->readPendingObjects(); cout << "Got string `" << str << "' and class: s.name=" << c->s.name @@ -250,7 +250,7 @@ InvokeClient::run(int argc, char* argv[]) Demo::StringDict dict; dict["The"] = "streaming"; dict["API"] = "works!"; - Demo::ice_writeStringDict(out, dict); + out->write(dict); out->finished(inParams); // @@ -275,7 +275,7 @@ InvokeClient::run(int argc, char* argv[]) // Ice::ByteSeq inParams, outParams; Ice::OutputStreamPtr out = Ice::createOutputStream(communicator()); - Demo::ice_writeColor(out, Demo::green); + out->write(Demo::green); out->finished(inParams); // @@ -303,7 +303,7 @@ InvokeClient::run(int argc, char* argv[]) Demo::Structure s; s.name = "red"; s.value = Demo::red; - Demo::ice_writeStructure(out, s); + out->write(s); out->finished(inParams); // @@ -338,7 +338,7 @@ InvokeClient::run(int argc, char* argv[]) arr.push_back(Demo::Structure()); arr.back().name = "blue"; arr.back().value = Demo::blue; - Demo::ice_writeStructureSeq(out, arr); + out->write(arr); out->finished(inParams); // @@ -366,7 +366,7 @@ InvokeClient::run(int argc, char* argv[]) Demo::CPtr c = new Demo::C; c->s.name = "blue"; c->s.value = Demo::blue; - Demo::ice_writeC(out, c); + out->write(c); out->writePendingObjects(); out->finished(inParams); @@ -409,7 +409,7 @@ InvokeClient::run(int argc, char* argv[]) // Ice::InputStreamPtr in = Ice::createInputStream(communicator(), outParams); Demo::CPtr c; - Demo::ice_readC(in, c); + in->read(c); string str = in->readString(); in->readPendingObjects(); cout << "Got string `" << str << "' and class: s.name=" << c->s.name diff --git a/cpp/demo/Ice/invoke/PrinterI.cpp b/cpp/demo/Ice/invoke/PrinterI.cpp index f6752c6b16b..c6ca9c4aef8 100644 --- a/cpp/demo/Ice/invoke/PrinterI.cpp +++ b/cpp/demo/Ice/invoke/PrinterI.cpp @@ -65,7 +65,7 @@ PrinterI::ice_invoke(const vector<Ice::Byte>& inParams, vector<Ice::Byte>& outPa else if(current.operation == "printDictionary") { Demo::StringDict dict; - Demo::ice_readStringDict(in, dict); + in->read(dict); cout << "Printing dictionary {"; for(Demo::StringDict::iterator p = dict.begin(); p != dict.end(); ++p) { @@ -81,21 +81,21 @@ PrinterI::ice_invoke(const vector<Ice::Byte>& inParams, vector<Ice::Byte>& outPa else if(current.operation == "printEnum") { Demo::Color c; - Demo::ice_readColor(in, c); + in->read(c); cout << "Printing enum " << c << endl; return true; } else if(current.operation == "printStruct") { Demo::Structure s; - Demo::ice_readStructure(in, s); + in->read(s); cout << "Printing struct: name=" << s.name << ", value=" << s.value << endl; return true; } else if(current.operation == "printStructSequence") { Demo::StructureSeq seq; - Demo::ice_readStructureSeq(in, seq); + in->read(seq); cout << "Printing struct sequence: {"; for(Demo::StructureSeq::iterator p = seq.begin(); p != seq.end(); ++p) { @@ -111,7 +111,7 @@ PrinterI::ice_invoke(const vector<Ice::Byte>& inParams, vector<Ice::Byte>& outPa else if(current.operation == "printClass") { Demo::CPtr c; - Demo::ice_readC(in, c); + in->read(c); in->readPendingObjects(); cout << "Printing class: s.name=" << c->s.name << ", s.value=" << c->s.value << endl; return true; @@ -122,7 +122,7 @@ PrinterI::ice_invoke(const vector<Ice::Byte>& inParams, vector<Ice::Byte>& outPa c->s.name = "green"; c->s.value = Demo::green; Ice::OutputStreamPtr out = Ice::createOutputStream(communicator); - Demo::ice_writeC(out, c); + out->write(c); out->writeString("hello"); out->writePendingObjects(); out->finished(outParams); diff --git a/cpp/include/Ice/Stream.h b/cpp/include/Ice/Stream.h index 9c8afae8966..48c006fcb43 100644 --- a/cpp/include/Ice/Stream.h +++ b/cpp/include/Ice/Stream.h @@ -18,6 +18,115 @@ namespace Ice { + +#if defined(_MSC_VER) && (_MSC_VER < 1300) // COMPILERBUG +// +// VC++ 6 compiler bugs doesn't allow to write +// the Stream API using c++ templates. +// +// see: http://support.microsoft.com/kb/240866 +// http://support.microsoft.com/kb/241569 +// +#else + +enum StreamTraitType +{ + StreamTraitTypeStruct, + StreamTraitTypeStructClass, // struct with cpp:class metadata + StreamTraitTypeByteEnum, // Enums with up to 127 enumerators + StreamTraitTypeShortEnum, // Enums with up to 32767 enumerators + StreamTraitTypeIntEnum, // Enums with more than 32767 enumerators + StreamTraitTypeSequence, + StreamTraitTypeDictionary, + StreamTraitTypeUnknown +}; + +// +// We need to predefine this, it is used by the enum +// stream writer specializations. +// +class MarshalException; + +// +// Basic trait template. This doesn't actually do anything--we +// just use it as a template that we can specialize. +// +template <typename T> +struct StreamTrait +{ + static const ::Ice::StreamTraitType type = Ice::StreamTraitTypeUnknown; + static const int enumLimit = 0; // Used to implement enum range check +}; + +// +// StreamTrait specialization for std::vector +// +template <typename T> +struct StreamTrait< std::vector<T> > +{ + static const ::Ice::StreamTraitType type = Ice::StreamTraitTypeSequence; + static const int enumLimit = 0; // Used to implement enum range check +}; + +// +// StreamTrait specialization for std::map. +// +template <typename K, typename V> +struct StreamTrait< std::map<K, V> > +{ + static const ::Ice::StreamTraitType type = Ice::StreamTraitTypeDictionary; + static const int enumLimit = 0; // Used to implement enum range check +}; + +// +// This is the non-specialized version of the writer. For each +// kind of user-defined type (enum, struct, etc), we specialize +// this template to call the correct member function that writes +// an instance of that type to the stream. +// +template <StreamTraitType st> +struct StreamWriter +{ + template<typename T> + static void write(const ::Ice::OutputStreamPtr&, const T&) + { + // This asserts because we end up writing + // something for which we never defined a trait. + assert(false); + } +}; + +// +// This is the non-specialized version of the reader. For each +// kind of user-defined type (enum, struct, etc), we specialize +// this template to call the correct member function that reads +// an instance of that type to the stream. +// +template<StreamTraitType st> +struct StreamReader +{ + template<typename T> + static void read(const ::Ice::InputStreamPtr&, T&) + { + // This asserts because we end up reading + // something for wich we never define a trait. + assert(false); + } +}; + +template<typename T>void +__patch__Ptr(void* __addr, ::Ice::ObjectPtr& v) +{ + ::IceInternal::Handle<T>* p = static_cast< ::IceInternal::Handle<T>*>(__addr); + assert(p); + *p = ::IceInternal::Handle<T>::dynamicCast(v); + if(v && !*p) + { + IceInternal::Ex::throwUOE(T::ice_staticId(), v->ice_id()); + } +} +#endif + class ICE_API ReadObjectCallback : public ::IceUtil::Shared { @@ -27,6 +136,22 @@ public: }; typedef IceUtil::Handle< ReadObjectCallback > ReadObjectCallbackPtr; +class ICE_API ReadObjectCallbackI : public ReadObjectCallback +{ +public: + + typedef void (*PatchFunc)(void*, Ice::ObjectPtr&); + + ReadObjectCallbackI(PatchFunc, void*); + + virtual void invoke(const ::Ice::ObjectPtr&); + +private: + + PatchFunc _func; + void* _arg; +}; + class ICE_API InputStream : public ::IceUtil::Shared { public: @@ -96,6 +221,117 @@ public: virtual void readPendingObjects() = 0; virtual void rewind() = 0; + +#if defined(_MSC_VER) && (_MSC_VER < 1300) // COMPILERBUG +// +// VC++ 6 compiler bugs doesn't allow to write +// the Stream API using c++ templates. +// +// see: http://support.microsoft.com/kb/240866 +// http://support.microsoft.com/kb/241569 +// +#else + + // + // read overloads for bool references in a std::vector. + // + inline void +#if defined(_MSC_VER) && (_MSC_VER >= 1300) + // std::vector<bool> optimization for Vs2008 + read(std::_Vb_reference<unsigned int, __w64 int, std::vector<bool, std::allocator<bool> > > v) +#elif defined(__BCPLUSPLUS__) + // std::vector<bool> optimization for Borland. + read(std::_Vb_reference<unsigned int, int> v) +#else + // default optimization for GCC + read(std::_Bit_reference v) +#endif + { + v = readBool(); + } + + inline void + read(bool& v) + { + v = readBool(); + } + + inline void + read(::Ice::Byte& v) + { + v = readByte(); + } + + inline void + read(::Ice::Short& v) + { + v = readShort(); + } + + inline void + read(Ice::Int& v) + { + v = readInt(); + } + + inline void + read(Ice::Long& v) + { + v = readLong(); + } + + inline void + read(Ice::Float& v) + { + v = readFloat(); + } + + inline void + read(Ice::Double& v) + { + v = readDouble(); + } + + inline void + read(std::string& v) + { + v = readString(); + } + + inline void + read(std::wstring& v) + { + v = readWstring(); + } + + template<typename T> inline void + read(::IceInternal::ProxyHandle<T>& v) + { + ::Ice::ObjectPrx proxy = readProxy(); + if(!proxy) + { + v = 0; + } + else + { + v = new T; + v->__copyFrom(proxy); + } + } + + template<typename T> inline void + read(::IceInternal::Handle<T>& v) + { + ::Ice::ReadObjectCallbackPtr cb = new ::Ice::ReadObjectCallbackI(&__patch__Ptr< T>, &v); + readObject(cb); + } + + template<typename T> inline void + read(T& v) + { + StreamReader< ::Ice::StreamTrait<T>::type>::read(this, v); + } +#endif }; class ICE_API OutputStream : public ::IceUtil::Shared @@ -159,7 +395,296 @@ public: virtual void finished(::std::vector< ::Ice::Byte >&) = 0; virtual void reset(bool) = 0; + +#if defined(_MSC_VER) && (_MSC_VER < 1300) // COMPILERBUG +// +// VC++ 6 compiler bugs doesn't allow to write +// the Stream API using c++ templates. +// +// see: http://support.microsoft.com/kb/240866 +// http://support.microsoft.com/kb/241569 +// +#else + inline void + write(bool v) + { + writeBool(v); + } + + inline void + write(::Ice::Byte v) + { + writeByte(v); + } + + inline void + write(::Ice::Short v) + { + writeShort(v); + } + + inline void + write(::Ice::Int v) + { + writeInt(v); + } + + inline void + write(::Ice::Long v) + { + writeLong(v); + } + + inline void + write(::Ice::Float v) + { + writeFloat(v); + } + + inline void + write(::Ice::Double v) + { + writeDouble(v); + } + + inline void + write(const std::string& v) + { + writeString(v); + } + + inline void + write(const char* v) + { + writeString(v); + } + + inline void + write(const std::wstring& v) + { + writeWstring(v); + } + + template<typename T> inline void + write(const ::IceInternal::ProxyHandle<T>& v) + { + writeProxy(v); + } + + template<typename T> inline void + write(const ::IceInternal::Handle<T>& v) + { + writeObject(v); + } + + template<typename T> inline void + write(const T& v) + { + StreamWriter< ::Ice::StreamTrait<T>::type>::write(this, v); + } +#endif +}; + +#if defined(_MSC_VER) && (_MSC_VER < 1300) // COMPILERBUG +// +// VC++ 6 compiler bugs doesn't allow to write +// the Stream API using c++ templates. +// +// see: http://support.microsoft.com/kb/240866 +// http://support.microsoft.com/kb/241569 +// +#else +template <> // StreamWriter specialization for structs +struct StreamWriter<StreamTraitTypeStruct> +{ + template<typename T> + static void write(const ::Ice::OutputStreamPtr& outS, const T& v) + { + v.ice_write(outS); // Call the member function in the struct + } +}; + +template <> // Reder specialization for structs +struct StreamReader<StreamTraitTypeStruct> +{ + template<typename T> + static void read(const ::Ice::InputStreamPtr& inS, T& v) + { + v.ice_read(inS); // Call the member function in the struct + } +}; + +template <> // Writer specialization for structs with cpp:class metadata +struct StreamWriter<StreamTraitTypeStructClass> +{ + template<typename T> + static void write(const ::Ice::OutputStreamPtr& outS, const T& v) + { + v->ice_write(outS); // Call the member function in the class + } +}; + +template <> // Reder specialization for structs with cpp:class metadata +struct StreamReader<StreamTraitTypeStructClass> +{ + template<typename T> + static void read(const ::Ice::InputStreamPtr& inS, T& v) + { + v->ice_read(inS); // Call the member function in the class + } +}; + +template <> // Writer specialization for byte enums +struct StreamWriter<StreamTraitTypeByteEnum> +{ + template<typename T> + static void write(const ::Ice::OutputStreamPtr& outS, const T& v) + { + if(static_cast<int>(v) < 0 || static_cast<int>(v) >= ::Ice::StreamTrait<T>::enumLimit) + { + throw ::Ice::MarshalException(__FILE__, __LINE__, "enumerator out of range"); + } + outS->writeByte(static_cast< ::Ice::Byte>(v)); + } +}; + +template<> // Reader specialization for byte enums +struct StreamReader<StreamTraitTypeByteEnum> +{ + template<typename T> + static void read(const ::Ice::InputStreamPtr& inS, T& v) + { + ::Ice::Byte val = inS->readByte(); + if(val > ::Ice::StreamTrait<T>::enumLimit) + { + throw ::Ice::MarshalException(__FILE__, __LINE__, "enumerator out of range"); + } + v = static_cast<T>(val); + } +}; + + +template <> // Writer specialization for short enums +struct StreamWriter<StreamTraitTypeShortEnum> +{ + template<typename T> + static void write(const ::Ice::OutputStreamPtr& outS, const T& v) + { + if(static_cast<int>(v) < 0 || static_cast<int>(v) >= ::Ice::StreamTrait<T>::enumLimit) + { + throw ::Ice::MarshalException(__FILE__, __LINE__, "enumerator out of range"); + } + outS->writeShort(static_cast< ::Ice::Short>(v)); + } +}; + +template<> // Reader specialization for short enums +struct StreamReader<StreamTraitTypeShortEnum> +{ + template<typename T> + static void read(const ::Ice::InputStreamPtr& inS, T& v) + { + ::Ice::Short val = inS->readShort(); + if(val < 0 || val > ::Ice::StreamTrait<T>::enumLimit) + { + throw ::Ice::MarshalException(__FILE__, __LINE__, "enumerator out of range"); + } + v = static_cast<T>(val); + } +}; + +template <> // Writer specialization for int enums +struct StreamWriter<StreamTraitTypeIntEnum> +{ + template<typename T> + static void write(const ::Ice::OutputStreamPtr& outS, const T& v) + { + if(static_cast<int>(v) < 0 || static_cast<int>(v) >= ::Ice::StreamTrait<T>::enumLimit) + { + throw ::Ice::MarshalException(__FILE__, __LINE__, "enumerator out of range"); + } + outS->writeInt(static_cast< ::Ice::Int>(v)); + } +}; + +template<> // Reader specialization for int enums +struct StreamReader<StreamTraitTypeIntEnum> +{ + template<typename T> + static void read(const ::Ice::InputStreamPtr& inS, T& v) + { + ::Ice::Int val = inS->readInt(); + if(val < 0 || val > ::Ice::StreamTrait<T>::enumLimit) + { + throw ::Ice::MarshalException(__FILE__, __LINE__, "enumerator out of range"); + } + v = static_cast<T>(val); + } +}; + +template<> // Writer specialization for sequences +struct StreamWriter<StreamTraitTypeSequence> +{ + template<typename T> + static void write(const ::Ice::OutputStreamPtr& outS, const T& v) + { + outS->writeSize(::Ice::Int(v.size())); + typename T::const_iterator p; + for(p = v.begin(); p != v.end(); ++p) + { + outS->write((*p)); + } + } +}; + +template<> // Reader specialization for sequences +struct StreamReader<StreamTraitTypeSequence> +{ + template<typename T> + static void read(const ::Ice::InputStreamPtr& inS, T& v) + { + ::Ice::Int sz = inS->readSize(); + v.resize(sz); + for(int i = 0; i < sz; ++i) + { + inS->read(v[i]); + } + } +}; + +template<> // Writer specialization for dictionaries. +struct StreamWriter<StreamTraitTypeDictionary> +{ + template<typename T> + static void write(const ::Ice::OutputStreamPtr& outS, const T& v) + { + outS->writeSize(::Ice::Int(v.size())); + typename T::const_iterator p; + for(p = v.begin(); p != v.end(); ++p) + { + outS->write(p->first); + outS->write(p->second); + } + } +}; + +template<> // Reader specialization for dictionaries. +struct StreamReader<StreamTraitTypeDictionary> +{ + template<typename T> + static void read(const ::Ice::InputStreamPtr& inS, T& v) + { + ::Ice::Int sz = inS->readSize(); + while(sz--) + { + typename T::value_type p; + inS->read(const_cast< typename T::key_type&>(p.first)); + typename T::iterator i = v.insert(v.end(), p); + inS->read(i->second); + } + } }; +#endif class ICE_API ObjectReader : public ::Ice::Object { @@ -193,21 +718,6 @@ private: }; typedef ::IceInternal::Handle< ObjectWriter > ObjectWriterPtr; -class ICE_API ReadObjectCallbackI : public ReadObjectCallback -{ -public: - - typedef void (*PatchFunc)(void*, Ice::ObjectPtr&); - - ReadObjectCallbackI(PatchFunc, void*); - - virtual void invoke(const ::Ice::ObjectPtr&); - -private: - - PatchFunc _func; - void* _arg; -}; class ICE_API UserExceptionWriter : public UserException { diff --git a/cpp/src/Slice/CPlusPlusUtil.cpp b/cpp/src/Slice/CPlusPlusUtil.cpp index 93c5f25a1d3..a19636f2ef8 100644 --- a/cpp/src/Slice/CPlusPlusUtil.cpp +++ b/cpp/src/Slice/CPlusPlusUtil.cpp @@ -1124,418 +1124,14 @@ Slice::writeStreamMarshalUnmarshalCode(Output& out, const TypePtr& type, const s stream = str; } - BuiltinPtr builtin = BuiltinPtr::dynamicCast(type); - if(builtin) - { - switch(builtin->kind()) - { - case Builtin::KindByte: - { - if(marshal) - { - out << nl << stream << "->writeByte(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readByte();"; - } - break; - } - case Builtin::KindBool: - { - if(marshal) - { - out << nl << stream << "->writeBool(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readBool();"; - } - break; - } - case Builtin::KindShort: - { - if(marshal) - { - out << nl << stream << "->writeShort(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readShort();"; - } - break; - } - case Builtin::KindInt: - { - if(marshal) - { - out << nl << stream << "->writeInt(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readInt();"; - } - break; - } - case Builtin::KindLong: - { - if(marshal) - { - out << nl << stream << "->writeLong(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readLong();"; - } - break; - } - case Builtin::KindFloat: - { - if(marshal) - { - out << nl << stream << "->writeFloat(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readFloat();"; - } - break; - } - case Builtin::KindDouble: - { - if(marshal) - { - out << nl << stream << "->writeDouble(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readDouble();"; - } - break; - } - case Builtin::KindString: - { - string strType = findMetaData(metaData, true); - if(strType != "string" && (useWstring || strType == "wstring")) - { - if(marshal) - { - out << nl << stream << "->writeWstring(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readWstring();"; - } - } - else - { - if(marshal) - { - out << nl << stream << "->writeString(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readString();"; - } - } - break; - } - case Builtin::KindObject: - { - if(marshal) - { - out << nl << "::Ice::ice_writeObject(" << stream << ", " << fixedParam << ");"; - } - else - { - out << nl << "::Ice::ice_readObject(" << stream << ", " << fixedParam << ");"; - } - break; - } - case Builtin::KindObjectProxy: - { - // TODO - if(marshal) - { - out << nl << stream << "->writeProxy(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readProxy();"; - } - break; - } - case Builtin::KindLocalObject: - { - assert(false); - break; - } - } - - return; - } - - ClassDeclPtr cl = ClassDeclPtr::dynamicCast(type); - if(cl) + if(marshal) { - string scope = fixKwd(cl->scope()); - if(marshal) - { - out << nl << scope << "ice_write" << cl->name() << "(" << stream << ", " << fixedParam << ");"; - } - else - { - out << nl << scope << "ice_read" << cl->name() << "(" << stream << ", " << fixedParam << ");"; - } - - return; + out << nl << stream << "->write(" << fixedParam << ");"; } - - StructPtr st = StructPtr::dynamicCast(type); - if(st) - { - string scope = fixKwd(st->scope()); - if(marshal) - { - out << nl << scope << "ice_write" << st->name() << "(" << stream << ", " << fixedParam << ");"; - } - else - { - if(findMetaData(st->getMetaData(), false) == "class") - { - out << nl << fixedParam << " = new " << fixKwd(st->scoped()) << ";"; - } - out << nl << scope << "ice_read" << st->name() << "(" << stream << ", " << fixedParam << ");"; - } - - return; - } - - SequencePtr seq = SequencePtr::dynamicCast(type); - if(seq) - { - string seqType = findMetaData(metaData, false); - if(!seqType.empty()) - { - if(marshal) - { - out << nl << stream << "->writeSize(static_cast< ::Ice::Int>(" << fixedParam << ".size()));"; - out << nl << seqType << "::const_iterator ___" << fixedParam << ";"; - out << nl << "for(___" << fixedParam << " = " << fixedParam << ".begin(); ___" << fixedParam << " != " - << fixedParam << ".end(); ++___" << fixedParam << ")"; - out << sb; - writeStreamMarshalUnmarshalCode(out, seq->type(), "(*___" + fixedParam + ")", true); - out << eb; - } - else - { - out << nl << seqType << "(static_cast< ::Ice::Int>(" << stream << "->readSize())).swap(" - << fixedParam << ");"; - out << nl << seqType << "::iterator ___" << fixedParam << ";"; - out << nl << "for(___" << fixedParam << " = " << fixedParam << ".begin(); ___" << fixedParam << " != " - << fixedParam << ".end(); ++___" << fixedParam << ")"; - out << sb; - writeStreamMarshalUnmarshalCode(out, seq->type(), "(*___" + fixedParam + ")", false); - out << eb; - } - } - else - { - bool protobuf; - seqType = findMetaData(seq, seq->getMetaData(), false, protobuf); - builtin = BuiltinPtr::dynamicCast(seq->type()); - if(protobuf || !seqType.empty() || !builtin || (builtin->kind() == Builtin::KindObject || - builtin->kind() == Builtin::KindObjectProxy)) - { - string scope = fixKwd(seq->scope()); - if(marshal) - { - out << nl << scope << "ice_write" << seq->name() << '(' << stream << ", " << fixedParam << ");"; - } - else - { - out << nl << scope << "ice_read" << seq->name() << '(' << stream << ", " << fixedParam << ");"; - } - } - else - { - switch(builtin->kind()) - { - case Builtin::KindByte: - { - if(marshal) - { - out << nl << stream << "->writeByteSeq(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readByteSeq();"; - } - break; - } - case Builtin::KindBool: - { - if(marshal) - { - out << nl << stream << "->writeBoolSeq(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readBoolSeq();"; - } - break; - } - case Builtin::KindShort: - { - if(marshal) - { - out << nl << stream << "->writeShortSeq(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readShortSeq();"; - } - break; - } - case Builtin::KindInt: - { - if(marshal) - { - out << nl << stream << "->writeIntSeq(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readIntSeq();"; - } - break; - } - case Builtin::KindLong: - { - if(marshal) - { - out << nl << stream << "->writeLongSeq(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readLongSeq();"; - } - break; - } - case Builtin::KindFloat: - { - if(marshal) - { - out << nl << stream << "->writeFloatSeq(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readFloatSeq();"; - } - break; - } - case Builtin::KindDouble: - { - if(marshal) - { - out << nl << stream << "->writeDoubleSeq(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readDoubleSeq();"; - } - break; - } - case Builtin::KindString: - { - string strType = findMetaData(seq->typeMetaData(), true); - if(strType != "string" && (useWstring || strType == "wstring")) - { - if(marshal) - { - out << nl << stream << "->writeWstringSeq(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readWstringSeq();"; - } - } - else - { - if(marshal) - { - out << nl << stream << "->writeStringSeq(" << fixedParam << ");"; - } - else - { - out << nl << fixedParam << " = " << stream << "->readStringSeq();"; - } - } - break; - } - case Builtin::KindObject: - case Builtin::KindObjectProxy: - case Builtin::KindLocalObject: - { - assert(false); - break; - } - } - } - } - - return; - } - - DictionaryPtr dict = DictionaryPtr::dynamicCast(type); - if(dict) - { - string scope = fixKwd(dict->scope()); - if(marshal) - { - out << nl << scope << "ice_write" << dict->name() << "(" << stream << ", " << fixedParam << ");"; - } - else - { - out << nl << scope << "ice_read" << dict->name() << "(" << stream << ", " << fixedParam << ");"; - } - - return; - } - - EnumPtr en = EnumPtr::dynamicCast(type); - if(en) - { - string scope = fixKwd(en->scope()); - if(marshal) - { - out << nl << scope << "ice_write" << en->name() << "(" << stream << ", " << fixedParam << ");"; - } - else - { - out << nl << scope << "ice_read" << en->name() << "(" << stream << ", " << fixedParam << ");"; - } - - return; - } - - ProxyPtr prx = ProxyPtr::dynamicCast(type); - if(prx) + else { - ClassDeclPtr cls = prx->_class(); - string scope = fixKwd(cls->scope()); - if(marshal) - { - out << nl << scope << "ice_write" << cls->name() << "Prx(" << stream << ", " << fixedParam << ");"; - } - else - { - out << nl << scope << "ice_read" << cls->name() << "Prx(" << stream << ", " << fixedParam << ");"; - } - - return; + out << nl << stream << "->read(" << fixedParam << ");"; } - - assert(false); } // Accepted metadata. diff --git a/cpp/src/slice2cpp/Gen.cpp b/cpp/src/slice2cpp/Gen.cpp index 774d1766bc5..18369db167e 100644 --- a/cpp/src/slice2cpp/Gen.cpp +++ b/cpp/src/slice2cpp/Gen.cpp @@ -260,8 +260,6 @@ Slice::Gen::generate(const UnitPtr& p) if(_stream || p->hasNonLocalClassDefs() || p->hasNonLocalExceptions()) { - H << "\n#include <Ice/StreamF.h>"; - if(!p->hasNonLocalClassDefs()) { C << "\n#include <Ice/LocalException.h>"; @@ -269,7 +267,7 @@ Slice::Gen::generate(const UnitPtr& p) if(_stream) { - C << "\n#include <Ice/Stream.h>"; + H << "\n#include <Ice/Stream.h>"; } } @@ -364,6 +362,11 @@ Slice::Gen::generate(const UnitPtr& p) ObjectVisitor objectVisitor(H, C, _dllExport, _stream); p->visit(&objectVisitor, false); + if(_stream) + { + StreamVisitor streamVistor(H, C); + p->visit(&streamVistor, false); + } if(_impl) { implH << "\n#include <"; @@ -698,9 +701,20 @@ Slice::Gen::TypesVisitor::visitExceptionEnd(const ExceptionPtr& p) H << sp << nl << "virtual void __write(::IceInternal::BasicStream*) const;"; H << nl << "virtual void __read(::IceInternal::BasicStream*, bool);"; + + H.zeroIndent(); + H << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + H.restoreIndent(); + H << nl << "//Stream api is not supported in VC++ 6"; + H.zeroIndent(); + H << nl << "#else"; + H.restoreIndent(); H << nl << "virtual void __write(const ::Ice::OutputStreamPtr&) const;"; H << nl << "virtual void __read(const ::Ice::InputStreamPtr&, bool);"; - + H.zeroIndent(); + H << nl << "#endif"; + H.restoreIndent(); + C << sp << nl << "void" << nl << scoped.substr(2) << "::__write(::IceInternal::BasicStream* __os) const"; C << sb; C << nl << "__os->write(::std::string(\"" << p->scoped() << "\"), false);"; @@ -737,6 +751,13 @@ Slice::Gen::TypesVisitor::visitExceptionEnd(const ExceptionPtr& p) if(_stream) { + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C << nl << "#else"; + C.restoreIndent(); C << sp << nl << "void" << nl << scoped.substr(2) << "::__write(const ::Ice::OutputStreamPtr& __outS) const"; C << sb; @@ -773,12 +794,22 @@ Slice::Gen::TypesVisitor::visitExceptionEnd(const ExceptionPtr& p) emitUpcall(base, "::__read(__inS, true);"); } C << eb; + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } else { // // Emit placeholder functions to catch errors. // + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C << nl << "#else"; + C.restoreIndent(); C << sp << nl << "void" << nl << scoped.substr(2) << "::__write(const ::Ice::OutputStreamPtr&) const"; C << sb; C << nl << "Ice::MarshalException ex(__FILE__, __LINE__);"; @@ -792,6 +823,10 @@ Slice::Gen::TypesVisitor::visitExceptionEnd(const ExceptionPtr& p) C << nl << "ex.reason = \"exception " << scoped .substr(2)<< " was not generated with stream support\";"; C << nl << "throw ex;"; C << eb; + + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } if(p->usesClasses()) @@ -1020,8 +1055,18 @@ Slice::Gen::TypesVisitor::visitStructEnd(const StructPtr& p) if(_stream) { + H.zeroIndent(); + H << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + H.restoreIndent(); + H << nl << "//Stream api is not supported in VC++ 6"; + H.zeroIndent(); + H << nl << "#else"; + H.restoreIndent(); H << sp << nl << dllExport << "void ice_write(const ::Ice::OutputStreamPtr&) const;"; H << nl << dllExport << "void ice_read(const ::Ice::InputStreamPtr&);"; + H.zeroIndent(); + H << nl << "#endif"; + H.restoreIndent(); } C << sp << nl << "void" << nl << scoped.substr(2) << "::__write(::IceInternal::BasicStream* __os) const"; @@ -1042,6 +1087,13 @@ Slice::Gen::TypesVisitor::visitStructEnd(const StructPtr& p) if(_stream) { + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C << nl << "#else"; + C.restoreIndent(); C << sp << nl << "void" << nl << scoped.substr(2) << "::ice_write(const ::Ice::OutputStreamPtr& __outS) const"; C << sb; @@ -1060,6 +1112,9 @@ Slice::Gen::TypesVisitor::visitStructEnd(const StructPtr& p) (*q)->getMetaData()); } C << eb; + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } } @@ -1070,11 +1125,28 @@ Slice::Gen::TypesVisitor::visitStructEnd(const StructPtr& p) if(!p->isLocal() && _stream) { + H.zeroIndent(); + H << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + H.restoreIndent(); + H << nl << "//Stream api is not supported in VC++ 6"; + H.zeroIndent(); + H << nl << "#else"; + H.restoreIndent(); H << sp << nl << "void ice_write" << p->name() << "(const ::Ice::OutputStreamPtr&, const " << p->name() << "Ptr&);"; H << nl << "void ice_read" << p->name() << "(const ::Ice::InputStreamPtr&, " << p->name() << "Ptr&);"; - + H.zeroIndent(); + H << nl << "#endif"; + H.restoreIndent(); + + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C << nl << "#else"; + C.restoreIndent(); C << sp << nl << "void" << nl << scope.substr(2) << "ice_write" << p->name() << "(const ::Ice::OutputStreamPtr& __outS, const " << fixKwd(p->scoped() + "Ptr") << "& __v)"; C << sb; @@ -1086,16 +1158,36 @@ Slice::Gen::TypesVisitor::visitStructEnd(const StructPtr& p) C << sb; C << nl << "__v->ice_read(__inS);"; C << eb; + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } } else { if(!p->isLocal() && _stream) { + H.zeroIndent(); + H << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + H.restoreIndent(); + H << nl << "//Stream api is not supported in VC++ 6"; + H.zeroIndent(); + H << nl << "#else"; + H.restoreIndent(); H << sp << nl << dllExport << "void ice_write" << p->name() << "(const ::Ice::OutputStreamPtr&, const " << name << "&);"; H << nl << dllExport << "void ice_read" << p->name() << "(const ::Ice::InputStreamPtr&, " << name << "&);"; - + H.zeroIndent(); + H << nl << "#endif"; + H.restoreIndent(); + + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C << nl << "#else"; + C.restoreIndent(); C << sp << nl << "void" << nl << scope.substr(2) << "ice_write" << p->name() << "(const ::Ice::OutputStreamPtr& __outS, const " << scoped << "& __v)"; C << sb; @@ -1107,6 +1199,9 @@ Slice::Gen::TypesVisitor::visitStructEnd(const StructPtr& p) C << sb; C << nl << "__v.ice_read(__inS);"; C << eb; + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } } @@ -1186,10 +1281,20 @@ Slice::Gen::TypesVisitor::visitSequence(const SequencePtr& p) if(_stream) { - H << nl << _dllExport << "void ice_write" << p->name() << "(const ::Ice::OutputStreamPtr&, const " + H.zeroIndent(); + H << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + H.restoreIndent(); + H << nl << "//Stream api is not supported in VC++ 6"; + H.zeroIndent(); + H << nl << "#else"; + H.restoreIndent(); + H << nl << _dllExport << "ICE_DEPRECATED_API void ice_write" << p->name() << "(const ::Ice::OutputStreamPtr&, const " << typeName << "&);"; - H << nl << _dllExport << "void ice_read" << p->name() << "(const ::Ice::InputStreamPtr&, " << typeName + H << nl << _dllExport << "ICE_DEPRECATED_API void ice_read" << p->name() << "(const ::Ice::InputStreamPtr&, " << typeName << "&);"; + H.zeroIndent(); + H << nl << "#endif"; + H.restoreIndent(); } C << sp << nl << "void" << nl << scope.substr(2) << "__write" << name << @@ -1280,6 +1385,13 @@ Slice::Gen::TypesVisitor::visitSequence(const SequencePtr& p) if(_stream) { + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C << nl << "#else"; + C.restoreIndent(); C << sp << nl << "void" << nl << scope.substr(2) << "ice_write" << p->name() << "(const ::Ice::OutputStreamPtr& __outS, const " << scopedName << "& v)"; C << sb; @@ -1328,6 +1440,9 @@ Slice::Gen::TypesVisitor::visitSequence(const SequencePtr& p) C << eb; } C << eb; + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } } else if(!builtin || builtin->kind() == Builtin::KindObject || builtin->kind() == Builtin::KindObjectProxy) @@ -1338,10 +1453,20 @@ Slice::Gen::TypesVisitor::visitSequence(const SequencePtr& p) if(_stream) { - H << nl << _dllExport << "void ice_write" << p->name() << "(const ::Ice::OutputStreamPtr&, const " + H.zeroIndent(); + H << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + H.restoreIndent(); + H << nl << "//Stream api is not supported in VC++ 6"; + H.zeroIndent(); + H << nl << "#else"; + H.restoreIndent(); + H << nl << _dllExport << "ICE_DEPRECATED_API void ice_write" << p->name() << "(const ::Ice::OutputStreamPtr&, const " << name << "&);"; - H << nl << _dllExport << "void ice_read" << p->name() << "(const ::Ice::InputStreamPtr&, " << name + H << nl << _dllExport << "ICE_DEPRECATED_API void ice_read" << p->name() << "(const ::Ice::InputStreamPtr&, " << name << "&);"; + H.zeroIndent(); + H << nl << "#endif"; + H.restoreIndent(); } C << sp << nl << "void" << nl << scope.substr(2) << "__write" << name @@ -1404,6 +1529,13 @@ Slice::Gen::TypesVisitor::visitSequence(const SequencePtr& p) if(_stream) { + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C << nl << "#else"; + C.restoreIndent(); C << sp << nl << "void" << nl << scope.substr(2) << "ice_write" << p->name() << "(const ::Ice::OutputStreamPtr& __outS, const " << scoped << "& v)"; C << sb; @@ -1425,6 +1557,9 @@ Slice::Gen::TypesVisitor::visitSequence(const SequencePtr& p) writeStreamMarshalUnmarshalCode(C, type, "v[i]", false, "", _useWstring); C << eb; C << eb; + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } } } @@ -1470,9 +1605,19 @@ Slice::Gen::TypesVisitor::visitDictionary(const DictionaryPtr& p) if(_stream) { - H << nl << _dllExport << "void ice_write" << p->name() << "(const ::Ice::OutputStreamPtr&, const " << name + H.zeroIndent(); + H << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + H.restoreIndent(); + H << nl << "//Stream api is not supported in VC++ 6"; + H.zeroIndent(); + H << nl << "#else"; + H.restoreIndent(); + H << nl << _dllExport << "ICE_DEPRECATED_API void ice_write" << p->name() << "(const ::Ice::OutputStreamPtr&, const " << name << "&);"; - H << nl << _dllExport << "void ice_read" << p->name() << "(const ::Ice::InputStreamPtr&, " << name << "&);"; + H << nl << _dllExport << "ICE_DEPRECATED_API void ice_read" << p->name() << "(const ::Ice::InputStreamPtr&, " << name << "&);"; + H.zeroIndent(); + H << nl << "#endif"; + H.restoreIndent(); } C << sp << nl << "void" << nl << scope.substr(2) << "__write" << name @@ -1504,6 +1649,13 @@ Slice::Gen::TypesVisitor::visitDictionary(const DictionaryPtr& p) if(_stream) { + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C << nl << "#else"; + C.restoreIndent(); C << sp << nl << "void" << nl << scope.substr(2) << "ice_write" << p->name() << "(const ::Ice::OutputStreamPtr& __outS, const " << scoped << "& v)"; C << sb; @@ -1528,6 +1680,9 @@ Slice::Gen::TypesVisitor::visitDictionary(const DictionaryPtr& p) writeStreamMarshalUnmarshalCode(C, valueType, "__i->second", false, "", _useWstring, p->valueMetaData()); C << eb; C << eb; + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } } } @@ -1563,9 +1718,19 @@ Slice::Gen::TypesVisitor::visitEnum(const EnumPtr& p) if(_stream) { - H << sp << nl << _dllExport << "void ice_write" << p->name() + H.zeroIndent(); + H << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + H.restoreIndent(); + H << nl << "//Stream api is not supported in VC++ 6"; + H.zeroIndent(); + H.restoreIndent(); + H << nl << "#else"; + H << sp << nl << _dllExport << "ICE_DEPRECATED_API void ice_write" << p->name() << "(const ::Ice::OutputStreamPtr&, " << name << ");"; - H << nl << _dllExport << "void ice_read" << p->name() << "(const ::Ice::InputStreamPtr&, " << name << "&);"; + H << nl << _dllExport << "ICE_DEPRECATED_API void ice_read" << p->name() << "(const ::Ice::InputStreamPtr&, " << name << "&);"; + H.zeroIndent(); + H << nl << "#endif"; + H.restoreIndent(); } C << sp << nl << "void" << nl << scope.substr(2) << "__write(::IceInternal::BasicStream* __os, " << scoped @@ -1606,6 +1771,13 @@ Slice::Gen::TypesVisitor::visitEnum(const EnumPtr& p) if(_stream) { + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C.restoreIndent(); + C << nl << "#else"; C << sp << nl << "void" << nl << scope.substr(2) << "ice_write" << p->name() << "(const ::Ice::OutputStreamPtr& __outS, " << scoped << " v)"; C << sb; @@ -1658,6 +1830,9 @@ Slice::Gen::TypesVisitor::visitEnum(const EnumPtr& p) C << eb; C << nl << "v = static_cast< " << scoped << ">(val);"; C << eb; + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } } } @@ -3734,9 +3909,21 @@ Slice::Gen::ObjectVisitor::visitClassDefEnd(const ClassDefPtr& p) H << sp; H << nl << "virtual void __write(::IceInternal::BasicStream*) const;"; H << nl << "virtual void __read(::IceInternal::BasicStream*, bool);"; + + + H.zeroIndent(); + H << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + H.restoreIndent(); + H << nl << "//Stream api is not supported in VC++ 6"; + H.zeroIndent(); + H << nl << "#else"; + H.restoreIndent(); H << nl << "virtual void __write(const ::Ice::OutputStreamPtr&) const;"; H << nl << "virtual void __read(const ::Ice::InputStreamPtr&, bool);"; - + H.zeroIndent(); + H << nl << "#endif"; + H.restoreIndent(); + C << sp; C << nl << "void" << nl << scoped.substr(2) << "::__write(::IceInternal::BasicStream* __os) const"; @@ -3771,6 +3958,13 @@ Slice::Gen::ObjectVisitor::visitClassDefEnd(const ClassDefPtr& p) if(_stream) { + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C << nl << "#else"; + C.restoreIndent(); C << sp; C << nl << "void" << nl << scoped.substr(2) << "::__write(const ::Ice::OutputStreamPtr& __outS) const"; C << sb; @@ -3800,9 +3994,19 @@ Slice::Gen::ObjectVisitor::visitClassDefEnd(const ClassDefPtr& p) C << nl << "__inS->endSlice();"; emitUpcall(base, "::__read(__inS, true);"); C << eb; + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } else { + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C << nl << "#else"; + C.restoreIndent(); // // Emit placeholder functions to catch errors. // @@ -3820,6 +4024,9 @@ Slice::Gen::ObjectVisitor::visitClassDefEnd(const ClassDefPtr& p) C << nl << "ex.reason = \"type " << scoped.substr(2) << " was not generated with stream support\";"; C << nl << "throw ex;"; C << eb; + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } if(!p->isAbstract()) @@ -4739,15 +4946,25 @@ Slice::Gen::HandleVisitor::visitClassDecl(const ClassDeclPtr& p) H << nl << _dllExport << "void __patch__" << name << "Ptr(void*, ::Ice::ObjectPtr&);"; if(_stream) { + H.zeroIndent(); + H << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + H.restoreIndent(); + H << nl << "//Stream api is not supported in VC++ 6"; + H.zeroIndent(); + H << nl << "#else"; + H.restoreIndent(); H << sp; - H << nl << _dllExport << "void ice_write" << name << "Prx(const ::Ice::OutputStreamPtr&, const " << name + H << nl << _dllExport << "ICE_DEPRECATED_API void ice_write" << name << "Prx(const ::Ice::OutputStreamPtr&, const " << name << "Prx&);"; - H << nl << _dllExport << "void ice_read" << name << "Prx(const ::Ice::InputStreamPtr&, " << name + H << nl << _dllExport << "ICE_DEPRECATED_API void ice_read" << name << "Prx(const ::Ice::InputStreamPtr&, " << name << "Prx&);"; - H << nl << _dllExport << "void ice_write" << name << "(const ::Ice::OutputStreamPtr&, const " + H << nl << _dllExport << "ICE_DEPRECATED_API void ice_write" << name << "(const ::Ice::OutputStreamPtr&, const " << name << "Ptr&);"; - H << nl << _dllExport << "void ice_read" << name << "(const ::Ice::InputStreamPtr&, " << name << "Ptr&);"; + H << nl << _dllExport << "ICE_DEPRECATED_API void ice_read" << name << "(const ::Ice::InputStreamPtr&, " << name << "Ptr&);"; + H.zeroIndent(); + H << nl << "#endif"; + H.restoreIndent(); } } } @@ -4793,6 +5010,13 @@ Slice::Gen::HandleVisitor::visitClassDefStart(const ClassDefPtr& p) if(_stream) { + C.zeroIndent(); + C << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + C.restoreIndent(); + C << nl << "//Stream api is not supported in VC++ 6"; + C.zeroIndent(); + C << nl << "#else"; + C.restoreIndent(); C << sp; C << nl << "void" << nl << scope.substr(2) << "ice_write" << name << "Prx(const ::Ice::OutputStreamPtr& __outS, const " << scope << name << "Prx& v)"; @@ -4831,6 +5055,9 @@ Slice::Gen::HandleVisitor::visitClassDefStart(const ClassDefPtr& p) << name << "Ptr, &__v);"; C << nl << "__inS->readObject(__cb);"; C << eb; + C.zeroIndent(); + C << nl << "#endif"; + C.restoreIndent(); } } @@ -5757,6 +5984,95 @@ Slice::Gen::AsyncImplVisitor::visitOperation(const OperationPtr& p) } } +Slice::Gen::StreamVisitor::StreamVisitor(Output& h, Output& c) : + H(h), C(c) +{ + +} + +bool +Slice::Gen::StreamVisitor::visitModuleStart(const ModulePtr&) +{ + H.zeroIndent(); + H << nl << "#if defined(_MSC_VER) && (_MSC_VER < 1300) // VC++ 6 compiler bug"; // COMPILERBUG + H << nl << "#else"; + H.restoreIndent(); + H << nl << "namespace Ice" << sb; + return true; +} + +void +Slice::Gen::StreamVisitor::visitModuleEnd(const ModulePtr&) +{ + H << eb; + H << nl; + H.zeroIndent(); + H << nl << "#endif"; + H.restoreIndent(); +} + +bool +Slice::Gen::StreamVisitor::visitStructStart(const StructPtr& p) +{ + if(!p->isLocal()) + { + bool classMetaData = findMetaData(p->getMetaData(), false) == "class"; + string scoped = p->scoped(); + H << nl << sp << "template<>"; + if(classMetaData) + { + H << nl << "struct StreamTrait< " << fixKwd(scoped + "Ptr") << " >" << nl; + } + else + { + H << nl << "struct StreamTrait< " << fixKwd(scoped) << " >" << nl; + } + H << sb; + if(classMetaData) + { + H << nl << "static const ::Ice::StreamTraitType type = ::Ice::StreamTraitTypeStructClass;" << nl; + } + else + { + H << nl << "static const ::Ice::StreamTraitType type = ::Ice::StreamTraitTypeStruct;"; + } + H << nl << "static const int enumLimit = 0;"; + H << eb << ";" << nl; + } + return true; +} + +void +Slice::Gen::StreamVisitor::visitStructEnd(const StructPtr&) +{ +} + +void +Slice::Gen::StreamVisitor::visitEnum(const EnumPtr& p) +{ + string scoped = fixKwd(p->scoped()); + H << nl << sp << "template<>" << nl + << "struct StreamTrait< " << scoped << ">" << nl + << sb << nl + << "static const ::Ice::StreamTraitType type = "; + + size_t sz = p->getEnumerators().size(); + if(sz <= 127) + { + H << "::Ice::StreamTraitTypeByteEnum;"; + } + else if(sz <= 32767) + { + H << "::Ice::StreamTraitTypeShortEnum;"; + } + else + { + H << "::Ice::StreamTraitTypeIntEnum;"; + } + H << nl << "static const int enumLimit = " << sz << ";" + << eb << ";" << nl; +} + void Slice::Gen::validateMetaData(const UnitPtr& u) { diff --git a/cpp/src/slice2cpp/Gen.h b/cpp/src/slice2cpp/Gen.h index cca39fcdbc3..2a70c01c66f 100644 --- a/cpp/src/slice2cpp/Gen.h +++ b/cpp/src/slice2cpp/Gen.h @@ -387,6 +387,24 @@ private: bool _useWstring; std::list<bool> _useWstringHist; }; + + class StreamVisitor : private ::IceUtil::noncopyable, public ParserVisitor + { + public: + + StreamVisitor(::IceUtilInternal::Output&, ::IceUtilInternal::Output&); + + virtual bool visitModuleStart(const ModulePtr&); + virtual void visitModuleEnd(const ModulePtr&); + virtual bool visitStructStart(const StructPtr&); + virtual void visitStructEnd(const StructPtr&); + virtual void visitEnum(const EnumPtr&); + + private: + + ::IceUtilInternal::Output& H; + ::IceUtilInternal::Output& C; + }; private: diff --git a/cpp/test/Ice/objects/TestI.cpp b/cpp/test/Ice/objects/TestI.cpp index 51cab366ed7..30e1f0f2c14 100644 --- a/cpp/test/Ice/objects/TestI.cpp +++ b/cpp/test/Ice/objects/TestI.cpp @@ -231,7 +231,7 @@ UnexpectedObjectExceptionTestI::ice_invoke(const std::vector<Ice::Byte>&, Ice::CommunicatorPtr communicator = current.adapter->getCommunicator(); Ice::OutputStreamPtr out = Ice::createOutputStream(communicator); AlsoEmptyPtr ae = new AlsoEmpty; - ice_writeAlsoEmpty(out, ae); + out->write(ae); out->writePendingObjects(); out->finished(outParams); return true; diff --git a/cpp/test/Ice/stream/Client.cpp b/cpp/test/Ice/stream/Client.cpp index 5ea7856c6aa..3e0e5f6b663 100644 --- a/cpp/test/Ice/stream/Client.cpp +++ b/cpp/test/Ice/stream/Client.cpp @@ -11,6 +11,13 @@ #include <TestCommon.h> #include <Test.h> +// XXX: We disable deprecation warning here, to allow clean +// compilation of test cases that uses the old stream api. +// Once the old stream API is gone this could be removed. +#ifdef _MSC_VER +# pragma warning( disable : 4996 ) +#endif + using namespace std; class TestObjectWriter : public Ice::ObjectWriter @@ -146,6 +153,446 @@ run(int argc, char** argv, const Ice::CommunicatorPtr& communicator) Ice::OutputStreamPtr out; vector<Ice::Byte> data; +#if defined(_MSC_VER) && (_MSC_VER < 1300) +// +// VC++ 6 compiler bugs doesn't allow to write +// the Stream API using c++ templates. +// +// see: http://support.microsoft.com/kb/240866 +// http://support.microsoft.com/kb/241569 +// +#else + // + // Test the new stream api. + // + cout << "testing primitive types... " << flush; + + { + vector<Ice::Byte> byte; + in = Ice::createInputStream(communicator, byte); + } + + { + out = Ice::createOutputStream(communicator); + out->startEncapsulation(); + out->write(true); + out->endEncapsulation(); + out->finished(data); + out = 0; + + in = Ice::createInputStream(communicator, data); + in->startEncapsulation(); + bool v; + in->read(v); + test(v); + in->endEncapsulation(); + } + + { + vector<Ice::Byte> byte; + in = Ice::createInputStream(communicator, byte); + try + { + bool v; + in->read(v); + test(false); + } + catch(const Ice::UnmarshalOutOfBoundsException&) + { + } + } + + { + out = Ice::createOutputStream(communicator); + out->write(true); + out->finished(data); + in = Ice::createInputStream(communicator, data); + bool v; + in->read(v); + test(v); + } + + { + out = Ice::createOutputStream(communicator); + out->write((Ice::Byte)1); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Ice::Byte v; + in->read(v); + test(v == 1); + } + + { + out = Ice::createOutputStream(communicator); + out->write((Ice::Short)2); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Ice::Short v; + in->read(v); + test(v == 2); + } + + { + out = Ice::createOutputStream(communicator); + out->write((Ice::Int)3); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Ice::Int v; + in->read(v); + test(v == 3); + } + + { + out = Ice::createOutputStream(communicator); + out->write((Ice::Long)4); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Ice::Long v; + in->read(v); + test(v == 4); + } + + { + out = Ice::createOutputStream(communicator); + out->write((Ice::Float)5.0); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Ice::Float v; + in->read(v); + test(v == 5.0); + } + + { + out = Ice::createOutputStream(communicator); + out->write((Ice::Double)6.0); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Ice::Double v; + in->read(v); + test(v == 6.0); + } + + { + out = Ice::createOutputStream(communicator); + out->write("hello world"); + out->finished(data); + in = Ice::createInputStream(communicator, data); + string v; + in->read(v); + test(v == "hello world"); + } + + cout << "ok" << endl; + + cout << "testing constructed types... " << flush; + + { + out = Ice::createOutputStream(communicator); + out->write(Test::enum3); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Test::MyEnum e; + in->read(e); + test(e == Test::enum3); + } + + { + out = Ice::createOutputStream(communicator); + Test::SmallStruct s; + s.bo = true; + s.by = 1; + s.sh = 2; + s.i = 3; + s.l = 4; + s.f = 5.0; + s.d = 6.0; + s.str = "7"; + s.e = Test::enum2; + s.p = Test::MyClassPrx::uncheckedCast(communicator->stringToProxy("test:default")); + out->write(s); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Test::SmallStruct s2; + in->read(s2); + test(s2 == s); + } + + { + Test::BoolS arr; + arr.push_back(true); + arr.push_back(false); + arr.push_back(true); + arr.push_back(false); + + out = Ice::createOutputStream(communicator); + out->write(arr); + out->finished(data); + + in = Ice::createInputStream(communicator, data); + Test::BoolS arr2; + in->read(arr2); + test(arr2 == arr); + } + + { + Test::ByteS arr; + arr.push_back(0x01); + arr.push_back(0x11); + arr.push_back(0x12); + arr.push_back(0x22); + + out = Ice::createOutputStream(communicator); + out->write(arr); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Test::ByteS arr2; + in->read(arr2); + test(arr2 == arr); + } + + { + Test::ShortS arr; + arr.push_back(0x01); + arr.push_back(0x11); + arr.push_back(0x12); + arr.push_back(0x22); + out = Ice::createOutputStream(communicator); + out->write(arr); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Test::ShortS arr2; + in->read(arr2); + test(arr2 == arr); + } + + { + Test::IntS arr; + arr.push_back(0x01); + arr.push_back(0x11); + arr.push_back(0x12); + arr.push_back(0x22); + out = Ice::createOutputStream(communicator); + out->write(arr); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Test::IntS arr2; + in->read(arr2); + test(arr2 == arr); + } + + { + Test::LongS arr; + arr.push_back(0x01); + arr.push_back(0x11); + arr.push_back(0x12); + arr.push_back(0x22); + out = Ice::createOutputStream(communicator); + out->write(arr); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Test::LongS arr2; + in->read(arr2); + test(arr2 == arr); + } + + { + Test::FloatS arr; + arr.push_back(1); + arr.push_back(2); + arr.push_back(3); + arr.push_back(4); + out = Ice::createOutputStream(communicator); + out->write(arr); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Test::FloatS arr2; + in->read(arr2); + test(arr2 == arr); + } + + { + Test::DoubleS arr; + arr.push_back(1); + arr.push_back(2); + arr.push_back(3); + arr.push_back(4); + out = Ice::createOutputStream(communicator); + out->write(arr); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Test::DoubleS arr2; + in->read(arr2); + test(arr2 == arr); + } + + { + Test::StringS arr; + arr.push_back("string1"); + arr.push_back("string2"); + arr.push_back("string3"); + arr.push_back("string4"); + out = Ice::createOutputStream(communicator); + out->write(arr); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Test::StringS arr2; + in->read(arr2); + test(arr2 == arr); + } + + { + Test::MyEnumS arr; + arr.push_back(Test::enum3); + arr.push_back(Test::enum2); + arr.push_back(Test::enum1); + arr.push_back(Test::enum2); + + out = Ice::createOutputStream(communicator); + out->write(arr); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Test::MyEnumS arr2; + in->read(arr2); + test(arr2 == arr); + } + + { + Test::MyClassS arr; + for(int i = 0; i < 4; ++i) + { + Test::MyClassPtr c = new Test::MyClass; + c->c = c; + c->o = c; + c->s.e = Test::enum2; + + c->seq1.push_back(true); + c->seq1.push_back(false); + c->seq1.push_back(true); + c->seq1.push_back(false); + + c->seq2.push_back(1); + c->seq2.push_back(2); + c->seq2.push_back(3); + c->seq2.push_back(4); + + c->seq3.push_back(1); + c->seq3.push_back(2); + c->seq3.push_back(3); + c->seq3.push_back(4); + + c->seq4.push_back(1); + c->seq4.push_back(2); + c->seq4.push_back(3); + c->seq4.push_back(4); + + c->seq5.push_back(1); + c->seq5.push_back(2); + c->seq5.push_back(3); + c->seq5.push_back(4); + + c->seq6.push_back(1); + c->seq6.push_back(2); + c->seq6.push_back(3); + c->seq6.push_back(4); + + c->seq7.push_back(1); + c->seq7.push_back(2); + c->seq7.push_back(3); + c->seq7.push_back(4); + + c->seq8.push_back("string1"); + c->seq8.push_back("string2"); + c->seq8.push_back("string3"); + c->seq8.push_back("string4"); + + c->seq9.push_back(Test::enum3); + c->seq9.push_back(Test::enum2); + c->seq9.push_back(Test::enum1); + + c->d["hi"] = c; + } + out = Ice::createOutputStream(communicator); + out->write(arr); + out->writePendingObjects(); + out->finished(data); + in = Ice::createInputStream(communicator, data); + Test::MyClassS arr2; + in->read(arr2); + in->readPendingObjects(); + test(arr2.size() == arr.size()); + for(Test::MyClassS::size_type j = 0; j < arr2.size(); ++j) + { + test(arr2[j]); + test(arr2[j]->c == arr2[j]); + test(arr2[j]->o == arr2[j]); + test(arr2[j]->s.e == Test::enum2); + test(arr2[j]->seq1 == arr[j]->seq1); + test(arr2[j]->seq2 == arr[j]->seq2); + test(arr2[j]->seq3 == arr[j]->seq3); + test(arr2[j]->seq4 == arr[j]->seq4); + test(arr2[j]->seq5 == arr[j]->seq5); + test(arr2[j]->seq6 == arr[j]->seq6); + test(arr2[j]->seq7 == arr[j]->seq7); + test(arr2[j]->seq8 == arr[j]->seq8); + test(arr2[j]->seq9 == arr[j]->seq9); + test(arr2[j]->d["hi"] == arr2[j]); + } + } + + { + Test::MyInterfacePtr i = new Test::MyInterface(); + out = Ice::createOutputStream(communicator); + out->write(i); + out->writePendingObjects(); + out->finished(data); + in = Ice::createInputStream(communicator, data); + i = 0; + in->read(i); + in->readPendingObjects(); + test(i); + } + + { + out = Ice::createOutputStream(communicator); + Test::MyClassPtr obj = new Test::MyClass; + obj->s.e = Test::enum2; + TestObjectWriterPtr writer = new TestObjectWriter(obj); + out->writeObject(writer); + out->writePendingObjects(); + out->finished(data); + test(writer->called); + } + + { + out = Ice::createOutputStream(communicator); + Test::MyClassPtr obj = new Test::MyClass; + obj->s.e = Test::enum2; + TestObjectWriterPtr writer = new TestObjectWriter(obj); + out->writeObject(writer); + out->writePendingObjects(); + out->finished(data); + test(writer->called); + factoryWrapper->setFactory(new TestObjectFactory); + in = Ice::createInputStream(communicator, data); + TestReadObjectCallbackPtr cb = new TestReadObjectCallback; + in->readObject(cb); + in->readPendingObjects(); + test(cb->obj); + TestObjectReaderPtr reader = TestObjectReaderPtr::dynamicCast(cb->obj); + test(reader); + test(reader->called); + test(reader->obj); + test(reader->obj->s.e == Test::enum2); + } + + cout << "ok" << endl; + +#endif + + // + // Test the old stream api. + // + cout << "testing primitive types... " << flush; { |