1 /* 2 * Copyright (c) 2002, 2012, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 package com.sun.corba.se.impl.protocol; 27 28 import org.omg.CORBA.portable.ServantObject; 29 30 import com.sun.corba.se.spi.protocol.LocalClientRequestDispatcher; 31 import com.sun.corba.se.spi.protocol.RequestDispatcherRegistry; 32 33 import com.sun.corba.se.spi.orb.ORB; 34 import com.sun.corba.se.spi.ior.IOR ; 35 import com.sun.corba.se.spi.oa.ObjectAdapterFactory; 36 37 import com.sun.corba.se.spi.ior.ObjectAdapterId; 38 import com.sun.corba.se.spi.ior.TaggedProfile; 39 import com.sun.corba.se.spi.ior.ObjectKeyTemplate; 40 import com.sun.corba.se.spi.ior.ObjectId; 41 42 public abstract class LocalClientRequestDispatcherBase implements LocalClientRequestDispatcher 43 { 44 protected ORB orb; 45 int scid; 46 47 // Cached information needed for local dispatch 48 protected boolean servantIsLocal ; 49 protected ObjectAdapterFactory oaf ; 50 protected ObjectAdapterId oaid ; 51 protected byte[] objectId ; 52 53 // If isNextIsLocalValid.get() == Boolean.TRUE, 54 // the next call to isLocal should be valid 55 private static final ThreadLocal isNextCallValid = new ThreadLocal() { 56 protected synchronized Object initialValue() { 57 return Boolean.TRUE; 58 } 59 }; 60 61 protected LocalClientRequestDispatcherBase(ORB orb, int scid, IOR ior) 62 { 63 this.orb = orb ; 64 65 TaggedProfile prof = ior.getProfile() ; 66 servantIsLocal = orb.getORBData().isLocalOptimizationAllowed() && 67 prof.isLocal(); 68 69 ObjectKeyTemplate oktemp = prof.getObjectKeyTemplate() ; 70 this.scid = oktemp.getSubcontractId() ; 71 RequestDispatcherRegistry sreg = orb.getRequestDispatcherRegistry() ; 72 oaf = sreg.getObjectAdapterFactory( scid ) ; 73 oaid = oktemp.getObjectAdapterId() ; 74 ObjectId oid = prof.getObjectId() ; 75 objectId = oid.getId() ; 76 } 77 78 public byte[] getObjectId() 79 { 80 return objectId ; 81 } 82 83 public boolean is_local(org.omg.CORBA.Object self) 84 { 85 return false; 86 } 87 88 /* 89 * Possible paths through 90 * useLocalInvocation/servant_preinvoke/servant_postinvoke: 91 * 92 * A: call useLocalInvocation 93 * If useLocalInvocation returns false, servant_preinvoke is not called. 94 * If useLocalInvocation returns true, 95 * call servant_preinvoke 96 * If servant_preinvoke returns null, 97 * goto A 98 * else 99 * (local invocation proceeds normally) 100 * servant_postinvoke is called 101 * 102 */ 103 public boolean useLocalInvocation( org.omg.CORBA.Object self ) 104 { 105 if (isNextCallValid.get() == Boolean.TRUE) 106 return servantIsLocal ; 107 else 108 isNextCallValid.set( Boolean.TRUE ) ; 109 110 return false ; 111 } 112 113 /** Check that the servant in info (which must not be null) is 114 * an instance of the expectedType. If not, set the thread local flag 115 * and return false. 116 */ 117 protected boolean checkForCompatibleServant( ServantObject so, 118 Class expectedType ) 119 { 120 if (so == null) 121 return false ; 122 123 // Normally, this test will never fail. However, if the servant 124 // and the stub were loaded in different class loaders, this test 125 // will fail. 126 if (!expectedType.isInstance( so.servant )) { 127 isNextCallValid.set( Boolean.FALSE ) ; 128 129 // When servant_preinvoke returns null, the stub will 130 // recursively re-invoke itself. Thus, the next call made from 131 // the stub is another useLocalInvocation call. 132 return false ; 133 } 134 135 return true ; 136 } 137 138 } 139 140 // End of file.