MICO

This talk introduces the MICO [1] CORBA implementation. More documentation is available at that website.

1 Using MICO

2 account.idl

interface Account {
  void deposit (in unsigned long amount);
  void withdraw (in unsigned long amount);
  long balance();
};
account files UML diagram

3 account.h

/*
 *  MICO --- an Open Source CORBA implementation
 *  Copyright (c) 1997-2001 by The Mico Team
 *
 *  This file was automatically generated. DO NOT EDIT!
 */

#include <CORBA.h>
#include <mico/throw.h>

#ifndef __ACCOUNT_H__
#define __ACCOUNT_H__



class Account;
typedef Account *Account_ptr;
typedef Account_ptr AccountRef;
typedef ObjVar<Account> Account_var;
typedef ObjOut<Account> Account_out;


/*
 * Base class and common definitions for interface Account
 */

class Account : 
  virtual public CORBA::Object
{
  public:
    virtual ~Account();

    #ifdef HAVE_TYPEDEF_OVERLOAD
    typedef Account_ptr _ptr_type;
    typedef Account_var _var_type;
    #endif

    static Account_ptr _narrow( CORBA::Object_ptr obj );
    static Account_ptr _narrow( CORBA::AbstractBase_ptr obj );
    static Account_ptr _duplicate( Account_ptr _obj )
    {
      CORBA::Object::_duplicate (_obj);
      return _obj;
    }

    static Account_ptr _nil()
    {
      return 0;
    }

    virtual void *_narrow_helper( const char *repoid );

    virtual void deposit( CORBA::ULong amount ) = 0;
    virtual void withdraw( CORBA::ULong amount ) = 0;
    virtual CORBA::Long balance() = 0;

  protected:
    Account() {};
  private:
    Account( const Account& );
    void operator=( const Account& );
};

// Stub for interface Account
class Account_stub:
  virtual public Account
{
  public:
    virtual ~Account_stub();
    void deposit( CORBA::ULong amount );
    void withdraw( CORBA::ULong amount );
    CORBA::Long balance();

  private:
    void operator=( const Account_stub& );
};

class Account_skel :
  virtual public StaticMethodDispatcher,
  virtual public Account
{
  public:
    Account_skel( const CORBA::BOA::ReferenceData & = CORBA::BOA::ReferenceData() );
    virtual ~Account_skel();
    Account_skel( CORBA::Object_ptr obj );
    virtual bool dispatch( CORBA::StaticServerRequest_ptr __req, CORBA::Environment &_env );
    Account_ptr _this();

};

#ifndef MICO_CONF_NO_POA

#endif // MICO_CONF_NO_POA

extern CORBA::StaticTypeInfo *_marshaller_Account;

#endif

4 account.cc

/*
 *  MICO --- an Open Source CORBA implementation
 *  Copyright (c) 1997-2001 by The Mico Team
 *
 *  This file was automatically generated. DO NOT EDIT!
 */

#include "account.h"

//--------------------------------------------------------
//  Implementation of stubs
//--------------------------------------------------------

/*
 * Base interface for class Account
 */

Account::~Account()
{
}

void *
Account::_narrow_helper( const char *_repoid )
{
  if( strcmp( _repoid, "IDL:Account:1.0" ) == 0 )
    return (void *)this;
  return NULL;
}

Account_ptr
Account::_narrow( CORBA::Object_ptr _obj )
{
  Account_ptr _o;
  if( !CORBA::is_nil( _obj ) ) {
    void *_p;
    if( (_p = _obj->_narrow_helper( "IDL:Account:1.0" )))
      return _duplicate( (Account_ptr) _p );
    if (!strcmp (_obj->_repoid(), "IDL:Account:1.0") || _obj->_is_a_remote ("IDL:Account:1.0")) {
      _o = new Account_stub;
      _o->MICO_SCOPE(CORBA,Object::operator=)( *_obj );
      return _o;
    }
  }
  return _nil();
}

Account_ptr
Account::_narrow( CORBA::AbstractBase_ptr _obj )
{
  return _narrow (_obj->_to_object());
}

class _Marshaller_Account : public CORBA::StaticTypeInfo {
    typedef Account_ptr _MICO_T;
  public:
    StaticValueType create () const;
    void assign (StaticValueType dst, const StaticValueType src) const;
    void free (StaticValueType) const;
    void release (StaticValueType) const;
    CORBA::Boolean demarshal (CORBA::DataDecoder&, StaticValueType) const;
    void marshal (CORBA::DataEncoder &, StaticValueType) const;
};


