// **********************************************************************
//
// Copyright (c) 1998
// Object-Oriented Concepts, Inc.
// Billerica, MA, USA
//
// Copyright (c) 1998
// Object-Oriented Concepts GmbH
// Ettlingen, Germany
//
// All Rights Reserved
//
// **********************************************************************

#ifndef OB_DSI_H
#define OB_DSI_H

//
// The ServerRequest class
//
class CORBA_ServerRequest;
typedef CORBA_ServerRequest* CORBA_ServerRequest_ptr;
typedef CORBA_ServerRequest_ptr ServerRequestRef;
void OBDuplicate(CORBA_ServerRequest_ptr);
void OBRelease(CORBA_ServerRequest_ptr);
typedef OBObjVar< CORBA_ServerRequest > CORBA_ServerRequest_var;

class CORBA_ServerRequest : public OBRefCount
{
    CORBA_Object_var object_;
    CORBA_String_var name_;
    OBBuffer& buf_;
    bool swap_;
    CORBA_ULong offOut_;
    const CORBA_Octet* coct_;

    CORBA_Context_var ctx_;
    CORBA_NVList_var params_;
    CORBA_Any_var result_;
    CORBA_Any_var exception_;

    //
    // Unmarshal and marshal
    //
    void unmarshal();
    void unmarshalCtx();
    void marshal();

protected:

    CORBA_ServerRequest(CORBA_Object_ptr, const char*, OBBuffer&, bool,
			CORBA_ULong, CORBA_ULong);

    // DynamicImpelmentations may create ServerRequests
    friend class CORBA_DynamicImplementation;

#ifdef HAVE_GNUC_2_7_BUGS
    ~CORBA_ServerRequest() { };
                   // Internal compiler error with GNU C++ 2.7.2 and option -O
                   // if I don't write the desctructor explicitly here
#endif 

public:

    static inline CORBA_ServerRequest_ptr _duplicate(CORBA_ServerRequest_ptr p)
    { if(p) p -> _OB_incRef(); return p; }
    static inline CORBA_ServerRequest_ptr _nil()
    { return 0; }

    CORBA_OperationDef_ptr op_def();
    const char* op_name();
    CORBA_Context_ptr ctx();
    void params(CORBA_NVList_ptr);
    void result(CORBA_Any*);
    void exception(CORBA_Any*);
};

inline void
CORBA_release(CORBA_ServerRequest_ptr p)
{
    if(p)
	p -> _OB_decRef();
}

inline CORBA_Boolean
CORBA_is_nil(CORBA_ServerRequest_ptr p)
{
    return p == 0;
}

//
// The DynamicImplementation class
//
class CORBA_DynamicImplementation : public virtual CORBA_Object_skel
{
    //
    // Hide copy-constructor and asignment operator
    //
    CORBA_DynamicImplementation(const CORBA_DynamicImplementation&);
    void operator=(const CORBA_DynamicImplementation&);

protected:

    CORBA_DynamicImplementation() { }

public:

    //
    // Standard IDL to C++ Mapping
    //
    virtual void invoke(CORBA_ServerRequest_ptr request) throw() = 0;

    //
    // Additonal ORBacus specific functions
    //
    virtual CORBA_Boolean _is_dynamic();

    //
    // ORBacus internal functions
    // Application programs must not use these functions directly
    //
    virtual OBDispatchStatus _OB_dispatch(const char*, OBBuffer&, bool,
					  CORBA_ULong, CORBA_ULong);
};

#endif
