Logo Search packages:      
Sourcecode: zeroc-ice-java version File versions  Download package

ReferenceFactory.java

// **********************************************************************
//
// Copyright (c) 2003-2006 ZeroC, Inc. All rights reserved.
//
// This copy of Ice is licensed to you under the terms described in the
// ICE_LICENSE file included in this distribution.
//
// **********************************************************************

package IceInternal;

public final class ReferenceFactory
{
    public synchronized Reference
    create(Ice.Identity ident,
           java.util.Map context,
           String facet,
           int mode,
           boolean secure,
           EndpointI[] endpoints,
           RouterInfo routerInfo,
         boolean collocationOptimization)
    {
        if(_instance == null)
        {
            throw new Ice.CommunicatorDestroyedException();
        }

        if(ident.name.length() == 0 && ident.category.length() == 0)
        {
            return null;
        }

        //
        // Create new reference
        //
        DirectReference ref = new DirectReference(_instance, _communicator, ident, context, facet, mode, secure,
                                      endpoints, routerInfo, collocationOptimization);
      return updateCache(ref);
    }

    public synchronized Reference
    create(Ice.Identity ident,
           java.util.Map context,
           String facet,
           int mode,
           boolean secure,
           String adapterId,
           RouterInfo routerInfo,
         LocatorInfo locatorInfo,
         boolean collocationOptimization,
         int locatorCacheTimeout)
    {
        if(_instance == null)
        {
            throw new Ice.CommunicatorDestroyedException();
        }

        if(ident.name.length() == 0 && ident.category.length() == 0)
        {
            return null;
        }

        //
        // Create new reference
        //
        IndirectReference ref = new IndirectReference(_instance, _communicator, ident, context, facet, mode, secure,
                                          adapterId, routerInfo, locatorInfo, collocationOptimization,
                                          locatorCacheTimeout);
      return updateCache(ref);
    }

    public synchronized Reference
    create(Ice.Identity ident,
           java.util.Map context,
           String facet,
           int mode,
         Ice.ConnectionI[] fixedConnections)
    {
        if(_instance == null)
        {
            throw new Ice.CommunicatorDestroyedException();
        }

        if(ident.name.length() == 0 && ident.category.length() == 0)
        {
            return null;
        }

        //
        // Create new reference
        //
        FixedReference ref = new FixedReference(_instance, _communicator, ident, context, facet, mode,
                                    fixedConnections);
      return updateCache(ref);
    }

    public synchronized Reference
    copy(Reference r)
    {
        if(_instance == null)
      {
          throw new Ice.CommunicatorDestroyedException();
      }

      Ice.Identity ident = r.getIdentity();
      if(ident.name.length() == 0 && ident.category.length() == 0)
      {
          return null;
      }
      return (Reference)r.clone();
    }