CORBA::StaticValueType _Marshaller_Account::create() const
{
  return (StaticValueType) new _MICO_T( 0 );
}

void _Marshaller_Account::assign( StaticValueType d, const StaticValueType s ) const
{
  *(_MICO_T*) d = ::Account::_duplicate( *(_MICO_T*) s );
}

void _Marshaller_Account::free( StaticValueType v ) const
{
  CORBA::release( *(_MICO_T *) v );
  delete (_MICO_T*) v;
}

void _Marshaller_Account::release( StaticValueType v ) const
{
  CORBA::release( *(_MICO_T *) v );
}

CORBA::Boolean _Marshaller_Account::demarshal( CORBA::DataDecoder &dc, StaticValueType v ) const
{
  CORBA::Object_ptr obj;
  if (!CORBA::_stc_Object->demarshal(dc, &obj))
    return FALSE;
  *(_MICO_T *) v = ::Account::_narrow( obj );
  CORBA::Boolean ret = CORBA::is_nil (obj) || !CORBA::is_nil (*(_MICO_T *)v);
  CORBA::release (obj);
  return ret;
}

void _Marshaller_Account::marshal( CORBA::DataEncoder &ec, StaticValueType v ) const
{
  CORBA::Object_ptr obj = *(_MICO_T *) v;
  CORBA::_stc_Object->marshal( ec, &obj );
}

CORBA::StaticTypeInfo *_marshaller_Account;


/*
 * Stub interface for class Account
 */

Account_stub::~Account_stub()
{
}

void Account_stub::deposit( CORBA::ULong amount )
{
  CORBA::StaticAny _amount( CORBA::_stc_ulong, &amount );
  CORBA::StaticRequest __req( this, "deposit" );
  __req.add_in_arg( &_amount );

  __req.invoke();

  mico_sii_throw( &__req, 
    0);
}


void Account_stub::withdraw( CORBA::ULong amount )
{
  CORBA::StaticAny _amount( CORBA::_stc_ulong, &amount );
  CORBA::StaticRequest __req( this, "withdraw" );
  __req.add_in_arg( &_amount );

  __req.invoke();

  mico_sii_throw( &__req, 
    0);
}


CORBA::Long Account_stub::balance()
{
  CORBA::Long _res;
  CORBA::StaticAny __res( CORBA::_stc_long, &_res );

  CORBA::StaticRequest __req( this, "balance" );
  __req.set_result( &__res );

  __req.invoke();

  mico_sii_throw( &__req, 
    0);
  return _res;
}


struct __tc_init_ACCOUNT {
  __tc_init_ACCOUNT()
  {
    _marshaller_Account = new _Marshaller_Account;
  }
};

static __tc_init_ACCOUNT __init_ACCOUNT;

//--------------------------------------------------------
//  Implementation of skeletons
//--------------------------------------------------------

Account_skel::Account_skel( const CORBA::BOA::ReferenceData &_id )
{
  CORBA::ImplementationDef_var _impl =
    _find_impl( "IDL:Account:1.0", "Account" );
  _create_ref( _id,
    0,
    _impl,
    "IDL:Account:1.0" );
  register_dispatcher( new StaticInterfaceDispatcherWrapper<Account_skel>( this ) );
}

Account_skel::Account_skel( CORBA::Object_ptr _obj )
{
  CORBA::ImplementationDef_var _impl =
    _find_impl( "IDL:Account:1.0", "Account" );
  assert( !CORBA::is_nil( _impl ) );
  _restore_ref( _obj,
    CORBA::BOA::ReferenceData(),
    0,
    _impl );
  register_dispatcher( new StaticInterfaceDispatcherWrapper<Account_skel>( this ) );
}

Account_skel::~Account_skel()
{
}

