All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.jinterop.dcom.core.JIComObjectImpl Maven / Gradle / Ivy

There is a newer version: 3.5.1
Show newest version
/** j-Interop (Pure Java implementation of DCOM protocol)
 * Copyright (C) 2006  Vikram Roopchand
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 3.0 of the License, or (at your option) any later version.
 *
 * Though a sincere effort has been made to deliver a professional,
 * quality product,the library itself is distributed WITHOUT ANY WARRANTY;
 * See the GNU Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110, USA
 */
package org.jinterop.dcom.core;

import com.iwombat.foundation.IdentifierFactory;
import com.iwombat.util.GUIDUtil;
import java.util.HashMap;
import java.util.Map;
import java.util.logging.Level;
import org.jinterop.dcom.common.IJIUnreferenced;
import org.jinterop.dcom.common.JIErrorCodes;
import org.jinterop.dcom.common.JIException;
import org.jinterop.dcom.common.JISystem;

/**
 * Implementation for IJIComObject. There is a 1 to 1 mapping between this and a
 * COM interface.
 *
 * @exclude
 * @since 1.0
 */
final class JIComObjectImpl implements IJIComObject {

    /**
     *
     */
    private static final long serialVersionUID = -1661750453596032089L;
    private boolean isDual = false;
    private boolean dualInfo = false;
    private transient JISession session = null;
    private JIInterfacePointer ptr = null;
    private Map connectionPointInfo = null;
    private int timeout = 0;
    private final boolean isLocal;

    JIComObjectImpl(JISession session, JIInterfacePointer ptr) {
        this(session, ptr, false);
    }

    JIComObjectImpl(JISession session, JIInterfacePointer ptr, boolean isLocal) {
        this.session = session;
        this.ptr = ptr;
        this.isLocal = isLocal;
    }

    void replaceMembers(IJIComObject comObject) {
        this.session = comObject.getAssociatedSession();
        this.ptr = comObject.internal_getInterfacePointer();
    }

    private void checkLocal() {
        if (session == null) {
            throw new IllegalStateException(JISystem.getLocalizedMessage(JIErrorCodes.JI_SESSION_NOT_ATTACHED));
        }

        if (isLocalReference()) {
            throw new IllegalStateException(JISystem.getLocalizedMessage(JIErrorCodes.E_NOTIMPL));
        }
    }

    public IJIComObject queryInterface(String iid) throws JIException {
        checkLocal();
        return session.getStub().getInterface(iid, ptr.getIPID());
    }

    public void addRef() throws JIException {
        checkLocal();
        JICallBuilder obj = new JICallBuilder(true);
        obj.setParentIpid(ptr.getIPID());
        obj.setOpnum(1);//addRef

        //length
        obj.addInParamAsShort((short) 1, JIFlags.FLAG_NULL);
        //ipid to addfref on
        JIArray array = new JIArray(new rpc.core.UUID[]{new rpc.core.UUID(ptr.getIPID())}, true);
        obj.addInParamAsArray(array, JIFlags.FLAG_NULL);
        //TODO requesting 5 for now, will later build caching mechnaism to exhaust 5 refs first before asking for more
        // same with release.
        obj.addInParamAsInt(5, JIFlags.FLAG_NULL);
        obj.addInParamAsInt(0, JIFlags.FLAG_NULL);//private refs = 0

        obj.addOutParamAsType(Short.class, JIFlags.FLAG_NULL);//size
        obj.addOutParamAsType(Integer.class, JIFlags.FLAG_NULL);//Hresult for size
        if (JISystem.getLogger().isLoggable(Level.INFO)) {
            JISystem.getLogger().warning("addRef: Adding 5 references for " + ptr.getIPID() + " session: " + session.getSessionIdentifier());
        }

        JISession.debug_addIpids(ptr.getIPID(), 5);

        session.getStub2().addRef_ReleaseRef(obj);

        if (obj.getResultAsIntAt(1) != 0) {
            throw new JIException(obj.getResultAsIntAt(1), (Throwable) null);
        }
    }

