code: private void _addSubtreeClientId(String clientId)
    {
      // Loop over the client id and find the substring corresponding to
      // each ancestor NamingContainer client id.  For each ancestor
      // NamingContainer, add an entry into the map for the full client
      // id.
      final char separator = getFacesContext().getNamingContainerSeparatorChar();
      
      int length = clientId.length();
  
      for (int i = 0; i < length; i++)
      {
        if (clientId.charAt(i) == separator)
        {
          // We found an ancestor NamingContainer client id - add 
          // an entry to the map.
          String namingContainerClientId = clientId.substring(0, i);
  
          // Check to see whether we've already ids under this
          // NamingContainer client id.  If not, create the 
          // Collection for this NamingContainer client id and
          // stash it away in our map
          Collection<String> c = _subtreeClientIds.get(namingContainerClientId);
  
          if (c == null)
          {
            // TODO: smarter initial size?
            c = new ArrayList<String>();
            _subtreeClientIds.put(namingContainerClientId, c);
          }
  
          // Stash away the client id
          c.add(clientId);
        }
      }
    }
docs: subtree client ids