    public Reference
    create(String s)
    {
        if(s == null || s.length() == 0)
        {
            return null;
        }

        final String delim = " \t\n\r";

        int beg;
        int end = 0;

        beg = IceUtil.StringUtil.findFirstNotOf(s, delim, end);
        if(beg == -1)
        {
            Ice.ProxyParseException e = new Ice.ProxyParseException();
          e.str = s;
          throw e;
        }

        //
        // Extract the identity, which may be enclosed in single
        // or double quotation marks.
        //
        String idstr = null;
        end = IceUtil.StringUtil.checkQuote(s, beg);
        if(end == -1)
        {
            Ice.ProxyParseException e = new Ice.ProxyParseException();
          e.str = s;
          throw e;
        }
        else if(end == 0)
        {
            end = IceUtil.StringUtil.findFirstOf(s, delim + ":@", beg);
            if(end == -1)
            {
                end = s.length();
            }
            idstr = s.substring(beg, end);
        }
        else
        {
            beg++; // Skip leading quote
            idstr = s.substring(beg, end);
            end++; // Skip trailing quote
        }

        if(beg == end)
        {
            Ice.ProxyParseException e = new Ice.ProxyParseException();
          e.str = s;
          throw e;
        }

        //
        // Parsing the identity may raise IdentityParseException.
        //
        Ice.Identity ident = _instance.stringToIdentity(idstr);

        if(ident.name.length() == 0)
        {
            //
            // An identity with an empty name and a non-empty
            // category is illegal.
            //
            if(ident.category.length() > 0)
            {
                Ice.IllegalIdentityException e = new Ice.IllegalIdentityException();
                e.id = ident;
                throw e;
            }
            //
            // Treat a stringified proxy containing two double
            // quotes ("") the same as an empty string, i.e.,
            // a null proxy, but only if nothing follows the
            // quotes.
            //
            else if(IceUtil.StringUtil.findFirstNotOf(s, delim, end) != -1)
            {
                Ice.ProxyParseException e = new Ice.ProxyParseException();
                e.str = s;
                throw e;
            }
            else
            {
                return null;
            }
        }

        String facet = "";
        int mode = Reference.ModeTwoway;
        boolean secure = false;
      String adapter = "";

        while(true)
        {
            beg = IceUtil.StringUtil.findFirstNotOf(s, delim, end);
            if(beg == -1)
            {
                break;
            }

            if(s.charAt(beg) == ':' || s.charAt(beg) == '@')
            {
                break;
            }

            end = IceUtil.StringUtil.findFirstOf(s, delim + ":@", beg);
            if(end == -1)
            {
                end = s.length();
            }

            if(beg == end)
            {
                break;
            }

            String option = s.substring(beg, end);
            if(option.length() != 2 || option.charAt(0) != '-')
            {
                Ice.ProxyParseException e = new Ice.ProxyParseException();
            e.str = s;
            throw e;
            }

            //
            // Check for the presence of an option argument. The
            // argument may be enclosed in single or double
            // quotation marks.
            //
            String argument = null;
            int argumentBeg = IceUtil.StringUtil.findFirstNotOf(s, delim, end);
            if(argumentBeg != -1)
            {
                final char ch = s.charAt(argumentBeg);
                if(ch != '@' && ch != ':' && ch != '-')
                {
                    beg = argumentBeg;
                    end = IceUtil.StringUtil.checkQuote(s, beg);
                    if(end == -1)
                    {
                        Ice.ProxyParseException e = new Ice.ProxyParseException();
                  e.str = s;
                  throw e;
                    }
                    else if(end == 0)
                    {
                        end = IceUtil.StringUtil.findFirstOf(s, delim + ":@", beg);
                        if(end == -1)
                        {
                            end = s.length();
                        }
                        argument = s.substring(beg, end);
                    }
                    else
                    {
                        beg++; // Skip leading quote
                        argument = s.substring(beg, end);
                        end++; // Skip trailing quote
                    }
                }
            }

            //
            // If any new options are added here,
            // IceInternal::Reference::toString() and its derived classes must be updated as well.
            //
            switch(option.charAt(1))
            {
                case 'f':
                {
                    if(argument == null)
                    {
                        Ice.ProxyParseException e = new Ice.ProxyParseException();
                  e.str = s;
                  throw e;
                    }

                    Ice.StringHolder facetH = new Ice.StringHolder();
                    if(!IceUtil.StringUtil.unescapeString(argument, 0, argument.length(), facetH))
                    {
                        Ice.ProxyParseException e = new Ice.ProxyParseException();
                  e.str = s;
                  throw e;
                    }

                    facet = facetH.value;
                    break;
                }

                case 't':
                {
                    if(argument != null)
                    {
                        Ice.ProxyParseException e = new Ice.ProxyParseException();
                  e.str = s;
                  throw e;
                    }
                    mode = Reference.ModeTwoway;
                    break;
                }

                case 'o':
                {
                    if(argument != null)
                    {
                        Ice.ProxyParseException e = new Ice.ProxyParseException();
                  e.str = s;
                  throw e;
                    }
                    mode = Reference.ModeOneway;
                    break;
                }

                case 'O':
                {
                    if(argument != null)
                    {
                        Ice.ProxyParseException e = new Ice.ProxyParseException();
                  e.str = s;
                  throw e;
                    }
                    mode = Reference.ModeBatchOneway;
                    break;
                }

                case 'd':
                {
                    if(argument != null)
                    {
                        Ice.ProxyParseException e = new Ice.ProxyParseException();
                  e.str = s;
                  throw e;
                    }
                    mode = Reference.ModeDatagram;
                    break;
                }

                case 'D':
                {
                    if(argument != null)
                    {
                        Ice.ProxyParseException e = new Ice.ProxyParseException();
                  e.str = s;
                  throw e;
                    }
                    mode = Reference.ModeBatchDatagram;
                    break;
                }

                case 's':
                {
                    if(argument != null)
                    {
                        Ice.ProxyParseException e = new Ice.ProxyParseException();
                  e.str = s;
                  throw e;
                    }
                    secure = true;
                    break;
                }

                default:
                {
                    Ice.ProxyParseException e = new Ice.ProxyParseException();
                e.str = s;
                throw e;
                }
            }
        }

      RouterInfo routerInfo = _instance.routerManager().get(getDefaultRouter());
      LocatorInfo locatorInfo = _instance.locatorManager().get(getDefaultLocator());

      if(beg == -1)
      {
          return create(ident, _instance.getDefaultContext(), facet, mode, secure, "", routerInfo,
                    locatorInfo, _instance.defaultsAndOverrides().defaultCollocationOptimization,
                    _instance.defaultsAndOverrides().defaultLocatorCacheTimeout);
      }

        java.util.ArrayList endpoints = new java.util.ArrayList();

      if(s.charAt(beg) == ':')
      {
          java.util.ArrayList unknownEndpoints = new java.util.ArrayList();
          end = beg;

          while(end < s.length() && s.charAt(end) == ':')
          {
            beg = end + 1;
            
            end = s.indexOf(':', beg);
            if(end == -1)
            {
                end = s.length();
            }
            
            String es = s.substring(beg, end);
            EndpointI endp = _instance.endpointFactoryManager().create(es);
            if(endp != null)
            {
                java.util.ArrayList endps = endp.expand(false);
                endpoints.addAll(endps);
            }
            else
            {
                unknownEndpoints.add(es);
            }
          }
          if(endpoints.size() == 0)
          {
              Ice.EndpointParseException e = new Ice.EndpointParseException();
            e.str = (String)unknownEndpoints.get(0);
            throw e;
          }
          else if(unknownEndpoints.size() != 0 &&
                 _instance.initializationData().properties.getPropertyAsIntWithDefault("Ice.Warn.Endpoints", 1) > 0)
          {
              String msg = "Proxy contains unknown endpoints:";
            java.util.Iterator iter = unknownEndpoints.iterator();
            while(iter.hasNext())
            {
                msg += " `" + (String)iter.next() + "'";
            }
            _instance.initializationData().logger.warning(msg);
          }

          EndpointI[] endp = new EndpointI[endpoints.size()];
          endpoints.toArray(endp);
          return create(ident, _instance.getDefaultContext(), facet, mode, secure, endp, routerInfo,
                    _instance.defaultsAndOverrides().defaultCollocationOptimization);
      }
      else if(s.charAt(beg) == '@')
      {
          beg = IceUtil.StringUtil.findFirstNotOf(s, delim, beg + 1);
          if(beg == -1)
          {
            Ice.ProxyParseException e = new Ice.ProxyParseException();
            e.str = s;
            throw e;
          }

          end = IceUtil.StringUtil.checkQuote(s, beg);
          if(end == -1)
          {
            Ice.ProxyParseException e = new Ice.ProxyParseException();
            e.str = s;
            throw e;
          }
          else if(end == 0)
          {
            end = IceUtil.StringUtil.findFirstOf(s, delim, beg);
            if(end == -1)
            {
                end = s.length();
            }
          }
          else
          {
            beg++; // Skip leading quote
          }

          Ice.StringHolder token = new Ice.StringHolder();
          if(!IceUtil.StringUtil.unescapeString(s, beg, end, token) || token.value.length() == 0)
          {
            Ice.ProxyParseException e = new Ice.ProxyParseException();
            e.str = s;
            throw e;
          }
          adapter = token.value;
          return create(ident, _instance.getDefaultContext(), facet, mode, secure, adapter,
                    routerInfo, locatorInfo, _instance.defaultsAndOverrides().defaultCollocationOptimization,
                    _instance.defaultsAndOverrides().defaultLocatorCacheTimeout);
      }

      Ice.ProxyParseException ex = new Ice.ProxyParseException();
      ex.str = s;
      throw ex;
    }

    public Reference
    create(Ice.Identity ident, BasicStream s)
    {
        //
        // Don't read the identity here. Operations calling this
        // constructor read the identity, and pass it as a parameter.
        //

        if(ident.name.length() == 0 && ident.category.length() == 0)
        {
            return null;
        }

        //
        // For compatibility with the old FacetPath.
        //
        String[] facetPath = s.readStringSeq();
        String facet;
        if(facetPath.length > 0)
        {
          if(facetPath.length > 1)
          {
              throw new Ice.ProxyUnmarshalException();
          }
            facet = facetPath[0];
        }
      else
        {
          facet = "";
      }

        int mode = (int)s.readByte();
        if(mode < 0 || mode > Reference.ModeLast)
        {
            throw new Ice.ProxyUnmarshalException();
        }

        boolean secure = s.readBool();

        EndpointI[] endpoints;
      String adapterId = "";

        RouterInfo routerInfo = _instance.routerManager().get(getDefaultRouter());
        LocatorInfo locatorInfo = _instance.locatorManager().get(getDefaultLocator());

        int sz = s.readSize();
      if(sz > 0)
      {
          endpoints = new EndpointI[sz];
          for(int i = 0; i < sz; i++)
          {
            endpoints[i] = _instance.endpointFactoryManager().read(s);
          }
          return create(ident, _instance.getDefaultContext(), facet, mode, secure, endpoints,
                    routerInfo, _instance.defaultsAndOverrides().defaultCollocationOptimization);
      }
      else
      {
          endpoints = new EndpointI[0];
          adapterId = s.readString();
          return create(ident, _instance.getDefaultContext(), facet, mode, secure,
                        adapterId, routerInfo, locatorInfo,
                    _instance.defaultsAndOverrides().defaultCollocationOptimization,
                    _instance.defaultsAndOverrides().defaultLocatorCacheTimeout);
      }
    }