    public void release() throws JIException {
        checkLocal();
        JICallBuilder obj = new JICallBuilder(true);
        obj.setParentIpid(ptr.getIPID());
        obj.setOpnum(2);//release
        //length
        obj.addInParamAsShort((short) 1, JIFlags.FLAG_NULL);
        //ipid to addfref on
        JIArray array = new JIArray(new rpc.core.UUID[]{new rpc.core.UUID(ptr.getIPID())}, true);
        obj.addInParamAsArray(array, JIFlags.FLAG_NULL);
        //TODO requesting 5 for now, will later build caching mechnaism to exhaust 5 refs first before asking for more
        // same with release.
        obj.addInParamAsInt(5, JIFlags.FLAG_NULL);
        obj.addInParamAsInt(0, JIFlags.FLAG_NULL);//private refs = 0
        if (JISystem.getLogger().isLoggable(Level.INFO)) {
            JISystem.getLogger().warning("RELEASE called directly ! removing 5 references for " + ptr.getIPID() + " session: " + session.getSessionIdentifier());
            JISession.debug_delIpids(ptr.getIPID(), 5);
        }
        session.getStub2().addRef_ReleaseRef(obj);
    }

    public Object[] call(JICallBuilder obj) throws JIException {
        checkLocal();
        return call(obj, timeout);
    }

    public JIInterfacePointer internal_getInterfacePointer() {
        return ptr == null ? session.getStub().getServerInterfacePointer() : ptr;
    }

    public String getIpid() {
        return ptr.getIPID();
    }

    public boolean equals(Object obj) {

        if (!(obj instanceof JIComObjectImpl)) {
            return false;
        }

        return (this.ptr.getIPID().equalsIgnoreCase(((IJIComObject) obj).getIpid()));
    }

    public int hashCode() {
        return ptr.getIPID().hashCode();
    }

    public JISession getAssociatedSession() {
        return session;
    }

    public String getInterfaceIdentifier() {
        return ptr.getIID();
    }

//	public JIComServer getAssociatedComServer()
//	{
//		checkLocal();
//		return session.getStub();
//	}
    public synchronized boolean isDispatchSupported() {
        checkLocal();
        if (!dualInfo) {
            //query interface for it and then release it.
            try {
                IJIComObject comObject = queryInterface("00020400-0000-0000-c000-000000000046");
                comObject.release();
                setIsDual(true);
            } catch (JIException e) {
                setIsDual(false);
            }
        }
        return isDual;
    }

    public synchronized String internal_setConnectionInfo(IJIComObject connectionPoint, Integer cookie) {
        checkLocal();
        if (connectionPointInfo == null) //lazy creation, since this is used by event callbacks only.
        {
            connectionPointInfo = new HashMap();
        }
        String uniqueId = GUIDUtil.guidStringFromHexString(IdentifierFactory.createUniqueIdentifier().toHexString());
        connectionPointInfo.put(uniqueId, new Object[]{connectionPoint, cookie});
        return uniqueId;
    }

    public synchronized Object[] internal_getConnectionInfo(String identifier) {
        checkLocal();
        return (Object[]) connectionPointInfo.get(identifier);
    }

    public synchronized Object[] internal_removeConnectionInfo(String identifier) {
        checkLocal();
        return (Object[]) connectionPointInfo.remove(identifier);
    }

    public IJIUnreferenced getUnreferencedHandler() {
        checkLocal();
        return session.getUnreferencedHandler(getIpid());
    }

    public void registerUnreferencedHandler(IJIUnreferenced unreferenced) {
        checkLocal();
        session.registerUnreferencedHandler(getIpid(), unreferenced);
    }

    public void unregisterUnreferencedHandler() {
        checkLocal();
        session.unregisterUnreferencedHandler(getIpid());
    }

    public Object[] call(JICallBuilder obj, int socketTimeout) throws JIException {
        checkLocal();
        obj.attachSession(session);
        obj.setParentIpid(ptr.getIPID());
        //Call is always made on your stub.

        if (socketTimeout != 0) //using instance level timeout
        {
            return session.getStub().call(obj, ptr.getIID(), socketTimeout);
        } else {
            return session.getStub().call(obj, ptr.getIID());
        }
    }

    public int getInstanceLevelSocketTimeout() {
        checkLocal();
        return timeout;
    }

    public void setInstanceLevelSocketTimeout(int timeout) {
        checkLocal();
        this.timeout = timeout;
    }

    public void internal_setDeffered(boolean deffered) {
        ptr.setDeffered(deffered);
    }

    public boolean isLocalReference() {
        return isLocal;
    }

    void setIsDual(boolean isDual) {
        this.dualInfo = true;
        this.isDual = isDual;
    }

    public String toString() {
        return "IJIComObject[" + internal_getInterfacePointer() + " , session: " + getAssociatedSession().getSessionIdentifier() + ", isLocal: " + isLocalReference() + "]";
    }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy