Introduce connector, to help subchannel connect
diff --git a/BUILD b/BUILD
index 29cc773..e6087a0 100644
--- a/BUILD
+++ b/BUILD
@@ -157,6 +157,7 @@
     "src/core/channel/http_server_filter.h",
     "src/core/channel/noop_filter.h",
     "src/core/client_config/client_config.h",
+    "src/core/client_config/connector.h",
     "src/core/client_config/lb_policies/pick_first.h",
     "src/core/client_config/lb_policy.h",
     "src/core/client_config/resolver.h",
@@ -271,6 +272,7 @@
     "src/core/channel/http_server_filter.c",
     "src/core/channel/noop_filter.c",
     "src/core/client_config/client_config.c",
+    "src/core/client_config/connector.c",
     "src/core/client_config/lb_policies/pick_first.c",
     "src/core/client_config/lb_policy.c",
     "src/core/client_config/resolver.c",
@@ -403,6 +405,7 @@
     "src/core/channel/http_server_filter.h",
     "src/core/channel/noop_filter.h",
     "src/core/client_config/client_config.h",
+    "src/core/client_config/connector.h",
     "src/core/client_config/lb_policies/pick_first.h",
     "src/core/client_config/lb_policy.h",
     "src/core/client_config/resolver.h",
@@ -495,6 +498,7 @@
     "src/core/channel/http_server_filter.c",
     "src/core/channel/noop_filter.c",
     "src/core/client_config/client_config.c",
+    "src/core/client_config/connector.c",
     "src/core/client_config/lb_policies/pick_first.c",
     "src/core/client_config/lb_policy.c",
     "src/core/client_config/resolver.c",
diff --git a/Makefile b/Makefile
index 7ca182d..a58ef8f 100644
--- a/Makefile
+++ b/Makefile
@@ -3022,6 +3022,7 @@
     src/core/channel/http_server_filter.c \
     src/core/channel/noop_filter.c \
     src/core/client_config/client_config.c \
+    src/core/client_config/connector.c \
     src/core/client_config/lb_policies/pick_first.c \
     src/core/client_config/lb_policy.c \
     src/core/client_config/resolver.c \
@@ -3279,6 +3280,7 @@
     src/core/channel/http_server_filter.c \
     src/core/channel/noop_filter.c \
     src/core/client_config/client_config.c \
+    src/core/client_config/connector.c \
     src/core/client_config/lb_policies/pick_first.c \
     src/core/client_config/lb_policy.c \
     src/core/client_config/resolver.c \
diff --git a/build.json b/build.json
index dc3d2ac..5534843 100644
--- a/build.json
+++ b/build.json
@@ -118,6 +118,7 @@
         "src/core/channel/http_server_filter.h",
         "src/core/channel/noop_filter.h",
         "src/core/client_config/client_config.h",
+        "src/core/client_config/connector.h",
         "src/core/client_config/lb_policies/pick_first.h",
         "src/core/client_config/lb_policy.h",
         "src/core/client_config/resolver.h",
@@ -210,6 +211,7 @@
         "src/core/channel/http_server_filter.c",
         "src/core/channel/noop_filter.c",
         "src/core/client_config/client_config.c",
+        "src/core/client_config/connector.c",
         "src/core/client_config/lb_policies/pick_first.c",
         "src/core/client_config/lb_policy.c",
         "src/core/client_config/resolver.c",
diff --git a/gRPC.podspec b/gRPC.podspec
index 1707ee7..862c24b 100644
--- a/gRPC.podspec
+++ b/gRPC.podspec
@@ -159,6 +159,7 @@
                       'src/core/channel/http_server_filter.h',
                       'src/core/channel/noop_filter.h',
                       'src/core/client_config/client_config.h',
+                      'src/core/client_config/connector.h',
                       'src/core/client_config/lb_policies/pick_first.h',
                       'src/core/client_config/lb_policy.h',
                       'src/core/client_config/resolver.h',
@@ -280,6 +281,7 @@
                       'src/core/channel/http_server_filter.c',
                       'src/core/channel/noop_filter.c',
                       'src/core/client_config/client_config.c',
+                      'src/core/client_config/connector.c',
                       'src/core/client_config/lb_policies/pick_first.c',
                       'src/core/client_config/lb_policy.c',
                       'src/core/client_config/resolver.c',
@@ -411,6 +413,7 @@
                               'src/core/channel/http_server_filter.h',
                               'src/core/channel/noop_filter.h',
                               'src/core/client_config/client_config.h',
+                              'src/core/client_config/connector.h',
                               'src/core/client_config/lb_policies/pick_first.h',
                               'src/core/client_config/lb_policy.h',
                               'src/core/client_config/resolver.h',
