Added support for default credentials.

- Tested with new tool (print_default_creds_token) on:
  - workstation for env var and well known place.
  - GCE for compute engine default creds.
- I'd prefer the grpc_default_credentials_create() API to remain
  synchronous even though there may be an async call for gce detection
  on which we block.
diff --git a/Makefile b/Makefile
index 08f5ba2..b60f22d 100644
--- a/Makefile
+++ b/Makefile
@@ -481,6 +481,7 @@
 grpc_credentials_test: $(BINDIR)/$(CONFIG)/grpc_credentials_test
 grpc_fetch_oauth2: $(BINDIR)/$(CONFIG)/grpc_fetch_oauth2
 grpc_json_token_test: $(BINDIR)/$(CONFIG)/grpc_json_token_test
+grpc_print_default_creds_token: $(BINDIR)/$(CONFIG)/grpc_print_default_creds_token
 grpc_stream_op_test: $(BINDIR)/$(CONFIG)/grpc_stream_op_test
 hpack_parser_test: $(BINDIR)/$(CONFIG)/hpack_parser_test
 hpack_table_test: $(BINDIR)/$(CONFIG)/hpack_table_test
@@ -1763,7 +1764,7 @@
 	$(Q) $(BINDIR)/$(CONFIG)/thread_pool_test || ( echo test thread_pool_test failed ; exit 1 )
 
 
-tools: privatelibs $(BINDIR)/$(CONFIG)/gen_hpack_tables $(BINDIR)/$(CONFIG)/grpc_create_jwt $(BINDIR)/$(CONFIG)/grpc_fetch_oauth2
+tools: privatelibs $(BINDIR)/$(CONFIG)/gen_hpack_tables $(BINDIR)/$(CONFIG)/grpc_create_jwt $(BINDIR)/$(CONFIG)/grpc_fetch_oauth2 $(BINDIR)/$(CONFIG)/grpc_print_default_creds_token
 
 buildbenchmarks: privatelibs $(BINDIR)/$(CONFIG)/grpc_completion_queue_benchmark $(BINDIR)/$(CONFIG)/low_level_ping_pong_benchmark
 
@@ -2283,6 +2284,9 @@
     src/core/security/auth.c \
     src/core/security/base64.c \
     src/core/security/credentials.c \
+    src/core/security/credentials_posix.c \
+    src/core/security/credentials_win32.c \
+    src/core/security/default_credentials.c \
     src/core/security/factories.c \
     src/core/security/json_token.c \
     src/core/security/secure_endpoint.c \
@@ -2424,6 +2428,9 @@
 src/core/security/auth.c: $(OPENSSL_DEP)
 src/core/security/base64.c: $(OPENSSL_DEP)
 src/core/security/credentials.c: $(OPENSSL_DEP)
+src/core/security/credentials_posix.c: $(OPENSSL_DEP)
+src/core/security/credentials_win32.c: $(OPENSSL_DEP)
+src/core/security/default_credentials.c: $(OPENSSL_DEP)
 src/core/security/factories.c: $(OPENSSL_DEP)
 src/core/security/json_token.c: $(OPENSSL_DEP)
 src/core/security/secure_endpoint.c: $(OPENSSL_DEP)
@@ -2582,6 +2589,9 @@
 $(OBJDIR)/$(CONFIG)/src/core/security/auth.o: 
 $(OBJDIR)/$(CONFIG)/src/core/security/base64.o: 
 $(OBJDIR)/$(CONFIG)/src/core/security/credentials.o: 
+$(OBJDIR)/$(CONFIG)/src/core/security/credentials_posix.o: 
+$(OBJDIR)/$(CONFIG)/src/core/security/credentials_win32.o: 
+$(OBJDIR)/$(CONFIG)/src/core/security/default_credentials.o: 
 $(OBJDIR)/$(CONFIG)/src/core/security/factories.o: 
 $(OBJDIR)/$(CONFIG)/src/core/security/json_token.o: 
 $(OBJDIR)/$(CONFIG)/src/core/security/secure_endpoint.o: 