    public synchronized void
    setDefaultRouter(Ice.RouterPrx defaultRouter)
    {
        _defaultRouter = defaultRouter;
    }

    public synchronized Ice.RouterPrx
    getDefaultRouter()
    {
        return _defaultRouter;
    }

    public synchronized void
    setDefaultLocator(Ice.LocatorPrx defaultLocator)
    {
        _defaultLocator = defaultLocator;
    }

    public synchronized Ice.LocatorPrx
    getDefaultLocator()
    {
        return _defaultLocator;
    }

    //
    // Only for use by Instance
    //
    ReferenceFactory(Instance instance, Ice.Communicator communicator)
    {
        _instance = instance;
        _communicator = communicator;
    }

    synchronized void
    destroy()
    {
        if(_instance == null)
        {
            throw new Ice.CommunicatorDestroyedException();
        }

        _instance = null;
        _communicator = null;
        _defaultRouter = null;
        _defaultLocator = null;
        _references.clear();
    }

    private Reference
    updateCache(Reference ref)
    {
        //
        // If we already have an equivalent reference, use such equivalent
        // reference. Otherwise add the new reference to the reference
        // set.
        //
        // Java implementation note: A WeakHashMap is used to hold References,
        // allowing References to be garbage collected automatically. A
        // Reference serves as both key and value in the map. The
        // WeakHashMap class internally creates a weak reference for the
        // key, and we use a weak reference for the value as well.
        //
        java.lang.ref.WeakReference w = (java.lang.ref.WeakReference)_references.get(ref);
        if(w != null)
        {
            Reference r = (Reference)w.get();
            if(r != null)
            {
                ref = r;
            }
            else
            {
                _references.put(ref, new java.lang.ref.WeakReference(ref));
            }
        }
        else
        {
            _references.put(ref, new java.lang.ref.WeakReference(ref));
        }

        return ref;
    }

    private Instance _instance;
    private Ice.Communicator _communicator;
    private Ice.RouterPrx _defaultRouter;
    private Ice.LocatorPrx _defaultLocator;
    private java.util.WeakHashMap _references = new java.util.WeakHashMap();
}

Generated by  Doxygen 1.6.0   Back to index