diff --git a/src/core/channel/channel_args.h b/src/core/channel/channel_args.h
index bf747b2..41f3a55 100644
--- a/src/core/channel/channel_args.h
+++ b/src/core/channel/channel_args.h
@@ -45,6 +45,8 @@
 grpc_channel_args *grpc_channel_args_copy_and_add(const grpc_channel_args *src,
                                                   const grpc_arg *to_add);
 
+grpc_channel_args *grpc_channel_args_merge(const grpc_channel_args *a, const grpc_channel_args *b);
+
 /** Destroy arguments created by grpc_channel_args_copy */
 void grpc_channel_args_destroy(grpc_channel_args *a);
 
diff --git a/src/core/client_config/connector.c b/src/core/client_config/connector.c
new file mode 100644
index 0000000..c9115ac
--- /dev/null
+++ b/src/core/client_config/connector.c
@@ -0,0 +1,35 @@
+/*
+ *
+ * Copyright 2015, Google Inc.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ *     * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *     * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ *     * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ */
+
+#include "src/core/client_config/connector.h"
+
diff --git a/src/core/client_config/connector.h b/src/core/client_config/connector.h
new file mode 100644
index 0000000..0985432
--- /dev/null
+++ b/src/core/client_config/connector.h
@@ -0,0 +1,56 @@
+/*
+ *
+ * Copyright 2015, Google Inc.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ *     * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *     * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ *     * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ */
+
+#ifndef GRPC_INTERNAL_CORE_CLIENT_CONFIG_CONNECTOR_H
+#define GRPC_INTERNAL_CORE_CLIENT_CONFIG_CONNECTOR_H
+
+#include "src/core/transport/transport.h"
+
+typedef struct grpc_connector grpc_connector;
+typedef struct grpc_connector_vtable grpc_connector_vtable;
+
+struct grpc_connector {
+  const grpc_connector_vtable *vtable;
+};
+
+struct grpc_connector_vtable {
+  void (*ref)(grpc_connector *connector);
+  void (*unref)(grpc_connector *connector);
+  void (*connect)(grpc_connector *connector, const grpc_channel_args *channel_args, grpc_mdctx *metadata_context, grpc_transport **transport, grpc_iomgr_closure *notify);
+};
+
+void grpc_connector_ref(grpc_connector *connector);
+void grpc_connector_unref(grpc_connector *connector);
+void grpc_connector_connect(grpc_connector *connector, const grpc_channel_args *channel_args, grpc_mdctx *metadata_context, grpc_transport **transport, grpc_iomgr_closure *notify);
+
+#endif
diff --git a/src/core/client_config/subchannel.c b/src/core/client_config/subchannel.c
index e268949..588c63c 100644
--- a/src/core/client_config/subchannel.c
+++ b/src/core/client_config/subchannel.c
@@ -37,6 +37,7 @@
 
 struct grpc_subchannel {
   gpr_refcount refs;
+  grpc_connector *connector;
 };
 
 struct grpc_subchannel_call {
diff --git a/src/core/client_config/subchannel.h b/src/core/client_config/subchannel.h
index 4d2efef..ab24123 100644
--- a/src/core/client_config/subchannel.h
+++ b/src/core/client_config/subchannel.h
@@ -35,9 +35,7 @@
 #define GRPC_INTERNAL_CORE_CLIENT_CONFIG_SUBCHANNEL_H
 
 #include "src/core/channel/channel_stack.h"
-#include "src/core/iomgr/iomgr.h"
-#include "src/core/iomgr/sockaddr.h"
-#include "src/core/transport/transport.h"
+#include "src/core/client_config/connector.h"
 
 /** A (sub-)channel that knows how to connect to exactly one target
     address. Provides a target for load balancing. */
@@ -60,7 +58,7 @@
                                             grpc_connectivity_state *state,
                                             grpc_iomgr_closure *notify);
 