@@ -6546,6 +6556,37 @@
 endif
 
 
+GRPC_PRINT_DEFAULT_CREDS_TOKEN_SRC = \
+    test/core/security/print_default_creds_token.c \
+
+GRPC_PRINT_DEFAULT_CREDS_TOKEN_OBJS = $(addprefix $(OBJDIR)/$(CONFIG)/, $(addsuffix .o, $(basename $(GRPC_PRINT_DEFAULT_CREDS_TOKEN_SRC))))
+
+ifeq ($(NO_SECURE),true)
+
+# You can't build secure targets if you don't have OpenSSL with ALPN.
+
+$(BINDIR)/$(CONFIG)/grpc_print_default_creds_token: openssl_dep_error
+
+else
+
+$(BINDIR)/$(CONFIG)/grpc_print_default_creds_token: $(GRPC_PRINT_DEFAULT_CREDS_TOKEN_OBJS) $(LIBDIR)/$(CONFIG)/libgrpc_test_util.a $(LIBDIR)/$(CONFIG)/libgrpc.a $(LIBDIR)/$(CONFIG)/libgpr_test_util.a $(LIBDIR)/$(CONFIG)/libgpr.a
+	$(E) "[LD]      Linking $@"
+	$(Q) mkdir -p `dirname $@`
+	$(Q) $(LD) $(LDFLAGS) $(GRPC_PRINT_DEFAULT_CREDS_TOKEN_OBJS) $(LIBDIR)/$(CONFIG)/libgrpc_test_util.a $(LIBDIR)/$(CONFIG)/libgrpc.a $(LIBDIR)/$(CONFIG)/libgpr_test_util.a $(LIBDIR)/$(CONFIG)/libgpr.a $(LDLIBS) $(LDLIBS_SECURE) -o $(BINDIR)/$(CONFIG)/grpc_print_default_creds_token
+
+endif
+
+$(OBJDIR)/$(CONFIG)/test/core/security/print_default_creds_token.o:  $(LIBDIR)/$(CONFIG)/libgrpc_test_util.a $(LIBDIR)/$(CONFIG)/libgrpc.a $(LIBDIR)/$(CONFIG)/libgpr_test_util.a $(LIBDIR)/$(CONFIG)/libgpr.a
+
+deps_grpc_print_default_creds_token: $(GRPC_PRINT_DEFAULT_CREDS_TOKEN_OBJS:.o=.dep)
+
+ifneq ($(NO_SECURE),true)
+ifneq ($(NO_DEPS),true)
+-include $(GRPC_PRINT_DEFAULT_CREDS_TOKEN_OBJS:.o=.dep)
+endif
+endif
+
+
 GRPC_STREAM_OP_TEST_SRC = \
     test/core/transport/stream_op_test.c \
 
diff --git a/build.json b/build.json
index f8c97e3..3ad8944 100644
--- a/build.json
+++ b/build.json
@@ -320,6 +320,9 @@
         "src/core/security/auth.c",
         "src/core/security/base64.c",
         "src/core/security/credentials.c",
+        "src/core/security/credentials_posix.c",
+        "src/core/security/credentials_win32.c",
+        "src/core/security/default_credentials.c",
         "src/core/security/factories.c",
         "src/core/security/json_token.c",
         "src/core/security/secure_endpoint.c",