bool Account_skel::dispatch( CORBA::StaticServerRequest_ptr __req, CORBA::Environment & /*_env*/ )
{
  #ifdef HAVE_EXCEPTIONS
  try {
  #endif
    if( strcmp( __req->op_name(), "deposit" ) == 0 ) {
      CORBA::ULong amount;
      CORBA::StaticAny _amount( CORBA::_stc_ulong, &amount );

      __req->add_in_arg( &_amount );

      if( !__req->read_args() )
        return true;

      deposit( amount );
      __req->write_results();
      return true;
    }
    if( strcmp( __req->op_name(), "withdraw" ) == 0 ) {
      CORBA::ULong amount;
      CORBA::StaticAny _amount( CORBA::_stc_ulong, &amount );

      __req->add_in_arg( &_amount );

      if( !__req->read_args() )
        return true;

      withdraw( amount );
      __req->write_results();
      return true;
    }
    if( strcmp( __req->op_name(), "balance" ) == 0 ) {
      CORBA::Long _res;
      CORBA::StaticAny __res( CORBA::_stc_long, &_res );
      __req->set_result( &__res );

      if( !__req->read_args() )
        return true;

      _res = balance();
      __req->write_results();
      return true;
    }
  #ifdef HAVE_EXCEPTIONS
  } catch( CORBA::SystemException_catch &_ex ) {
    __req->set_exception( _ex->_clone() );
    __req->write_results();
    return true;
  } catch( ... ) {
    assert( 0 );
    return true;
  }
  #endif
  return false;
}

Account_ptr Account_skel::_this()
{
  return Account::_duplicate( this );
}

5 account_impl.cc

#include "account.h"

class Account_impl : virtual public Account_skel
{
private:
  CORBA::Long _current_balance;

public:
  Account_impl()
  {
    _current_balance = 0;
  };

  void deposit(CORBA::ULong amount)
  {
    _current_balance += amount;
  };

  void withdraw(CORBA::ULong amount)
  {
    _current_balance -= amount;
  };

  CORBA::Long balance()
  {
    return _current_balance;
  };
};

int main(int argc, char *argv[])
{
  //ORB intialization
  CORBA::ORB_var orb = CORBA::ORB_init(argc, argv, "mico-local-orb");
  CORBA::BOA_var boa = orb->BOA_init(argc, argv, "mico-local-boa");

  //server side code
  //Notice how we allocate just the pointer, not the object.
  //This is because CORBA requires each object to be deleted with a
  // CORBA::release(obj) call only. Automatic allocation will call the
  // destructor when out of scope.
  Account_impl* server = new Account_impl;

  //This is how we turn the reference into a string.
  CORBA::String_var ref = orb->object_to_string(server);
  cour << "Server refrence: " << ref << endl;

  //client side code
  CORBA::Object_var obj = orb->string_to_object(ref);

  //Account_var is a smart pointer to Account instances that calls
  // release() when the object is destroyed. Account_ptr is a regular
  // smart pointer.
  Account_var client = Account::_narrow(obj);

  client->deposit(700);
  client->withdraw(250);
  cout << "Balance is " << client->balance() << endl;

  //We don't need the server object any more. This code belongs
  // to the server implementation
  CORBA::release(server);
  return 0;
}
  

6 Compilation

7 server.cc

#include <iostream.h>
#include <fstream.h>
#include <unistd.h>
#include "account.h"

class Account_impl : virtual public Account_skel {
  
  //as before.....
  
};

int main( int argc, char *argv[] )
{
    cout << "server init" << endl;

    AccountLoader loader;
    CORBA::ORB_var orb = CORBA::ORB_init( argc, argv, "mico-local-orb" );
    CORBA::BOA_var boa = orb->BOA_init (argc, argv, "mico-local-boa");

    Account_impl* server = new Account_impl;

    CORBA::String_var  ref= orb->object_to_string(server);
    ofstream out("/tmp/account.objid");
    out << ref << endl;
    out.close();

    boa->impl_is_ready(CORBA::ImplementationDef::_nil());
    orb->run();
    CORBA::release(server);

    return 0;
}

8 client.cc

#include <iostream.h>
#include <fstream.h>
#include "account.h"

int main( int argc, char *argv[] )
{
    // ORB initialization
    CORBA::ORB_var orb = CORBA::ORB_init( argc, argv, "mico-local-orb" );
    CORBA::BOA_var boa = orb->BOA_init (argc, argv, "mico-local-boa");

    ifstream in("/tmp/account.objid");
    char ref[1000];
    in >> ref;
    in.close();

    CORBA::Object_var obj = orb->string_to_object(ref);
    Account_var client = Account::_narrow(obj);
    

    client->deposit( 100 );
    client->deposit( 100 );
    client->deposit( 100 );
    client->deposit( 100 );
    client->deposit( 100 );
    client->withdraw( 240 );
    client->withdraw( 10 );
    cout << "Balance is " << client->balance() << endl;

    return 0;
}

URLs

  1. MICO, http://www.mico.org

This talk available at http://jmvidal.cse.sc.edu/talks/mico/
Copyright © 2009 José M. Vidal . All rights reserved.

27 March 2002, 02:57PM