У меня есть IDL, как показано ниже
module IClientServer {
interface IClient
{
void serverResponse(in string name, in string data);
void start();
void stop();
void shutdown();
};
interface IServer
{
// Server calls back to client just once in a
// recursive call before returning.
// void one_time(in CallBack cb, in string mesg);
void DataFromX(in string name,in string data,in long lbytes,in short usg);
void Authenticate(in IClient client, in string dataToNegotiate);
// Shuts down the server.
void shutdown();
};
};
для которого я сгенерировал прокси & скелет с помощью утилиты idl2cpp (onmiORB) и связал сгенерированные файлы с сервером & клиентское приложение, как предлагается в документе
Затем я запустил службу имен (omniNames) и добавил ключ реестра omniORB \ InitRef, как предложено в документации для сервера. & клиентские приложения для подключения без использования аргументов командной строки
Ниже приведен код сервера
int _tmain(int argc, _TCHAR* argv[])
{
try
{
int argc = 0;
_BRDTRACE("Initializing....\n");
CORBA::ORB_var orb = CORBA::ORB_init(argc, NULL);
// cerr << "Initialized." << endl;
CORBA::Object_var obj = orb->resolve_initial_references("RootPOA");
_BRDTRACE("Resolved.\n");PortableServer::POA_var poa = PortableServer::POA::_narrow(obj);
_BRDTRACE("Narrowed..\n");
// Obtain a reference to the object, and register it in
// the naming service.
server_i* myserver = new server_i();
// cerr << "Constructed." << endl;
obj = myserver->_this();
_BRDTRACE("obj retrieved.\n");
CORBA::String_var x;
x = orb->object_to_string(obj);
_BRDTRACE("obj to string.\n");
if( !bindObjectToName(orb, obj) )
{
// cerr << "Failed to bind obj to name." << endl;
throw;
}
_BRDTRACE("binded\n");
myserver->_remove_ref();
// cerr << "removed ref." << endl;
PortableServer::POAManager_var pman = poa->the_POAManager();
pman->activate();
_BRDTRACE("activated.\n");
// cerr << "Executing..." << endl;
orb->run();
_BRDTRACE("Terminated.\n");
myserver->shutdown();
// cerr << "Shutdown." << endl;
}
catch(CORBA::SystemException&)
{
_BRDTRACE("Caught CORBA::SystemException.\n");
}
catch(CORBA::Exception&) {
_BRDTRACE("Caught CORBA::Exception.\n");
}
catch(omniORB::fatalException&)
{
_BRDTRACE("Caught omniORB::fatalException:\n");
// cerr << " file: " << fe.file() << endl;
// cerr << " line: " << fe.line() << endl;
// cerr << " mesg: " << fe.errmsg() << endl;
}
catch(...) {
_BRDTRACE("Caught unknown exception.\n");
}
}
static CORBA::Boolean
bindObjectToName(CORBA::ORB_ptr orb, CORBA::Object_ptr objref)
{
CosNaming::NamingContext_var rootContext;
try {
// Obtain a reference to the root context of the Name service:
CORBA::Object_var obj;
obj = orb->resolve_initial_references("NameService");
// Narrow the reference returned.
rootContext = CosNaming::NamingContext::_narrow(obj);
if( CORBA::is_nil(rootContext) ) {
_BRDTRACE("Failed to narrow the root naming context.\n");
return 0;
}
}
catch(CORBA::ORB::InvalidName& ex) {
// This should not happen!
_BRDTRACE("Service required is invalid [does not exist].\n");
return 0;
}
try {
// Bind a context called "test" to the root context:
CosNaming::Name contextName;
contextName.length(1);
contextName[0].id = (const char*) "birdseye"; // string copied
contextName[0].kind = (const char*) "collections_context"; // string copied
// Note on kind: The kind field is used to indicate the type
// of the object. This is to avoid conventions such as that used
// by files (name.type -- e.g. test.ps = postscript etc.)
//CosNaming::NamingContext_var testContext;
try {
// Bind the context to root.
rootContext->bind(contextName, objref);
}
catch(CosNaming::NamingContext::AlreadyBound& ex) {
// If the context already exists, this exception will be raised.
// In this case, just resolve the name and assign testContext
// to the object returned:
CORBA::Object_var obj;
obj = rootContext->resolve(contextName);
CosNaming::NamingContext_var testContext = CosNaming::NamingContext::_narrow(obj);
if( CORBA::is_nil(testContext) ) {
_BRDTRACE("Failed to narrow naming context.\n");
return 0;
}
}
} catch(CORBA::COMM_FAILURE& ex) {
_BRDTRACE("Caught system exception COMM_FAILURE -- unable to contact the naming service.\n");
return 0;
}
catch(CORBA::SystemException&) {
_BRDTRACE("Caught a CORBA::SystemException while using the naming service.\n");
return 0;
}
return 1;
}
Но приведенный ниже код на стороне клиента возвращает nil-объект после имени
разрешение контекста. Не в состоянии разобраться в проблеме. Пожалуйста помоги!
int _tmain(int argc, _TCHAR* argv[])
{
CORBA::ORB_var orb = CORBA::ORB_init(argc, argv);
CORBA::Object_var objRef = orb->resolve_initial_references("NameService");
CORBA::Object_var obj = getObjectReference(orb);
IClientServer::IServer_var svr = IClientServer::IServer::_narrow(obj.in());
if( CORBA::is_nil(svr) ) { **//THIS IS WHERE THE ISSUE IS**
// _BRDTRACE("cb_client: The server reference is nil!\n");
return 0;
}
return 0;
}
static CORBA::Object_ptr
getObjectReference(CORBA::ORB_ptr orb)
{
CosNaming::NamingContext_var rootContext;
try {
// Obtain a reference to the root context of the Name service:
CORBA::Object_var obj;
obj = orb->resolve_initial_references("NameService");
// Narrow the reference returned.
rootContext = CosNaming::NamingContext::_narrow(obj);
if( CORBA::is_nil(rootContext) ) {
// cerr << "Failed to narrow the root naming context." << endl;
return CORBA::Object::_nil();
}
}
catch(CORBA::ORB::InvalidName& ) {
// This should not happen!
return CORBA::Object::_nil();
}
// Create a name object, containing the name test/context:
CosNaming::Name name;
name.length(1);
name[0].id = (const char*) "birdseye"; // string copied
name[0].kind = (const char*) "collections_context"; // string copied
// Note on kind: The kind field is used to indicate the type
// of the object. This is to avoid conventions such as that used
// by files (name.type -- e.g. test.ps = postscript etc.)try {
// Resolve the name to an object reference.
return rootContext->resolve(name);
}
catch(CosNaming::NamingContext::NotFound& nf) {
}
catch(CORBA::COMM_FAILURE& ) {
}
catch(CORBA::SystemException&) {
}
return CORBA::Object::_nil();
}
UPDATE-5PM:
Infact серверный код также имеет ту же проблему, сервер-> authenticate никогда не вызывается из-за нулевой ссылки.
Угадай: может ли быть проблема с прокси & заглушки, созданные с помощью инструмента idl2cpp?
UPDATE-7: 30PM
Неясность в отношении заглушек не в порядке, также исчезла, проблема все еще сохраняется после регенерации заглушек. & восстановление обоих клиентов & снова серверные приложения
ОБНОВЛЕНИЕ 3-31 | 11 утра
Я использую omniORB 4.0.3, которому более 10 лет. Это отлично работало в более ранних версиях ОС Windows, скомпилированных с VC6, я сомневаюсь, что есть проблема при перекомпиляции на VS 2008. Просто думаю об обновлении до ommiORB 4.2, выпущенном в прошлом году. Просто невежественный вообще …
ОБНОВЛЕНИЕ 3-31 | 5: 30 вечера
В настоящее время строится исходный код omniORB4.2.1. Пока я делаю это, я все еще хочу знать, есть ли какая-либо проблема, связывающая файлы .lib, которые генерируются в старых системах. В этом случае файлы omniORB .lib, которые я использую в Windows 7, построены на Windows XP, это будет проблемой? Четное этот пост не может ответить, у меня есть старый .lib, который скомпилирован & хорошо связаны без каких-либо проблем & даже во время выполнения это не вылетало, а также
ОБНОВЛЕНИЕ 4-01 | 4: 30PM
На самом деле я заметил, что сервер не работает, код сервера, который я разместил ранее, также является клиентом, теперь я обновил реальный код сервера (код, который связывает имя с сервером obj). Но проблема остается такой же даже после этой коррекции
Наконец я исправил проблему. Есть 2 проблемы с кодом
вопрос 1 Я уже обновил вопрос (отсутствует код сервера)
проблема 2 с привязкой контекста имени ..
ниже модифицированная версия bindObjectToName на сервере
static CORBA::Boolean
bindObjectToName(CORBA::ORB_ptr orb, CORBA::Object_ptr objref)
{
CosNaming::NamingContext_var rootContext;
try {
// Obtain a reference to the root context of the Name service:
CORBA::Object_var obj;
obj = orb->resolve_initial_references("NameService");
// Narrow the reference returned.
rootContext = CosNaming::NamingContext::_narrow(obj);
if( CORBA::is_nil(rootContext) ) {
// cerr << "Failed to narrow the root naming context." << endl;
return 0;
}
}
catch(CORBA::ORB::InvalidName& ex) {
// This should not happen!
// cerr << "Service required is invalid [does not exist]." << endl;
return 0;
}
try {
// Bind a context called "test" to the root context:
CosNaming::Name contextName;
contextName.length(1);
contextName[0].id = (const char*) "birdsEYE"; // string copied
contextName[0].kind = (const char*) "DataCollectionS"; // string copied
// Note on kind: The kind field is used to indicate the type
// of the object. This is to avoid conventions such as that used
// by files (name.type -- e.g. test.ps = postscript etc.)
CosNaming::NamingContext_var testContext;
try {
// Bind the context to root.
testContext = rootContext->bind_new_context(contextName);
}
catch(CosNaming::NamingContext::AlreadyBound& ex) {
// If the context already exists, this exception will be raised.
// In this case, just resolve the name and assign testContext
// to the object returned:
CORBA::Object_var obj;
obj = rootContext->resolve(contextName);
testContext = CosNaming::NamingContext::_narrow(obj);
if( CORBA::is_nil(testContext) ) {
// cerr << "Failed to narrow naming context." << endl;
return 0;
}
}
// Bind sender :
CosNaming::Name objectName;
objectName.length(1);
objectName[0].id = (const char*) "clienT"; // string copied
objectName[0].kind = (const char*) "sendeR"; // string copied
try {
testContext->bind(objectName, objref);
}
catch(CosNaming::NamingContext::AlreadyBound& ex) {
testContext->rebind(objectName, objref);
}
// Note: Using rebind() will overwrite any Object previously bound
// to /test/Echo with obj.
// Alternatively, bind() can be used, which will raise a
// CosNaming::NamingContext::AlreadyBound exception if the name
// supplied is already bound to an object.
// Bind receiver :
CosNaming::Name objectName2;
objectName2.length(1);
objectName2[0].id = (const char*) "clienT"; // string copied
objectName2[0].kind = (const char*) "receiveR"; // string copied
try {
testContext->bind(objectName2, objref);
}
catch(CosNaming::NamingContext::AlreadyBound& ex) {
testContext->rebind(objectName2, objref);
}// Amendment: When using OrbixNames, it is necessary to first try bind
// and then rebind, as rebind on it's own will throw a NotFoundexception if
// the Name has not already been bound. [This is incorrect behaviour -
// it should just bind].
}
catch(CORBA::COMM_FAILURE& ex) {
//cerr << "Caught system exception COMM_FAILURE -- unable to contact the "// << "naming service." << endl;
return 0;
}
catch(CORBA::SystemException&) {
//cerr << "Caught a CORBA::SystemException while using the naming service."// << endl;
return 0;
}
return 1;
}
А ниже модифицированный getObjectReference в клиентском коде
статический CORBA :: Object_ptr
getObjectReference(CORBA::ORB_ptr orb)
{
CosNaming::NamingContext_var rootContext;
try {
// Obtain a reference to the root context of the Name service:
CORBA::Object_var obj;
obj = orb->resolve_initial_references("NameService");
// Narrow the reference returned.
rootContext = CosNaming::NamingContext::_narrow(obj);
if( CORBA::is_nil(rootContext) ) {
// cerr << "Failed to narrow the root naming context." << endl;
return CORBA::Object::_nil();
}
}
catch(CORBA::ORB::InvalidName& ex) {
// This should not happen!
// cerr << "Service required is invalid [does not exist]." << endl;
_BRDTRACE("getObjRef: service required is invalid.\n");
exit(0);
return CORBA::Object::_nil();
}// Create a name object, containing the name test/context:
CosNaming::Name name;
name.length(2);
name[0].id = (const char*) "birdsEYE"; // string copied
name[0].kind = (const char*) "DataCollectionS"; // string copied
name[1].id = (const char*) "clienT";
name[1].kind = (const char*) "sendeR";
// Note on kind: The kind field is used to indicate the type
// of the object. This is to avoid conventions such as that used
// by files (name.type -- e.g. test.ps = postscript etc.)try {
// Resolve the name to an object reference.
return rootContext->resolve(name);
}
catch(CosNaming::NamingContext::NotFound& ex) {
// This exception is thrown if any of the components of the
// path [contexts or the object] aren't found:
//cerr << "Context not found." << endl;
_BRDTRACE("getObjRef: context not found.\n");
exit(0);
}
catch(CORBA::COMM_FAILURE& ex) {
//cerr << "Caught system exception COMM_FAILURE -- unable to contact the "// << "naming service." << endl;
_BRDTRACE("getObjRef: caught system exception COMM_FAILURE.\n");
exit(0);
}
catch(CORBA::SystemException&) {
//cerr << "Caught a CORBA::SystemException while using the naming service."//<< endl;
_BRDTRACE("getObjRef: caught system exception while using the name service.\n");
exit(0);
}
return CORBA::Object::_nil();
}
Других решений пока нет …