@@ -1187,6 +1190,20 @@
       ]
     },
     {
+      "name": "grpc_print_default_creds_token",
+      "build": "tool",
+      "language": "c",
+      "src": [
+        "test/core/security/print_default_creds_token.c"
+      ],
+      "deps": [
+        "grpc_test_util",
+        "grpc",
+        "gpr_test_util",
+        "gpr"
+      ]
+    },
+    {
       "name": "grpc_stream_op_test",
       "build": "test",
       "language": "c",
diff --git a/include/grpc/grpc_security.h b/include/grpc/grpc_security.h
index 472887f..217c194 100644
--- a/include/grpc/grpc_security.h
+++ b/include/grpc/grpc_security.h
@@ -51,7 +51,7 @@
    The creator of the credentials object is responsible for its release. */
 void grpc_credentials_release(grpc_credentials *creds);
 
-/* Creates default credentials. */
+/* Creates default credentials to connect to a google gRPC service. */
 grpc_credentials *grpc_default_credentials_create(void);
 
 /* Environment variable that points to the default SSL roots file. This file
diff --git a/src/core/httpcli/httpcli.c b/src/core/httpcli/httpcli.c
index d372e69..d2cf09a 100644
--- a/src/core/httpcli/httpcli.c
+++ b/src/core/httpcli/httpcli.c
@@ -216,6 +216,7 @@
   gpr_log(GPR_DEBUG, "%s", __FUNCTION__);
   if (!addresses) {
     finish(req, 0);
+    return;
   }
   req->addresses = addresses;
   req->next_address = 0;
diff --git a/src/core/security/credentials.c b/src/core/security/credentials.c
index 42d1a90..7e72b23 100644
--- a/src/core/security/credentials.c
+++ b/src/core/security/credentials.c
@@ -1076,7 +1076,3 @@
       c->md_ctx, GRPC_IAM_AUTHORITY_SELECTOR_METADATA_KEY, authority_selector);
   return &c->base;
 }
-
-/* -- Default credentials TODO(jboeuf). -- */
-
-grpc_credentials *grpc_default_credentials_create(void) { return NULL; }
diff --git a/src/core/security/credentials.h b/src/core/security/credentials.h
index 7b89294..9886afc 100644
--- a/src/core/security/credentials.h
+++ b/src/core/security/credentials.h
@@ -60,8 +60,15 @@
   "x-goog-iam-authorization-token"
 #define GRPC_IAM_AUTHORITY_SELECTOR_METADATA_KEY "x-goog-iam-authority-selector"
 
+#define GRPC_GOOGLE_CLOUD_SDK_CONFIG_DIRECTORY "gcloud"
+#define GRPC_GOOGLE_WELL_KNOWN_CREDENTIALS_FILE \
+  "application_default_credentials.json"
+
 /* --- grpc_credentials. --- */
 
+/* It is the caller's responsibility to gpr_free the result if not NULL. */
+char *grpc_get_well_known_credentials_file_path(void);
+
 typedef void (*grpc_credentials_metadata_cb)(void *user_data,
                                              grpc_mdelem **md_elems,
                                              size_t num_md,
diff --git a/src/core/security/credentials_posix.c b/src/core/security/credentials_posix.c
new file mode 100644
index 0000000..9cffd64
--- /dev/null
+++ b/src/core/security/credentials_posix.c
@@ -0,0 +1,60 @@
+/*
+ *
+ * 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 <grpc/support/port_platform.h>
+
+#ifdef GPR_POSIX_FILE
+
+#include "src/core/security/credentials.h"
+
+#include <grpc/support/alloc.h>
+#include <grpc/support/log.h>
+
+#include "src/core/support/env.h"
+#include "src/core/support/string.h"
+
+char *grpc_get_well_known_credentials_file_path(void) {
+  char *result = NULL;
+  char *home = gpr_getenv("HOME");
+  if (home == NULL) {
+    gpr_log(GPR_ERROR, "Could not get HOME environment variable.");
+    return NULL;
+  }
+  gpr_asprintf(&result, "%s/.config/%s/%s", home,
+               GRPC_GOOGLE_CLOUD_SDK_CONFIG_DIRECTORY,
+               GRPC_GOOGLE_WELL_KNOWN_CREDENTIALS_FILE);
+  gpr_free(home);
+  return result;
+}
+
+#endif /* GPR_POSIX_FILE */
diff --git a/src/core/security/credentials_win32.c b/src/core/security/credentials_win32.c
new file mode 100644
index 0000000..a8b7115
--- /dev/null
+++ b/src/core/security/credentials_win32.c
@@ -0,0 +1,60 @@
+/*
+ *
+ * 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 <grpc/support/port_platform.h>
+
+#ifdef GPR_WIN32
+
+#include "src/core/security/credentials.h"
+
+#include <grpc/support/alloc.h>
+#include <grpc/support/log.h>
+
+#include "src/core/support/env.h"
+#include "src/core/support/string.h"
+
+char *grpc_get_well_known_credentials_file_path(void) {
+  char *result = NULL;
+  char *appdata_path = gpr_getenv("APPDATA");
+  if (appdata_path == NULL) {
+    gpr_log(GPR_ERROR, "Could not get APPDATA environment variable.");
+    return NULL;
+  }
+  gpr_asprintf(&result, "%s/%s/%s", appdata_path,
+               GRPC_GOOGLE_CLOUD_SDK_CONFIG_DIRECTORY,
+               GRPC_GOOGLE_WELL_KNOWN_CREDENTIALS_FILE);
+  gpr_free(appdata_path);
+  return result;
+}
+
+#endif /* GPR_WIN32 */
diff --git a/src/core/security/default_credentials.c b/src/core/security/default_credentials.c
new file mode 100644
index 0000000..d7a974d
--- /dev/null
+++ b/src/core/security/default_credentials.c
@@ -0,0 +1,185 @@
+/*
+ *
+ * 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/security/credentials.h"
+
+#include <string.h>
+
+#include <grpc/support/alloc.h>
+#include <grpc/support/log.h>
+#include <grpc/support/sync.h>
+
+#include "src/core/httpcli/httpcli.h"
+#include "src/core/support/env.h"
+#include "src/core/support/file.h"
+
+/* -- Constants. -- */
+
+#define GRPC_COMPUTE_ENGINE_DETECTION_HOST "metadata.google.internal"
+#define GRPC_GOOGLE_CREDENTIALS_ENV_VAR "GOOGLE_APPLICATION_CREDENTIALS"
+
+/* -- Default credentials. -- */
+
+static grpc_credentials *default_credentials = NULL;
+static int compute_engine_detection_done = 0;
+static gpr_mu g_mu;
+static gpr_once g_once = GPR_ONCE_INIT;
+
+static void init_default_credentials(void) {
+  gpr_mu_init(&g_mu);
+}
+
+typedef struct {
+  gpr_cv cv;
+  gpr_mu mu;
+  int is_done;
+  int success;
+} compute_engine_detector;
+
+static void on_compute_engine_detection_http_response(
+    void *user_data, const grpc_httpcli_response *response) {
+  compute_engine_detector *detector = (compute_engine_detector *)user_data;
+  if (response != NULL && response->status == 200 && response->hdr_count > 0) {
+    /* Internet providers can return a generic response to all requests, so
+       it is necessary to check that metadata header is present also. */
+    size_t i;
+    for (i = 0; i < response->hdr_count; i++) {
+      grpc_httpcli_header *header = &response->hdrs[i];
+      if (!strcmp(header->key, "Metadata-Flavor") &&
+          !strcmp(header->value, "Google")) {
+        detector->success = 1;
+        break;
+      }
+    }
+  }
+  gpr_mu_lock(&detector->mu);
+  detector->is_done = 1;
+  gpr_mu_unlock(&detector->mu);
+  gpr_cv_signal(&detector->cv);
+}
+
+static int is_stack_running_on_compute_engine(void) {
+  compute_engine_detector detector;
+  grpc_httpcli_request request;
+
+  /* The http call is local. If it takes more than one sec, it is for sure not
+     on compute engine. */
+  gpr_timespec max_detection_delay = {1, 0};
+
+  gpr_mu_init(&detector.mu);
+  gpr_cv_init(&detector.cv);
+  detector.is_done = 0;
+  detector.success = 0;
+
+  memset(&request, 0, sizeof(grpc_httpcli_request));
+  request.host = GRPC_COMPUTE_ENGINE_DETECTION_HOST;
+  request.path = "/";
+
+  grpc_httpcli_get(&request, gpr_time_add(gpr_now(), max_detection_delay),
+                   on_compute_engine_detection_http_response, &detector);
+
+  /* Block until we get the response. This is not ideal but this should only be
+     called once for the lifetime of the process by the default credentials. */
+  gpr_mu_lock(&detector.mu);
+  while (!detector.is_done) {
+    gpr_cv_wait(&detector.cv, &detector.mu, gpr_inf_future);
+  }
+  gpr_mu_unlock(&detector.mu);
+
+  gpr_mu_destroy(&detector.mu);
+  gpr_cv_destroy(&detector.cv);
+  return detector.success;
+}
+
+/* Takes ownership of creds_path if not NULL. */
+static grpc_credentials *create_jwt_creds_from_path(char *creds_path) {
+  grpc_credentials *result = NULL;
+  gpr_slice creds_data;
+  int file_ok = 0;
+  if (creds_path == NULL) return NULL;
+  creds_data = gpr_load_file(creds_path, &file_ok);
+  gpr_free(creds_path);
+  if (file_ok) {
+    result = grpc_jwt_credentials_create(
+        (const char *)GPR_SLICE_START_PTR(creds_data),
+        grpc_max_auth_token_lifetime);
+    gpr_slice_unref(creds_data);
+  }
+  return result;
+}
+
+grpc_credentials *grpc_default_credentials_create(void) {
+  grpc_credentials *result = NULL;
+  int serving_cached_credentials = 0;
+  gpr_once_init(&g_once, init_default_credentials);
+
+  gpr_mu_lock(&g_mu);
+
+  if (default_credentials != NULL) {
+    result = default_credentials;
+    serving_cached_credentials = 1;
+    goto end;
+  }
+
+  /* First, try the environment variable. */
+  result =
+      create_jwt_creds_from_path(gpr_getenv(GRPC_GOOGLE_CREDENTIALS_ENV_VAR));
+  if (result != NULL) goto end;
+
+  /* Then the well-known file. */
+  result = create_jwt_creds_from_path(
+      grpc_get_well_known_credentials_file_path());
+  if (result != NULL) goto end;
+
+  /* At last try to see if we're on compute engine (do the detection only once
+     since it requires a network test). */
+  if (!compute_engine_detection_done) {
+    int need_compute_engine_creds = is_stack_running_on_compute_engine();
+    compute_engine_detection_done = 1;
+    if (need_compute_engine_creds) {
+      result = grpc_compute_engine_credentials_create();
+    }
+  }
+
+end:
+  if (!serving_cached_credentials && result != NULL) {
+    /* Blend with default ssl credentials and add a global reference so that it
+       can be cached and re-served. */
+    result = grpc_composite_credentials_create(
+        grpc_ssl_credentials_create(NULL, NULL), result);
+    GPR_ASSERT(result != NULL);
+    default_credentials = grpc_credentials_ref(result);
+  }
+  gpr_mu_unlock(&g_mu);
+  return result;
+}
diff --git a/test/core/security/print_default_creds_token.c b/test/core/security/print_default_creds_token.c
new file mode 100644
index 0000000..b11acac
--- /dev/null
+++ b/test/core/security/print_default_creds_token.c
@@ -0,0 +1,107 @@
+/*
+ *
+ * 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 <stdio.h>
+#include <string.h>
+
+#include "src/core/security/credentials.h"
+#include <grpc/grpc.h>
+#include <grpc/grpc_security.h>
+#include <grpc/support/alloc.h>
+#include <grpc/support/cmdline.h>
+#include <grpc/support/log.h>
+#include <grpc/support/slice.h>
+#include <grpc/support/sync.h>
+
+typedef struct {
+  gpr_cv cv;
+  gpr_mu mu;
+  int is_done;
+} synchronizer;
+
+static void on_metadata_response(void *user_data, grpc_mdelem **md_elems,
+                                 size_t num_md,
+                                 grpc_credentials_status status) {
+  synchronizer *sync = user_data;
+  if (status == GRPC_CREDENTIALS_ERROR) {
+    fprintf(stderr, "Fetching token failed.\n");
+  } else {
+    GPR_ASSERT(num_md == 1);
+    printf("\nGot token: %s\n\n",
+           (const char *)GPR_SLICE_START_PTR(md_elems[0]->value->slice));
+  }
+  gpr_mu_lock(&sync->mu);
+  sync->is_done = 1;
+  gpr_mu_unlock(&sync->mu);
+  gpr_cv_signal(&sync->cv);
+}
+
+int main(int argc, char **argv) {
+  int result = 0;
+  synchronizer sync;
+  grpc_credentials *creds = NULL;
+  char *service_url = "https://test.foo.google.com/Foo";
+  gpr_cmdline *cl = gpr_cmdline_create("print_default_creds_token");
+  gpr_cmdline_add_string(cl, "service_url",
+                         "Service URL for the token request.",
+                         &service_url);
+  gpr_cmdline_parse(cl, argc, argv);
+
+  grpc_init();
+
+  creds = grpc_default_credentials_create();
+  if (creds == NULL) {
+    fprintf(stderr, "\nCould not find default credentials.\n\n");
+    result = 1;
+    goto end;
+  }
+
+  gpr_mu_init(&sync.mu);
+  gpr_cv_init(&sync.cv);
+  sync.is_done = 0;
+
+  grpc_credentials_get_request_metadata(creds, "", on_metadata_response, &sync);
+
+  gpr_mu_lock(&sync.mu);
+  while (!sync.is_done) gpr_cv_wait(&sync.cv, &sync.mu, gpr_inf_future);
+  gpr_mu_unlock(&sync.mu);
+
+  gpr_mu_destroy(&sync.mu);
+  gpr_cv_destroy(&sync.cv);
+  grpc_credentials_release(creds);
+
+end:
+  gpr_cmdline_destroy(cl);
+  grpc_shutdown();
+  return result;
+}
diff --git a/vsprojects/vs2013/Grpc.mak b/vsprojects/vs2013/Grpc.mak
index 37bc9cb..2591a82 100644
--- a/vsprojects/vs2013/Grpc.mak
+++ b/vsprojects/vs2013/Grpc.mak
@@ -450,6 +450,14 @@
 	echo Running grpc_json_token_test
 	$(OUT_DIR)\grpc_json_token_test.exe
 
+grpc_print_default_creds_token.exe: grpc_test_util
+	echo Building grpc_print_default_creds_token
+	$(CC) $(CFLAGS) /Fo:$(OUT_DIR)\ ..\..\test\core\security\print_default_creds_token.c 
+	$(LINK) $(LFLAGS) /OUT:"$(OUT_DIR)\grpc_print_default_creds_token.exe" Debug\grpc_test_util.lib Debug\grpc.lib Debug\gpr_test_util.lib Debug\gpr.lib $(LIBS) $(OUT_DIR)\print_default_creds_token.obj 
+grpc_print_default_creds_token: grpc_print_default_creds_token.exe
+	echo Running grpc_print_default_creds_token
+	$(OUT_DIR)\grpc_print_default_creds_token.exe
+
 grpc_stream_op_test.exe: grpc_test_util
 	echo Building grpc_stream_op_test
 	$(CC) $(CFLAGS) /Fo:$(OUT_DIR)\ ..\..\test\core\transport\stream_op_test.c 
diff --git a/vsprojects/vs2013/grpc.vcxproj b/vsprojects/vs2013/grpc.vcxproj
index 89c0de3..bdbca92 100644
--- a/vsprojects/vs2013/grpc.vcxproj
+++ b/vsprojects/vs2013/grpc.vcxproj
@@ -201,6 +201,12 @@
     </ClCompile>
     <ClCompile Include="..\..\src\core\security\credentials.c">
     </ClCompile>
+    <ClCompile Include="..\..\src\core\security\credentials_posix.c">
+    </ClCompile>
+    <ClCompile Include="..\..\src\core\security\credentials_win32.c">
+    </ClCompile>
+    <ClCompile Include="..\..\src\core\security\default_credentials.c">
+    </ClCompile>
     <ClCompile Include="..\..\src\core\security\factories.c">
     </ClCompile>
     <ClCompile Include="..\..\src\core\security\json_token.c">
diff --git a/vsprojects/vs2013/grpc.vcxproj.filters b/vsprojects/vs2013/grpc.vcxproj.filters
index a2d9f30..d3dd374 100644
--- a/vsprojects/vs2013/grpc.vcxproj.filters
+++ b/vsprojects/vs2013/grpc.vcxproj.filters
@@ -22,6 +22,15 @@
     <ClCompile Include="..\..\src\core\security\credentials.c">
       <Filter>src\core\security</Filter>
     </ClCompile>
+    <ClCompile Include="..\..\src\core\security\credentials_posix.c">
+      <Filter>src\core\security</Filter>
+    </ClCompile>
+    <ClCompile Include="..\..\src\core\security\credentials_win32.c">
+      <Filter>src\core\security</Filter>
+    </ClCompile>
+    <ClCompile Include="..\..\src\core\security\default_credentials.c">
+      <Filter>src\core\security</Filter>
+    </ClCompile>
     <ClCompile Include="..\..\src\core\security\factories.c">
       <Filter>src\core\security</Filter>
     </ClCompile>
diff --git a/vsprojects/vs2013/grpc_shared.vcxproj b/vsprojects/vs2013/grpc_shared.vcxproj
index 81a280d..9655bb9 100644
--- a/vsprojects/vs2013/grpc_shared.vcxproj
+++ b/vsprojects/vs2013/grpc_shared.vcxproj
@@ -205,6 +205,12 @@
     </ClCompile>
     <ClCompile Include="..\..\src\core\security\credentials.c">
     </ClCompile>
+    <ClCompile Include="..\..\src\core\security\credentials_posix.c">
+    </ClCompile>
+    <ClCompile Include="..\..\src\core\security\credentials_win32.c">
+    </ClCompile>
+    <ClCompile Include="..\..\src\core\security\default_credentials.c">
+    </ClCompile>
     <ClCompile Include="..\..\src\core\security\factories.c">
     </ClCompile>
     <ClCompile Include="..\..\src\core\security\json_token.c">
diff --git a/vsprojects/vs2013/grpc_shared.vcxproj.filters b/vsprojects/vs2013/grpc_shared.vcxproj.filters
index a2d9f30..d3dd374 100644
--- a/vsprojects/vs2013/grpc_shared.vcxproj.filters
+++ b/vsprojects/vs2013/grpc_shared.vcxproj.filters
@@ -22,6 +22,15 @@
     <ClCompile Include="..\..\src\core\security\credentials.c">
       <Filter>src\core\security</Filter>
     </ClCompile>
+    <ClCompile Include="..\..\src\core\security\credentials_posix.c">
+      <Filter>src\core\security</Filter>
+    </ClCompile>
+    <ClCompile Include="..\..\src\core\security\credentials_win32.c">
+      <Filter>src\core\security</Filter>
+    </ClCompile>
+    <ClCompile Include="..\..\src\core\security\default_credentials.c">
+      <Filter>src\core\security</Filter>
+    </ClCompile>
     <ClCompile Include="..\..\src\core\security\factories.c">
       <Filter>src\core\security</Filter>
     </ClCompile>