Discussion:
Using different incompatible versions of a CORBA Interface in the same C++ app/module?
(too old to reply)
Martin B.
2011-03-04 10:06:08 UTC
Permalink
Maybe someone here can help:

Original question see: http://stackoverflow.com/q/5178031/321013

Given two IDL definitions: (I'm only implementing a client, the server
side is fixed.)

// Version 1.2
module Server {
interface IObject {
void Foo1();
void Foo2() raises(EFail);
string Foo3();
// ...
}
};

// Version 2.3
module Server {
interface IObject {
// no longer available: void Foo1();
void Foo2(string x) raises(ENotFound, EFail); // incompatible
change
wstring Foo3();
// ...
}
};

Is it somehow possible to compile both stub code files in the same C++
CORBA Client App?

Using the defaults of an IDL compiler, the above two IDL definitions
will result in stub code that cannot be compiled into the same C++
module, as you'd get multiple definition errors from the linker. The
client however needs to be able to talk to both server versions.

What are possible solutions?

(Note: We're using http://omniorb.sourceforge.net/)

cheers,
Martin
Raghu V. Hudli
2011-03-07 03:06:53 UTC
Permalink
Unfortunately, CORBA IDL does not support versioning of interfaces. You
will need to resort to using distinct interface names; 3 common
approaches people use are:
1. create new versions in a new module: Ex: Server1.2, Server2.3, etc.

2. use inheritance (with distinct subtype names; IObject1_2, IOject2_3
inheriting from IObject1_2) But when you
want to take remove methods, the implementation gets into ugly NO-OP
implementation)

3: Just use different and unrelated interfaces to represent
different versions

Unfortunately, there is no clean way of using versions of interfaces in
CORBA. If it is any consolation, Java, C++ and a other languages have
the same problem. COM and erstwhile SOM from IBM had native support for
interface versions.

