diff options
-rw-r--r-- | cpp/demo/Ice/value/Client.cpp | 47 | ||||
-rw-r--r-- | cpp/demo/Ice/value/Value.ice | 1 | ||||
-rw-r--r-- | cpp/demo/Ice/value/ValueI.cpp | 6 | ||||
-rw-r--r-- | cpp/demo/Ice/value/ValueI.h | 1 | ||||
-rw-r--r-- | cpp/include/Slice/Parser.h | 10 | ||||
-rw-r--r-- | cpp/src/Slice/JavaUtil.cpp | 21 | ||||
-rw-r--r-- | cpp/src/Slice/Parser.cpp | 76 | ||||
-rw-r--r-- | cpp/src/slice2cpp/Gen.cpp | 7 | ||||
-rw-r--r-- | cpp/src/slice2java/Gen.cpp | 180 | ||||
-rw-r--r-- | java/demo/Ice/value/Client.java | 46 | ||||
-rw-r--r-- | java/demo/Ice/value/InitialI.java | 6 | ||||
-rw-r--r-- | java/demo/Ice/value/Value.ice | 1 | ||||
-rw-r--r-- | java/src/Ice/ObjectHolder.java | 6 | ||||
-rw-r--r-- | java/src/Ice/ObjectImpl.java | 8 | ||||
-rw-r--r-- | java/src/IceInternal/BasicStream.java | 6 | ||||
-rw-r--r-- | java/src/IceInternal/Patcher.java | 3 |
16 files changed, 302 insertions, 123 deletions
diff --git a/cpp/demo/Ice/value/Client.cpp b/cpp/demo/Ice/value/Client.cpp index 408d810a2c1..4626a5e7690 100644 --- a/cpp/demo/Ice/value/Client.cpp +++ b/cpp/demo/Ice/value/Client.cpp @@ -52,13 +52,25 @@ run(int argc, char* argv[], const Ice::CommunicatorPtr& communicator) cout << '\n' << "Ok, this worked. Now let's try to transfer an object for a class\n" - << "with operations, without installing a factory first. This should\n" - << "give us a `no factory' exception.\n" + << "with operations as type ::Ice::Object. Because no factory is installed,\n" + << "the class will be sliced to ::Ice::Object.\n" + << "[press enter]\n"; + cin.getline(&c, 1); + + ::Ice::ObjectPtr obj = initial->getPrinterAsObject(); + cout << "==> The type ID of the received object is \"" << obj->ice_id() << "\"" << endl; + assert(obj->ice_id() == "::Ice::Object"); + + cout << '\n' + << "Yes, this worked. Now let's try to transfer an object for a class\n" + << "with operations as type ::Printer, without installing a factory first.\n" + << "This should give us a `no factory' exception.\n" << "[press enter]\n"; cin.getline(&c, 1); PrinterPtr printer; PrinterPrx printerProxy; + bool gotException = false; try { initial->getPrinter(printer, printerProxy); @@ -66,7 +78,9 @@ run(int argc, char* argv[], const Ice::CommunicatorPtr& communicator) catch(const Ice::NoObjectFactoryException& ex) { cout << "==> " << ex << endl; + gotException = true; } + assert(gotException); cout << '\n' << "Yep, that's what we expected. Now let's try again, but with\n" @@ -99,28 +113,22 @@ run(int argc, char* argv[], const Ice::CommunicatorPtr& communicator) printerProxy->printBackwards(); cout << '\n' - << "Next, we transfer a derived object from the server as base\n" - << "object. Since we didn't install a factory for the derived\n" - << "class yet, we will get another `no factory' exception.\n" + << "Next, we transfer a derived object from the server as a base\n" + << "object. Since we haven't yet installed a factory for the derived\n" + << "class, the derived class (::DerivedPrinter) is sliced\n" + << "to its base class (::Printer).\n" << "[press enter]\n"; cin.getline(&c, 1); PrinterPtr derivedAsBase; - try - { - derivedAsBase = initial->getDerivedPrinter(); - assert(false); - } - catch(const Ice::NoObjectFactoryException& ex) - { - cout << "==> " << ex << endl; - } + derivedAsBase = initial->getDerivedPrinter(); + cout << "==> The type ID of the received object is \"" << derivedAsBase->ice_id() << "\"" << endl; + assert(derivedAsBase->ice_id() == "::Printer"); cout << '\n' << "Now we install a factory for the derived class, and try again.\n" - << "We won't get a `no factory' exception anymore, but since we\n" - << "receive the derived object as base object, we need to do a\n" - << "dynamic_cast<> to get from the base to the derived object.\n" + << "Because we receive the derived object as a base object, we\n" + << "we need to do a dynamic_cast<> to get from the base to the derived object.\n" << "[press enter]\n"; cin.getline(&c, 1); @@ -129,8 +137,8 @@ run(int argc, char* argv[], const Ice::CommunicatorPtr& communicator) derivedAsBase = initial->getDerivedPrinter(); DerivedPrinterPtr derived = DerivedPrinterPtr::dynamicCast(derivedAsBase); assert(derived); - cout << "==> dynamic_cast<> to derived object succeded" << endl; + cout << "==> The type ID of the received object is \"" << derived->ice_id() << "\"" << endl; cout << '\n' << "Let's print the message contained in the derived object, and\n" @@ -150,6 +158,7 @@ run(int argc, char* argv[], const Ice::CommunicatorPtr& communicator) << "[press enter]\n"; cin.getline(&c, 1); + gotException = false; try { initial->throwDerivedPrinter(); @@ -158,7 +167,9 @@ run(int argc, char* argv[], const Ice::CommunicatorPtr& communicator) { derived = ex.derived; assert(derived); + gotException = true; } + assert(gotException); cout << "==> " << derived->derivedMessage << endl; cout << "==> "; diff --git a/cpp/demo/Ice/value/Value.ice b/cpp/demo/Ice/value/Value.ice index 3ef695aff55..4a69d6b6a7d 100644 --- a/cpp/demo/Ice/value/Value.ice +++ b/cpp/demo/Ice/value/Value.ice @@ -40,6 +40,7 @@ exception DerivedPrinterException class Initial { Simple getSimple(); + Object getPrinterAsObject(); void getPrinter(out Printer impl, out Printer* proxy); Printer getDerivedPrinter(); void throwDerivedPrinter() throws DerivedPrinterException; diff --git a/cpp/demo/Ice/value/ValueI.cpp b/cpp/demo/Ice/value/ValueI.cpp index fdb34fae120..9c096219ae5 100644 --- a/cpp/demo/Ice/value/ValueI.cpp +++ b/cpp/demo/Ice/value/ValueI.cpp @@ -39,6 +39,12 @@ InitialI::getSimple(const Ice::Current&) return _simple; } +::Ice::ObjectPtr +InitialI::getPrinterAsObject(const Ice::Current&) +{ + return _printer; +} + void InitialI::getPrinter(PrinterPtr& impl, PrinterPrx& proxy, const Ice::Current&) { diff --git a/cpp/demo/Ice/value/ValueI.h b/cpp/demo/Ice/value/ValueI.h index 8e1c811537f..67f2d9ae701 100644 --- a/cpp/demo/Ice/value/ValueI.h +++ b/cpp/demo/Ice/value/ValueI.h @@ -24,6 +24,7 @@ public: InitialI(const Ice::ObjectAdapterPtr&); virtual SimplePtr getSimple(const Ice::Current&); + virtual ::Ice::ObjectPtr getPrinterAsObject(const Ice::Current&); virtual void getPrinter(PrinterPtr&, PrinterPrx&, const Ice::Current&); virtual PrinterPtr getDerivedPrinter(const Ice::Current&); virtual void throwDerivedPrinter(const Ice::Current&); diff --git a/cpp/include/Slice/Parser.h b/cpp/include/Slice/Parser.h index db6835e227f..0ab0eed528f 100644 --- a/cpp/include/Slice/Parser.h +++ b/cpp/include/Slice/Parser.h @@ -236,6 +236,7 @@ class SLICE_API Type : virtual public SyntaxTreeBase public: virtual bool isLocal() const = 0; + virtual std::string typeId() const = 0; virtual bool usesClasses() const = 0; protected: @@ -267,6 +268,7 @@ public: }; virtual bool isLocal() const; + virtual std::string typeId() const; virtual bool usesClasses() const; Kind kind() const; @@ -426,7 +428,8 @@ class SLICE_API Constructed : virtual public Type, virtual public Contained { public: - bool isLocal() const; + virtual bool isLocal() const; + virtual std::string typeId() const; ConstructedList dependencies(); virtual void recDependencies(std::set<ConstructedPtr>&) = 0; // Internal operation, don't use directly. @@ -548,7 +551,7 @@ public: DataMemberList allClassDataMembers() const; bool isAbstract() const; bool isInterface() const; - bool isLocal() const; + virtual bool isLocal() const; bool hasDataMembers() const; virtual ContainedType containedType() const; virtual bool uses(const ContainedPtr&) const; @@ -576,6 +579,7 @@ class SLICE_API Proxy : virtual public Type public: virtual bool isLocal() const; + virtual std::string typeId() const; virtual bool usesClasses() const; ClassDeclPtr _class() const; @@ -603,7 +607,7 @@ public: DataMemberList allClassDataMembers() const; ExceptionPtr base() const; ExceptionList allBases() const; - bool isLocal() const; + virtual bool isLocal() const; virtual ContainedType containedType() const; virtual bool uses(const ContainedPtr&) const; bool usesClasses() const; diff --git a/cpp/src/Slice/JavaUtil.cpp b/cpp/src/Slice/JavaUtil.cpp index 8986ff98b3c..a5b55146e1f 100644 --- a/cpp/src/Slice/JavaUtil.cpp +++ b/cpp/src/Slice/JavaUtil.cpp @@ -990,10 +990,25 @@ Slice::JavaGenerator::writeSequenceMarshalUnmarshalCode(Output& out, out << nl << "for(int __i" << iter << " = 0; __i" << iter << " < __len" << iter << "; __i" << iter << "++)"; out << sb; - out << nl << origContentS << " __elem;"; + BuiltinPtr builtin = BuiltinPtr::dynamicCast(origContent); + if((builtin && builtin->kind() == Builtin::KindObject) || ClassDeclPtr::dynamicCast(origContent)) + { + out << nl << v << ".add(null);"; + ostringstream patchParams; + patchParams << v << ", __i" << iter; + writeMarshalUnmarshalCode(out, scope, seq->type(), "__elem", false, iter, false, + list<string>(), patchParams.str()); + } + else + { + out << nl << origContentS << " __elem;"; + writeMarshalUnmarshalCode(out, scope, seq->type(), "__elem", false, iter, false); + } iter++; - writeMarshalUnmarshalCode(out, scope, seq->type(), "__elem", false, iter, false); - out << nl << v << ".add(__elem);"; + if((builtin && builtin->kind() != Builtin::KindObject) && !ClassDeclPtr::dynamicCast(origContent)) + { + out << nl << v << ".add(__elem);"; + } out << eb; } } diff --git a/cpp/src/Slice/Parser.cpp b/cpp/src/Slice/Parser.cpp index 869b9ba115f..f04292a71d5 100644 --- a/cpp/src/Slice/Parser.cpp +++ b/cpp/src/Slice/Parser.cpp @@ -84,6 +84,70 @@ Slice::Builtin::isLocal() const return _kind == KindLocalObject; } +string +Slice::Builtin::typeId() const +{ + switch(_kind) + { + case KindByte: + { + return "::Ice::Byte"; + break; + } + case KindBool: + { + return "::Ice::Bool"; + break; + } + case KindShort: + { + return "::Ice::Short"; + break; + } + case KindInt: + { + return "::Ice::Int"; + break; + } + case KindLong: + { + return "::Ice::Long"; + break; + } + case KindFloat: + { + return "::Ice::Float"; + break; + } + case KindDouble: + { + return "::Ice::Double"; + break; + } + case KindString: + { + return "::Ice::String"; + break; + } + case KindObject: + { + return "::Ice::Object"; + break; + } + case KindObjectProxy: + { + return "::Ice::Object*"; + break; + } + case KindLocalObject: + { + return "::Ice::LocalObject"; + break; + } + } + assert(false); +} + bool Slice::Builtin::usesClasses() const { @@ -1612,6 +1676,12 @@ Slice::Constructed::isLocal() const return _local; } +string +Slice::Constructed::typeId() const +{ + return scoped(); +} + ConstructedList Slice::Constructed::dependencies() { @@ -2395,6 +2465,12 @@ Slice::Proxy::isLocal() const return __class->isLocal(); } +string +Slice::Proxy::typeId() const +{ + return __class->scoped(); +} + bool Slice::Proxy::usesClasses() const { diff --git a/cpp/src/slice2cpp/Gen.cpp b/cpp/src/slice2cpp/Gen.cpp index 6a5de35ff21..97aebb857a4 100644 --- a/cpp/src/slice2cpp/Gen.cpp +++ b/cpp/src/slice2cpp/Gen.cpp @@ -2446,7 +2446,12 @@ Slice::Gen::ObjectVisitor::visitClassDefEnd(const ClassDefPtr& p) C << nl << scope << name << "Ptr* p = static_cast< " << scope << name << "Ptr*>(__addr);"; C << nl << "assert(p);"; C << nl << "*p = " << scope << name << "Ptr::dynamicCast(v);"; - C << nl << "assert(!v || *p);"; + C << nl << "if(v && !*p)"; + C << sb; + C << nl << "::Ice::NoObjectFactoryException e(__FILE__, __LINE__);"; + C << nl << "e.type = " << scope << name << "::ice_staticId();"; + C << nl << "throw e;"; + C << eb; C << eb; C << sp; diff --git a/cpp/src/slice2java/Gen.cpp b/cpp/src/slice2java/Gen.cpp index 88295a2bd1e..671e852fa03 100644 --- a/cpp/src/slice2java/Gen.cpp +++ b/cpp/src/slice2java/Gen.cpp @@ -1227,59 +1227,6 @@ Slice::Gen::TypesVisitor::visitClassDefStart(const ClassDefPtr& p) out << sb; -#if 0 - // - // hashCode - // - if(!p->isInterface()) - { - // - // Does the class have (or inherit) any data members? - // - bool baseHasDataMembers = false; - ClassList l = p->bases(); - while(!l.empty() && !l.front()->isInterface()) - { - if(l.front()->hasDataMembers()) - { - baseHasDataMembers = true; - break; - } - l = l.front()->bases(); - } - - if(p->hasDataMembers() || baseHasDataMembers) - { - out << sp << nl << "public int" << nl << "hashCode()"; - out << sb; - if(p->hasDataMembers()) - { - DataMemberList members = p->dataMembers(); - DataMemberList::const_iterator d; - - out << nl << "int __h = 0;"; - int iter = 0; - for(d = members.begin(); d != members.end(); ++d) - { - string memberName = fixKwd((*d)->name()); - list<string> metaData = (*d)->getMetaData(); - writeHashCode(out, (*d)->type(), memberName, iter, metaData); - } - if(baseHasDataMembers) - { - out << nl << "__h = 5 * __h + super.hashCode();"; - } - out << nl << "return __h;"; - } - else - { - out << nl << "return super.hashCode();"; - } - out << eb; - } - } -#endif - // // Default factory for non-abstract classes. // @@ -1359,6 +1306,10 @@ Slice::Gen::TypesVisitor::visitClassDefStart(const ClassDefPtr& p) out << nl << "case " << memberCount << ":"; out.inc(); } + if(allClassMembers.size() > 1) + { + out << nl << "__typeId = \"" << (*d)->type()->typeId() << "\";"; + } string memberName = fixKwd((*d)->name()); string memberScope = fixKwd((*d)->scope()); string memberType = typeToString((*d)->type(), TypeModeMember, memberScope); @@ -1374,9 +1325,23 @@ Slice::Gen::TypesVisitor::visitClassDefStart(const ClassDefPtr& p) out << eb; } out << eb; + + out << sp << nl << "public String" << nl << "type()"; + out << sb; if(allClassMembers.size() > 1) { - out << nl << nl << "private int __member;"; + out << nl << "return __typeId;"; + } + else + { + out << nl << "return \"" << (*allClassMembers.begin())->type()->typeId() << "\";"; + } + out << eb; + + if(allClassMembers.size() > 1) + { + out << sp << nl << "private int __member;"; + out << nl << "private String __typeId;"; } out << eb; } @@ -1561,6 +1526,10 @@ Slice::Gen::TypesVisitor::visitExceptionEnd(const ExceptionPtr& p) out << nl << "case " << memberCount << ":"; out.inc(); } + if(allClassMembers.size() > 1) + { + out << nl << "__typeId = \"" << (*d)->type()->typeId() << "\";"; + } string memberName = fixKwd((*d)->name()); string memberScope = fixKwd((*d)->scope()); string memberType = typeToString((*d)->type(), TypeModeMember, memberScope); @@ -1576,9 +1545,22 @@ Slice::Gen::TypesVisitor::visitExceptionEnd(const ExceptionPtr& p) out << eb; } out << eb; + + out << sp << nl << "public String" << nl << "type()"; + out << sb; + if(allClassMembers.size() > 1) + { + out << nl << "return __typeId;"; + } + else + { + out << nl << "return \"" << (*allClassMembers.begin())->type()->typeId() << "\";"; + } + out << eb; if(allClassMembers.size() > 1) { - out << nl << nl << "private int __member;"; + out << sp << nl << "private int __member;"; + out << nl << "private String __typeId;"; } out << eb; } @@ -1862,6 +1844,10 @@ Slice::Gen::TypesVisitor::visitStructEnd(const StructPtr& p) out << nl << "case " << memberCount << ":"; out.inc(); } + if(classMembers.size() > 1) + { + out << nl << "__typeId = \"" << (*d)->type()->typeId() << "\";"; + } string memberName = fixKwd((*d)->name()); string memberScope = fixKwd((*d)->scope()); string memberType = typeToString((*d)->type(), TypeModeMember, memberScope); @@ -1877,9 +1863,23 @@ Slice::Gen::TypesVisitor::visitStructEnd(const StructPtr& p) out << eb; } out << eb; + + out << sp << nl << "public String" << nl << "type()"; + out << sb; + if(classMembers.size() > 1) + { + out << nl << "return __typeId;"; + } + else + { + out << nl << "return \"" << (*classMembers.begin())->type()->typeId() << "\";"; + } + out << eb; + if(classMembers.size() > 1) { - out << nl << nl << "private int __member;"; + out << sp << nl << "private int __member;"; + out << nl << "private String __typeId;"; } out << eb; } @@ -2265,23 +2265,31 @@ Slice::Gen::HolderVisitor::writeHolder(const TypePtr& p) out << sb; out << nl << "this.value = value;"; out << eb; - BuiltinPtr builtin = BuiltinPtr::dynamicCast(p); - if((builtin && builtin->kind() == Builtin::KindObject) || ClassDeclPtr::dynamicCast(p)) + if(!p->isLocal()) { - out << sp << nl << "public class Patcher implements IceInternal.Patcher"; - out << sb; - out << nl << "public void"; - out << nl << "patch(Ice.Object v)"; - out << sb; - out << nl << "value = (" << typeS << ")v;"; - out << eb; - out << eb; + BuiltinPtr builtin = BuiltinPtr::dynamicCast(p); + if((builtin && builtin->kind() == Builtin::KindObject) || ClassDeclPtr::dynamicCast(p)) + { + out << sp << nl << "public class Patcher implements IceInternal.Patcher"; + out << sb; + out << nl << "public void"; + out << nl << "patch(Ice.Object v)"; + out << sb; + out << nl << "value = (" << typeS << ")v;"; + out << eb; - out << sp << nl << "public Patcher"; - out << nl << "getPatcher()"; - out << sb; - out << nl << "return new Patcher();"; - out << eb; + out << sp << nl << "public String" << nl << "type()"; + out << sb; + out << nl << "return \"" << p->typeId() << "\";"; + out << eb; + out << eb; + + out << sp << nl << "public Patcher"; + out << nl << "getPatcher()"; + out << sb; + out << nl << "return new Patcher();"; + out << eb; + } } out << sp << nl << "public " << typeS << " value;"; out << eb; @@ -2611,9 +2619,12 @@ Slice::Gen::HelperVisitor::visitSequence(const SequencePtr& p) // // The sequence has class elements. // + string metaData = findMetaData(p->getMetaData()); + string listType = metaData.empty() ? typeS : "java.util.List"; + out << sp << nl << "private static class Patcher implements IceInternal.Patcher"; out << sb; - out << sp << nl << "Patcher(" << typeS << " values, int index)"; + out << sp << nl << "Patcher(" << listType << " values, int index)"; out << sb; out << nl << "__values = values;"; out << nl << "__index = index;"; @@ -2621,10 +2632,23 @@ Slice::Gen::HelperVisitor::visitSequence(const SequencePtr& p) out << sp << nl << "public void" << nl << "patch(Ice.Object v)"; out << sb; - out << nl << "__values[__index] = (" << typeToString(p->type(), TypeModeIn, scope) << ")v;"; + string elmtType = typeToString(p->type(), TypeModeIn, scope); + if(metaData.empty()) + { + out << nl << "__values[__index] = (" << elmtType << ")v;"; + } + else + { + out << nl << "__values.set(__index, (" << elmtType << ")v);"; + } out << eb; - out << sp << nl << "private " << typeS << " __values;"; + out << sp << nl << "public String" << nl << "type()"; + out << sb; + out << nl << "return \"" << p->type()->typeId() << "\";"; + out << eb; + + out << sp << nl << "private " << listType << " __values;"; out << nl << "private int __index;"; out << eb; } @@ -2633,7 +2657,7 @@ Slice::Gen::HelperVisitor::visitSequence(const SequencePtr& p) out << sb; out << nl << typeS << " __v;"; iter = 0; - writeSequenceMarshalUnmarshalCode(out, scope, p, "__v", false, iter, false); + writeSequenceMarshalUnmarshalCode(out, scope, p, "__v", false, iter, false); out << nl << "return __v;"; out << eb; @@ -2844,9 +2868,15 @@ Slice::Gen::HelperVisitor::visitDictionary(const DictionaryPtr& p) out << sp << nl << "public void" << nl << "patch(Ice.Object v)"; out << sb; + out << nl << valueS << " _v = (" << valueS << ")v;"; out << nl << "__m.put(__key, v);"; out << eb; + out << sp << nl << "public String" << nl << "type()"; + out << sb; + out << nl << "return \"" << value->typeId() << "\";"; + out << eb; + out << sp << nl << "private java.util.Map __m;"; out << nl << "private " << keyTypeS << " __key;"; out << eb; diff --git a/java/demo/Ice/value/Client.java b/java/demo/Ice/value/Client.java index bf1a2711cd2..9058936804f 100644 --- a/java/demo/Ice/value/Client.java +++ b/java/demo/Ice/value/Client.java @@ -61,13 +61,25 @@ public class Client System.out.println(); System.out.println("Ok, this worked. Now let's try to transfer an object for a class"); - System.out.println("with operations, without installing a factory first. This should"); - System.out.println("give us a `no factory' exception."); + System.out.println("with operations as type Ice.Object. Because no factory is installed,"); + System.out.println("the class will be sliced to Ice.Object."); + System.out.println("[press enter]"); + readline(in); + + Ice.Object obj = initial.getPrinterAsObject(); + System.out.println("The type ID of the received object is \"" + obj.ice_id(null) + "\""); + assert(obj.ice_id(null).equals("::Ice::Object")); + + System.out.println(); + System.out.println("Yes, this worked. Now let's try to transfer an object for a class"); + System.out.println("with operations as type Printer, without installing a factory first."); + System.out.println("This should give us a `no factory' exception."); System.out.println("[press enter]"); readline(in); PrinterHolder printer = new PrinterHolder(); PrinterPrxHolder printerProxy = new PrinterPrxHolder(); + boolean gotException = false; try { initial.getPrinter(printer, printerProxy); @@ -75,7 +87,9 @@ public class Client catch(Ice.NoObjectFactoryException ex) { System.out.println("==> " + ex); + gotException = true; } + assert(gotException); System.out.println(); System.out.println("Yep, that's what we expected. Now let's try again, but with"); @@ -102,34 +116,27 @@ public class Client System.out.println(); System.out.println("Now we call the same method, but on the remote object. Watch the"); System.out.println("server's output."); - System.out.println("[press enter]"); + System.out.println("press enter]"); readline(in); printerProxy.value.printBackwards(); System.out.println(); System.out.println("Next, we transfer a derived object from the server as base"); - System.out.println("object. Since we didn't install a factory for the derived"); - System.out.println("class yet, we will get another `no factory' exception."); + System.out.println("object. Since we haven't yet installed a factory for the derived"); + System.out.println("class, the derived class (DerivedPrinter) is sliced"); + System.out.println("to its base class (Printer)."); System.out.println("[press enter]"); readline(in); - Printer derivedAsBase; - try - { - derivedAsBase = initial.getDerivedPrinter(); - assert(false); - } - catch(Ice.NoObjectFactoryException ex) - { - System.out.println("==> " + ex); - } + Printer derivedAsBase = initial.getDerivedPrinter(); + System.out.println("The type ID of the received object is \"" + derivedAsBase.ice_id(null) + "\""); + assert(derivedAsBase.ice_id(null).equals("::Printer")); System.out.println(); System.out.println("Now we install a factory for the derived class, and try again."); - System.out.println("We won't get a `no factory' exception anymore, but since we"); - System.out.println("receive the derived object as base object, we need to do a"); - System.out.println("dynamic_cast<> to get from the base to the derived object."); + System.out.println("Because we receive the derived object as base object,"); + System.out.println("we need to do a class cast to get from the base to the derived object."); System.out.println("[press enter]"); readline(in); @@ -138,7 +145,8 @@ public class Client derivedAsBase = initial.getDerivedPrinter(); DerivedPrinter derived = (DerivedPrinter)derivedAsBase; - System.out.println("==> dynamic_cast<> to derived object succeded"); + System.out.println("==> class cast to derived object succeded"); + System.out.println("The type ID of the received object is \"" + derived.ice_id(null) + "\""); System.out.println(); System.out.println("Let's print the message contained in the derived object, and"); diff --git a/java/demo/Ice/value/InitialI.java b/java/demo/Ice/value/InitialI.java index 2919ec10b64..a7a64a2660d 100644 --- a/java/demo/Ice/value/InitialI.java +++ b/java/demo/Ice/value/InitialI.java @@ -37,6 +37,12 @@ class InitialI extends Initial return _simple; } + public Ice.Object + getPrinterAsObject(Ice.Current current) + { + return _printer; + } + public void getPrinter(PrinterHolder impl, PrinterPrxHolder proxy, Ice.Current current) { diff --git a/java/demo/Ice/value/Value.ice b/java/demo/Ice/value/Value.ice index 3ef695aff55..4a69d6b6a7d 100644 --- a/java/demo/Ice/value/Value.ice +++ b/java/demo/Ice/value/Value.ice @@ -40,6 +40,7 @@ exception DerivedPrinterException class Initial { Simple getSimple(); + Object getPrinterAsObject(); void getPrinter(out Printer impl, out Printer* proxy); Printer getDerivedPrinter(); void throwDerivedPrinter() throws DerivedPrinterException; diff --git a/java/src/Ice/ObjectHolder.java b/java/src/Ice/ObjectHolder.java index 9d1ad91e088..5d88becf0b9 100644 --- a/java/src/Ice/ObjectHolder.java +++ b/java/src/Ice/ObjectHolder.java @@ -34,6 +34,12 @@ public final class ObjectHolder { value = v; } + + public String + type() + { + return Ice.ObjectImpl.ice_staticId(); + } } public Patcher diff --git a/java/src/Ice/ObjectImpl.java b/java/src/Ice/ObjectImpl.java index 551ae4de307..eec827b0217 100644 --- a/java/src/Ice/ObjectImpl.java +++ b/java/src/Ice/ObjectImpl.java @@ -198,7 +198,7 @@ public class ObjectImpl implements Object, java.lang.Cloneable { synchronized(_activeFacetMap) { - __os.writeTypeId("::Ice::Object"); + __os.writeTypeId(ice_staticId()); __os.startWriteSlice(); final int sz = _activeFacetMap.size(); __os.writeSize(sz); @@ -228,6 +228,12 @@ public class ObjectImpl implements Object, java.lang.Cloneable _activeFacetMap.put(__key, v); } + public String + type() + { + return ice_staticId(); + } + private String __key; } diff --git a/java/src/IceInternal/BasicStream.java b/java/src/IceInternal/BasicStream.java index c157d980dae..09e68ff2f9a 100644 --- a/java/src/IceInternal/BasicStream.java +++ b/java/src/IceInternal/BasicStream.java @@ -1116,7 +1116,7 @@ public class BasicStream while(true) { String id = readTypeId(); - if(id.equals("::Ice::Object")) + if(id.equals(Ice.ObjectImpl.ice_staticId())) { v = new Ice.ObjectImpl(); } @@ -1323,7 +1323,9 @@ public class BasicStream } catch(ClassCastException ex) { - throw new Ice.UnmarshalOutOfBoundsException(); + Ice.NoObjectFactoryException nof = new Ice.NoObjectFactoryException(); + nof.type = p.type(); + throw nof; } } diff --git a/java/src/IceInternal/Patcher.java b/java/src/IceInternal/Patcher.java index 11fdbf06adb..b5e30377bd0 100644 --- a/java/src/IceInternal/Patcher.java +++ b/java/src/IceInternal/Patcher.java @@ -17,4 +17,5 @@ package IceInternal; public interface Patcher { void patch(Ice.Object v); -}; + String type(); +} |