-/** construct a call (asynchronously) */
+/** construct a call (possibly asynchronously) */
 void grpc_subchannel_create_call(grpc_subchannel *subchannel,
                                  grpc_call_element *parent,
                                  grpc_transport_stream_op *initial_op,
@@ -71,4 +69,7 @@
 void grpc_subchannel_call_process_op(grpc_subchannel_call *subchannel_call,
                                      grpc_transport_stream_op *op);
 
+/** create a subchannel given a connector */
+grpc_subchannel *grpc_subchannel_create(grpc_connector *connector);
+
 #endif /* GRPC_INTERNAL_CORE_CLIENT_CONFIG_SUBCHANNEL_H */
diff --git a/src/core/surface/channel_create.c b/src/core/surface/channel_create.c
index 14ff63a..2d63d7e 100644
--- a/src/core/surface/channel_create.c
+++ b/src/core/surface/channel_create.c
@@ -36,10 +36,55 @@
 #include <stdlib.h>
 #include <string.h>
 
+#include <grpc/support/alloc.h>
+
+#include "src/core/channel/channel_args.h"
 #include "src/core/channel/client_channel.h"
 #include "src/core/client_config/resolver_registry.h"
 #include "src/core/surface/channel.h"
 
+typedef struct {
+  grpc_connector base;
+  gpr_refcount refs;
+  struct sockaddr *addr;
+  int addr_len;
+  grpc_channel_args *args;
+} connector;
+
+typedef struct {
+  grpc_subchannel_factory base;
+  gpr_refcount refs;
+  grpc_channel_args *args;
+} subchannel_factory;
+
+static void subchannel_factory_ref(grpc_subchannel_factory *scf) {
+  subchannel_factory *f = (subchannel_factory*)scf;
+  gpr_ref(&f->refs);
+}
+
+static void subchannel_factory_unref(grpc_subchannel_factory *scf) {
+  subchannel_factory *f = (subchannel_factory*)scf;
+  if (gpr_unref(&f->refs)) {
+    grpc_channel_args_destroy(f->args);
+    gpr_free(f);
+  }
+}
+
+static grpc_subchannel *subchannel_factory_create_subchannel(grpc_subchannel_factory *scf, grpc_subchannel_args *args) {
+  subchannel_factory *f = (subchannel_factory*)scf;
+  connector *c = gpr_malloc(sizeof(*c));
+  c->base.vtable = &connector_vtable;
+  gpr_ref_init(&c->refs, 1);
+  c->addr = gpr_malloc(args->addr_len);
+  memcpy(c->addr, args->addr, args->addr_len);
+  c->addr_len = args->addr_len;
+  c->args = grpc_channel_args_merge(args->args, f->args);
+
+  return grpc_subchannel_create(&c->base);
+}
+
+static const grpc_subchannel_factory_vtable subchannel_factory_vtable = {subchannel_factory_ref, subchannel_factory_unref, subchannel_factory_create_subchannel};
+
 /* Create a client channel:
    Asynchronously: - resolve target
                    - connect to it (trying alternatives as presented)
@@ -47,6 +92,7 @@
 grpc_channel *grpc_channel_create(const char *target,
                                   const grpc_channel_args *args) {
   grpc_channel *channel = NULL;
+  subchannel_factory *scfactory = gpr_malloc(sizeof(*scfactory));
 #define MAX_FILTERS 3
   const grpc_channel_filter *filters[MAX_FILTERS];
   grpc_resolver *resolver;
@@ -58,8 +104,11 @@
   filters[n++] = &grpc_client_channel_filter;
   GPR_ASSERT(n <= MAX_FILTERS);
 
-  GPR_ASSERT(!"NULL should be a subchannel factory creation below");
-  resolver = grpc_resolver_create(target, NULL);
+  scfactory->base.vtable = &subchannel_factory_vtable;
+  gpr_ref_init(&scfactory->refs, 1);
+  scfactory->args = grpc_channel_args_copy(args);
+
+  resolver = grpc_resolver_create(target, &scfactory->base);
   if (!resolver) {
     return NULL;
   }
diff --git a/tools/doxygen/Doxyfile.core.internal b/tools/doxygen/Doxyfile.core.internal
index bc2cfaf..56af4ce 100644
--- a/tools/doxygen/Doxyfile.core.internal
+++ b/tools/doxygen/Doxyfile.core.internal
@@ -794,6 +794,7 @@
 src/core/channel/http_server_filter.h \
 src/core/channel/noop_filter.h \
 src/core/client_config/client_config.h \
+src/core/client_config/connector.h \
 src/core/client_config/lb_policies/pick_first.h \
 src/core/client_config/lb_policy.h \
 src/core/client_config/resolver.h \
@@ -908,6 +909,7 @@
 src/core/channel/http_server_filter.c \
 src/core/channel/noop_filter.c \
 src/core/client_config/client_config.c \
+src/core/client_config/connector.c \
 src/core/client_config/lb_policies/pick_first.c \
 src/core/client_config/lb_policy.c \
 src/core/client_config/resolver.c \
diff --git a/vsprojects/grpc/grpc.vcxproj b/vsprojects/grpc/grpc.vcxproj
index 6c55c4f..8544439 100644
--- a/vsprojects/grpc/grpc.vcxproj
+++ b/vsprojects/grpc/grpc.vcxproj
@@ -183,6 +183,7 @@
     <ClInclude Include="..\..\src\core\channel\http_server_filter.h" />
     <ClInclude Include="..\..\src\core\channel\noop_filter.h" />
     <ClInclude Include="..\..\src\core\client_config\client_config.h" />
+    <ClInclude Include="..\..\src\core\client_config\connector.h" />
     <ClInclude Include="..\..\src\core\client_config\lb_policies\pick_first.h" />
     <ClInclude Include="..\..\src\core\client_config\lb_policy.h" />
     <ClInclude Include="..\..\src\core\client_config\resolver.h" />
@@ -331,6 +332,8 @@
     </ClCompile>
     <ClCompile Include="..\..\src\core\client_config\client_config.c">
     </ClCompile>
+    <ClCompile Include="..\..\src\core\client_config\connector.c">
+    </ClCompile>
     <ClCompile Include="..\..\src\core\client_config\lb_policies\pick_first.c">
     </ClCompile>
     <ClCompile Include="..\..\src\core\client_config\lb_policy.c">
diff --git a/vsprojects/grpc/grpc.vcxproj.filters b/vsprojects/grpc/grpc.vcxproj.filters
index d2ada43..2c02e4a 100644
--- a/vsprojects/grpc/grpc.vcxproj.filters
+++ b/vsprojects/grpc/grpc.vcxproj.filters
@@ -97,6 +97,9 @@
     <ClCompile Include="..\..\src\core\client_config\client_config.c">
       <Filter>src\core\client_config</Filter>
     </ClCompile>
+    <ClCompile Include="..\..\src\core\client_config\connector.c">
+      <Filter>src\core\client_config</Filter>
+    </ClCompile>
     <ClCompile Include="..\..\src\core\client_config\lb_policies\pick_first.c">
       <Filter>src\core\client_config\lb_policies</Filter>
     </ClCompile>
@@ -494,6 +497,9 @@
     <ClInclude Include="..\..\src\core\client_config\client_config.h">
       <Filter>src\core\client_config</Filter>
     </ClInclude>
+    <ClInclude Include="..\..\src\core\client_config\connector.h">
+      <Filter>src\core\client_config</Filter>
+    </ClInclude>
     <ClInclude Include="..\..\src\core\client_config\lb_policies\pick_first.h">
       <Filter>src\core\client_config\lb_policies</Filter>
     </ClInclude>
diff --git a/vsprojects/grpc_unsecure/grpc_unsecure.vcxproj b/vsprojects/grpc_unsecure/grpc_unsecure.vcxproj
index 09b3997..9080bff 100644
--- a/vsprojects/grpc_unsecure/grpc_unsecure.vcxproj
+++ b/vsprojects/grpc_unsecure/grpc_unsecure.vcxproj
@@ -165,6 +165,7 @@
     <ClInclude Include="..\..\src\core\channel\http_server_filter.h" />
     <ClInclude Include="..\..\src\core\channel\noop_filter.h" />
     <ClInclude Include="..\..\src\core\client_config\client_config.h" />
+    <ClInclude Include="..\..\src\core\client_config\connector.h" />
     <ClInclude Include="..\..\src\core\client_config\lb_policies\pick_first.h" />
     <ClInclude Include="..\..\src\core\client_config\lb_policy.h" />
     <ClInclude Include="..\..\src\core\client_config\resolver.h" />
@@ -269,6 +270,8 @@
     </ClCompile>
     <ClCompile Include="..\..\src\core\client_config\client_config.c">
     </ClCompile>
+    <ClCompile Include="..\..\src\core\client_config\connector.c">
+    </ClCompile>
     <ClCompile Include="..\..\src\core\client_config\lb_policies\pick_first.c">
     </ClCompile>
     <ClCompile Include="..\..\src\core\client_config\lb_policy.c">
diff --git a/vsprojects/grpc_unsecure/grpc_unsecure.vcxproj.filters b/vsprojects/grpc_unsecure/grpc_unsecure.vcxproj.filters
index 3b65c46..3861eef 100644
--- a/vsprojects/grpc_unsecure/grpc_unsecure.vcxproj.filters
+++ b/vsprojects/grpc_unsecure/grpc_unsecure.vcxproj.filters
@@ -31,6 +31,9 @@
     <ClCompile Include="..\..\src\core\client_config\client_config.c">
       <Filter>src\core\client_config</Filter>
     </ClCompile>
+    <ClCompile Include="..\..\src\core\client_config\connector.c">
+      <Filter>src\core\client_config</Filter>
+    </ClCompile>
     <ClCompile Include="..\..\src\core\client_config\lb_policies\pick_first.c">
       <Filter>src\core\client_config\lb_policies</Filter>
     </ClCompile>
@@ -377,6 +380,9 @@
     <ClInclude Include="..\..\src\core\client_config\client_config.h">
       <Filter>src\core\client_config</Filter>
     </ClInclude>
+    <ClInclude Include="..\..\src\core\client_config\connector.h">
+      <Filter>src\core\client_config</Filter>
+    </ClInclude>
     <ClInclude Include="..\..\src\core\client_config\lb_policies\pick_first.h">
       <Filter>src\core\client_config\lb_policies</Filter>
     </ClInclude>