Raghu
Post by Martin B.
Original question see: http://stackoverflow.com/q/5178031/321013
Given two IDL definitions: (I'm only implementing a client, the server
side is fixed.)
// Version 1.2
module Server {
interface IObject {
void Foo1();
void Foo2() raises(EFail);
string Foo3();
// ...
}
};
// Version 2.3
module Server {
interface IObject {
// no longer available: void Foo1();
void Foo2(string x) raises(ENotFound, EFail); // incompatible change
wstring Foo3();
// ...
}
};
Is it somehow possible to compile both stub code files in the same C++
CORBA Client App?
Using the defaults of an IDL compiler, the above two IDL definitions
will result in stub code that cannot be compiled into the same C++
module, as you'd get multiple definition errors from the linker. The
client however needs to be able to talk to both server versions.
What are possible solutions?
(Note: We're using http://omniorb.sourceforge.net/)
cheers,
Martin
Martin B.
2011-03-07 08:09:41 UTC
Permalink
I know the problems versioning poses.

The problem I face atm. is that we have two conflicting server side
IDLs, *that cannot be changed* because I just have to implement a C++
client to these 3rd party servers. And the problem now is how to prevent
C++ Linker errors when including both different stub headers (but with
the identically named module+interface) into a C++ process.

cheers,
Martin
Post by Raghu V. Hudli
Unfortunately, CORBA IDL does not support versioning of interfaces. You
will need to resort to using distinct interface names; 3 common
1. create new versions in a new module: Ex: Server1.2, Server2.3, etc.
2. use inheritance (with distinct subtype names; IObject1_2, IOject2_3
inheriting from IObject1_2) But when you
want to take remove methods, the implementation gets into ugly NO-OP
implementation)
3: Just use different and unrelated interfaces to represent
different versions
Unfortunately, there is no clean way of using versions of interfaces in
CORBA. If it is any consolation, Java, C++ and a other languages have
the same problem. COM and erstwhile SOM from IBM had native support for
interface versions.
Raghu
Post by Martin B.
Original question see: http://stackoverflow.com/q/5178031/321013
Given two IDL definitions: (I'm only implementing a client, the server
side is fixed.)
// Version 1.2
module Server {
interface IObject {
void Foo1();
void Foo2() raises(EFail);
string Foo3();
// ...
}
};
// Version 2.3
module Server {
interface IObject {
// no longer available: void Foo1();
void Foo2(string x) raises(ENotFound, EFail); // incompatible change
wstring Foo3();
// ...
}
};
Is it somehow possible to compile both stub code files in the same C++
CORBA Client App?
Using the defaults of an IDL compiler, the above two IDL definitions
will result in stub code that cannot be compiled into the same C++
module, as you'd get multiple definition errors from the linker. The
client however needs to be able to talk to both server versions.
What are possible solutions?
(Note: We're using http://omniorb.sourceforge.net/)
cheers,
Martin
Raghu V. Hudli
2011-03-07 08:59:44 UTC
Permalink
There are two approaches - I am not happy with either of them - one is
a hack and the second is clumsy.

A simple *hack* may be to just alter the module name in the generated
class on the client side so that you get different name spaces. But
you will need to do it each time you recompile the idl.

A solution that does not use a hack is to restructure your client side
code.There may be more efficient ways of structuring your client-side
code. but without knowing much about the specific context, one way may
be for the client-side code to use a common wrapper for both server
instances, but you'd have two wrapper implementations one for each
server, and packaged as a separate DLL/shared object dynamic library.
Then you would write code to load and also unload specific DLLs based
on which server you want to use. This is clumsy, but not knowing why you
want to use two servers which have interfaces in the same name
space

Raghu
Post by Martin B.
I know the problems versioning poses.
The problem I face atm. is that we have two conflicting server side
IDLs, *that cannot be changed* because I just have to implement a C++
client to these 3rd party servers. And the problem now is how to prevent
C++ Linker errors when including both different stub headers (but with
the identically named module+interface) into a C++ process.
cheers,
Martin
Post by Raghu V. Hudli
Unfortunately, CORBA IDL does not support versioning of interfaces. You
will need to resort to using distinct interface names; 3 common
1. create new versions in a new module: Ex: Server1.2, Server2.3, etc.
2. use inheritance (with distinct subtype names; IObject1_2, IOject2_3
inheriting from IObject1_2) But when you
want to take remove methods, the implementation gets into ugly NO-OP
implementation)
3: Just use different and unrelated interfaces to represent
different versions
Unfortunately, there is no clean way of using versions of interfaces in
CORBA. If it is any consolation, Java, C++ and a other languages have
the same problem. COM and erstwhile SOM from IBM had native support for
interface versions.
Raghu
Post by Martin B.
Original question see: http://stackoverflow.com/q/5178031/321013
Given two IDL definitions: (I'm only implementing a client, the server
side is fixed.)
// Version 1.2
module Server {
interface IObject {
void Foo1();
void Foo2() raises(EFail);
string Foo3();
// ...
}
};
// Version 2.3
module Server {
interface IObject {
// no longer available: void Foo1();
void Foo2(string x) raises(ENotFound, EFail); // incompatible change
wstring Foo3();
// ...
}
};
Is it somehow possible to compile both stub code files in the same C++
CORBA Client App?
Using the defaults of an IDL compiler, the above two IDL definitions
will result in stub code that cannot be compiled into the same C++
module, as you'd get multiple definition errors from the linker. The
client however needs to be able to talk to both server versions.
What are possible solutions?
(Note: We're using http://omniorb.sourceforge.net/)
cheers,
Martin
Stefan Gustafsson
2011-03-08 11:40:30 UTC
Permalink
If you look at it as a C++ problem instead of a CORBA problem, the
solution is C++ namespaces.
You could try to wrap the different implementations in different C++
namespaces.
Like:
namespace v1 {
#include "v1/foo.h" // From foo.idl version 1
}
namespace v2 {
#include "v2/foo.h" // from foo.idl version 2
}
And to be able to compile the C++ proxy/stub code you need to create C
++ main files like:
foo.cpp
namespace v1 {
#include "v1/foo_proxy.cpp" // filename depend on IDL compiler
}
namespace v2 {
#include "v2/foo_proxy.cpp"
}

This will prevent the C++ linker complaining since the names will be
different. Of course you
could run into problems with C++ compilers not supporting nested
namespaces..

A second solution is to implement the invocation using DII, you could
write a C++ class
class Foo {
Stefan Gustafsson
2011-03-08 11:48:41 UTC
Permalink
Post by Stefan Gustafsson
If you look at it as a C++ problem instead of a CORBA problem, the
solution is C++ namespaces.
You could try to wrap the different implementations in different C++
namespaces.
namespace v1 {
#include "v1/foo.h" // From foo.idl version 1}
namespace v2 {
#include "v2/foo.h" // from foo.idl version 2}
 And to be able to compile the C++ proxy/stub code you need to create C
foo.cpp
namespace v1 {
#include "v1/foo_proxy.cpp"  // filename depend on IDL compiler}
namespace v2 {
#include "v2/foo_proxy.cpp"
}
This will prevent the C++ linker complaining since the names will be
different. Of course you
could run into problems with C++ compilers not supporting nested
namespaces..
A second solution is to implement the invocation using DII, you could
write a C++ class
class Foo {
Sorry, pressed send by misstate.

class ServerCall {
void foo2_v1() {
// create request
// invoke
}
void foo2_v2(String arg) {
// create_list
// add_value("x",value,ARG_IN)
// create_request
// invoke
}
}

By using DII you can create any invocation you like, and can keep full
control of your client code.

//Stefan Gustafsson
Expisoft AB

Loading...