diff --git a/BUILD b/BUILD
index e0fc55e5f7e4ed27ee966d63ac3ca3e78d8832ed..1448432913b8f6a79f6b4a2b04ecce0acb3c68f7 100644
--- a/BUILD
+++ b/BUILD
@@ -814,7 +814,6 @@ cc_library(
     "src/cpp/client/credentials.cc",
     "src/cpp/client/generic_stub.cc",
     "src/cpp/client/insecure_credentials.cc",
-    "src/cpp/common/alarm.cc",
     "src/cpp/common/call.cc",
     "src/cpp/common/channel_arguments.cc",
     "src/cpp/common/completion_queue.cc",
@@ -938,7 +937,6 @@ cc_library(
     "src/cpp/client/credentials.cc",
     "src/cpp/client/generic_stub.cc",
     "src/cpp/client/insecure_credentials.cc",
-    "src/cpp/common/alarm.cc",
     "src/cpp/common/call.cc",
     "src/cpp/common/channel_arguments.cc",
     "src/cpp/common/completion_queue.cc",
diff --git a/Makefile b/Makefile
index 11b2bfbb4db6c6dea4b759c14c3ef4563a419afc..1488535edf11535ed746b8f1c1ac12ea8ecd82d9 100644
--- a/Makefile
+++ b/Makefile
@@ -2972,7 +2972,6 @@ LIBGRPC++_SRC = \
     src/cpp/client/credentials.cc \
     src/cpp/client/generic_stub.cc \
     src/cpp/client/insecure_credentials.cc \
-    src/cpp/common/alarm.cc \
     src/cpp/common/call.cc \
     src/cpp/common/channel_arguments.cc \
     src/cpp/common/completion_queue.cc \
@@ -3253,7 +3252,6 @@ LIBGRPC++_UNSECURE_SRC = \
     src/cpp/client/credentials.cc \
     src/cpp/client/generic_stub.cc \
     src/cpp/client/insecure_credentials.cc \
-    src/cpp/common/alarm.cc \
     src/cpp/common/call.cc \
     src/cpp/common/channel_arguments.cc \
     src/cpp/common/completion_queue.cc \
diff --git a/PYTHON-MANIFEST.in b/PYTHON-MANIFEST.in
index 072089ac51f1442ab2f4d28410e4c4e10615f3f9..25aba87c187d22c3f7ff10b434339ecc6d84c6f2 100644
--- a/PYTHON-MANIFEST.in
+++ b/PYTHON-MANIFEST.in
@@ -1,4 +1,5 @@
-graft src/python/grpcio/grpc
+recursive-include src/python/grpcio/grpc *.c *.h *.py *.pyx *.pxd *.pxi *.python *.pem
+recursive-exclude src/python/grpcio/grpc/_cython *.so *.pyd
 graft src/python/grpcio/tests
 graft src/core
 graft include/grpc
diff --git a/build.yaml b/build.yaml
index d19bf67d523e2fa4f97d990c9cf530830ffb8f1f..b27ba9881cfbe7636f035f5d0a55ebadddc51b31 100644
--- a/build.yaml
+++ b/build.yaml
@@ -184,7 +184,6 @@ filegroups:
   - src/cpp/client/credentials.cc
   - src/cpp/client/generic_stub.cc
   - src/cpp/client/insecure_credentials.cc
-  - src/cpp/common/alarm.cc
   - src/cpp/common/call.cc
   - src/cpp/common/channel_arguments.cc
   - src/cpp/common/completion_queue.cc
@@ -1952,6 +1951,7 @@ targets:
   - linux
   - posix
 - name: alarm_cpp_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -1964,6 +1964,7 @@ targets:
   - gpr_test_util
   - gpr
 - name: async_end2end_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2010,6 +2011,7 @@ targets:
   - linux
   - posix
 - name: auth_property_iterator_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2022,6 +2024,7 @@ targets:
   - gpr_test_util
   - gpr
 - name: channel_arguments_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2031,6 +2034,7 @@ targets:
   - grpc
   - gpr
 - name: cli_call_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2043,6 +2047,7 @@ targets:
   - gpr_test_util
   - gpr
 - name: client_crash_test
+  gtest: true
   cpu_cost: 0.1
   build: test
   language: c++
@@ -2073,6 +2078,7 @@ targets:
   - gpr_test_util
   - gpr
 - name: credentials_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2082,6 +2088,7 @@ targets:
   - grpc
   - gpr
 - name: cxx_byte_buffer_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2093,6 +2100,7 @@ targets:
   - gpr_test_util
   - gpr
 - name: cxx_slice_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2104,6 +2112,7 @@ targets:
   - gpr_test_util
   - gpr
 - name: cxx_string_ref_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2111,6 +2120,7 @@ targets:
   deps:
   - grpc++
 - name: cxx_time_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2122,6 +2132,7 @@ targets:
   - gpr_test_util
   - gpr
 - name: end2end_test
+  gtest: true
   cpu_cost: 0.5
   build: test
   language: c++
@@ -2152,6 +2163,7 @@ targets:
   - linux
   - posix
 - name: generic_end2end_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2228,6 +2240,7 @@ targets:
   vs_config_type: Application
   vs_project_guid: '{069E9D05-B78B-4751-9252-D21EBAE7DE8E}'
 - name: grpclb_api_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2239,6 +2252,7 @@ targets:
   - grpc++
   - grpc
 - name: hybrid_end2end_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2318,6 +2332,7 @@ targets:
   - gpr
   - grpc++_test_config
 - name: mock_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2453,6 +2468,7 @@ targets:
   - gpr
   - grpc++_test_config
 - name: secure_auth_context_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2482,6 +2498,7 @@ targets:
   - linux
   - posix
 - name: server_crash_test
+  gtest: true
   cpu_cost: 0.1
   build: test
   language: c++
@@ -2512,6 +2529,7 @@ targets:
   - gpr_test_util
   - gpr
 - name: shutdown_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2535,6 +2553,7 @@ targets:
   - gpr_test_util
   - gpr
 - name: streaming_throughput_test
+  gtest: true
   build: test
   language: c++
   src:
@@ -2611,6 +2630,7 @@ targets:
   - linux
   - posix
 - name: thread_stress_test
+  gtest: true
   cpu_cost: 100
   build: test
   language: c++
@@ -2624,6 +2644,7 @@ targets:
   - gpr_test_util
   - gpr
 - name: zookeeper_test
+  gtest: true
   build: test
   run: false
   language: c++
@@ -2823,7 +2844,6 @@ php_config_m4:
   - grpc
   - gpr
   - boringssl
-  - z
   headers:
   - src/php/ext/grpc/byte_buffer.h
   - src/php/ext/grpc/call.h
diff --git a/config.m4 b/config.m4
index 25d3cb0e9fc2dbb62354ffa352275356123c5ebe..005f8dc633b0662c8fe4942b70d8ce9d918a5474 100644
--- a/config.m4
+++ b/config.m4
@@ -531,22 +531,74 @@ if test "$PHP_GRPC" != "no"; then
     third_party/boringssl/ssl/t1_enc.c \
     third_party/boringssl/ssl/t1_lib.c \
     third_party/boringssl/ssl/tls_record.c \
-    third_party/zlib/adler32.c \
-    third_party/zlib/compress.c \
-    third_party/zlib/crc32.c \
-    third_party/zlib/deflate.c \
-    third_party/zlib/gzclose.c \
-    third_party/zlib/gzlib.c \
-    third_party/zlib/gzread.c \
-    third_party/zlib/gzwrite.c \
-    third_party/zlib/infback.c \
-    third_party/zlib/inffast.c \
-    third_party/zlib/inflate.c \
-    third_party/zlib/inftrees.c \
-    third_party/zlib/trees.c \
-    third_party/zlib/uncompr.c \
-    third_party/zlib/zutil.c \
-    , $ext_shared, , -Wall -Werror -std=c11 \
+    , $ext_shared, , -Wall -Werror \
+    -Wno-parentheses-equality -Wno-unused-value -std=c11 \
     -fvisibility=hidden -DOPENSSL_NO_ASM -D_GNU_SOURCE -DWIN32_LEAN_AND_MEAN \
     -D_HAS_EXCEPTIONS=0 -DNOMINMAX)
+
+  PHP_ADD_BUILD_DIR($ext_builddir/src/php/ext/grpc)
+
+  PHP_ADD_BUILD_DIR($ext_builddir/src/boringssl)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/census)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/channel)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/client_config)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/client_config/lb_policies)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/client_config/resolvers)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/compression)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/debug)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/httpcli)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/iomgr)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/json)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/profiling)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/proto/grpc/lb/v0)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/security)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/support)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/surface)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/transport)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/transport/chttp2)
+  PHP_ADD_BUILD_DIR($ext_builddir/src/core/tsi)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/aes)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/asn1)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/base64)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/bio)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/bn)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/bn/asm)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/buf)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/bytestring)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/chacha)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/cipher)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/cmac)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/conf)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/curve25519)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/des)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/dh)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/digest)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/dsa)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/ec)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/ecdh)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/ecdsa)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/engine)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/err)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/evp)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/hkdf)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/hmac)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/lhash)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/md4)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/md5)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/modes)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/obj)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/pem)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/pkcs8)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/poly1305)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/rand)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/rc4)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/rsa)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/sha)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/stack)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/x509)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/crypto/x509v3)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/ssl)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/boringssl/ssl/pqueue)
+  PHP_ADD_BUILD_DIR($ext_builddir/third_party/nanopb)
 fi
diff --git a/doc/health-checking.md b/doc/health-checking.md
index 0b3f9c6a034c43e45859086b5a39d3acb12ab370..92512e942bd90f7d03bd1f3e6db4f48795f0a959 100644
--- a/doc/health-checking.md
+++ b/doc/health-checking.md
@@ -26,7 +26,7 @@ The server should export a service defined in the following proto:
 ```
 syntax = "proto3";
 
-package grpc.health.v1alpha;
+package grpc.health.v1;
 
 message HealthCheckRequest {
   string service = 1;
@@ -49,7 +49,7 @@ service Health {
 A client can query the server’s health status by calling the `Check` method, and
 a deadline should be set on the rpc. The client can optionally set the service
 name it wants to query for health status. The suggested format of service name
-is `package_names.ServiceName`, such as `grpc.health.v1alpha.Health`.
+is `package_names.ServiceName`, such as `grpc.health.v1.Health`.
 
 The server should register all the services manually and set
 the individual status, including an empty service name and its status. For each
diff --git a/examples/csharp/helloworld/.nuget/packages.config b/examples/csharp/helloworld/.nuget/packages.config
index 1cbe7e1d65ffdc21cef806cb81315acd267de100..fb778311d1f77f07aa041cf5a28cdc8113dcf799 100644
--- a/examples/csharp/helloworld/.nuget/packages.config
+++ b/examples/csharp/helloworld/.nuget/packages.config
@@ -1,4 +1,4 @@
 <?xml version="1.0" encoding="utf-8"?>
 <packages>
-  <package id="Grpc.Tools" version="0.12.0" />
+  <package id="Grpc.Tools" version="0.13.0" />
 </packages>
\ No newline at end of file
diff --git a/examples/csharp/helloworld/Greeter/Greeter.csproj b/examples/csharp/helloworld/Greeter/Greeter.csproj
index fa1c20f5ff4cddc2339e5a708dd1b16b15f8c0a8..a25ad5f7910b21001740e148bf70bc9ce4019755 100644
--- a/examples/csharp/helloworld/Greeter/Greeter.csproj
+++ b/examples/csharp/helloworld/Greeter/Greeter.csproj
@@ -10,7 +10,7 @@
     <RootNamespace>Greeter</RootNamespace>
     <AssemblyName>Greeter</AssemblyName>
     <TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
-    <NuGetPackageImportStamp>4eea1d1c</NuGetPackageImportStamp>
+    <NuGetPackageImportStamp>39f4a691</NuGetPackageImportStamp>
   </PropertyGroup>
   <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
     <DebugSymbols>true</DebugSymbols>
@@ -31,15 +31,18 @@
     <ConsolePause>false</ConsolePause>
   </PropertyGroup>
   <ItemGroup>
-    <Reference Include="Google.Protobuf">
-      <HintPath>..\packages\Google.Protobuf.3.0.0-alpha4\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
+    <Reference Include="Google.Protobuf, Version=3.0.0.0, Culture=neutral, PublicKeyToken=a7d26565bac4d604, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Google.Protobuf.3.0.0-beta2\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
     </Reference>
-    <Reference Include="Grpc.Core">
-      <HintPath>..\packages\Grpc.Core.0.12.0\lib\net45\Grpc.Core.dll</HintPath>
+    <Reference Include="Grpc.Core, Version=0.13.0.0, Culture=neutral, PublicKeyToken=d754f35622e28bad, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Grpc.Core.0.13.0\lib\net45\Grpc.Core.dll</HintPath>
     </Reference>
     <Reference Include="System" />
-    <Reference Include="System.Interactive.Async">
-      <HintPath>..\packages\Ix-Async.1.2.3\lib\net45\System.Interactive.Async.dll</HintPath>
+    <Reference Include="System.Interactive.Async, Version=1.2.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Ix-Async.1.2.5\lib\net45\System.Interactive.Async.dll</HintPath>
     </Reference>
   </ItemGroup>
   <ItemGroup>
@@ -53,15 +56,11 @@
     <None Include="protos\helloworld.proto" />
   </ItemGroup>
   <ItemGroup />
-  <Import Project="..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets" Condition="Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" />
+  <Import Project="..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
   <Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
     <PropertyGroup>
       <ErrorText>This project references NuGet package(s) that are missing on this computer. Enable NuGet Package Restore to download them.  For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
     </PropertyGroup>
-    <Error Condition="!Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
+    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
   </Target>
-  <Import Project="..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets" Condition="Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" />
-  <Import Project="..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
 </Project>
\ No newline at end of file
diff --git a/examples/csharp/helloworld/Greeter/Helloworld.cs b/examples/csharp/helloworld/Greeter/Helloworld.cs
index 668165a6ce60b431bc35a9ec63cd12ae7ab70720..63969b7514b9302aa44bc68aa4e4fdc9176ba3b7 100644
--- a/examples/csharp/helloworld/Greeter/Helloworld.cs
+++ b/examples/csharp/helloworld/Greeter/Helloworld.cs
@@ -9,41 +9,46 @@ using pbr = global::Google.Protobuf.Reflection;
 using scg = global::System.Collections.Generic;
 namespace Helloworld {
 
+  /// <summary>Holder for reflection information generated from helloworld.proto</summary>
   [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
-  public static partial class Helloworld {
+  public static partial class HelloworldReflection {
 
     #region Descriptor
+    /// <summary>File descriptor for helloworld.proto</summary>
     public static pbr::FileDescriptor Descriptor {
       get { return descriptor; }
     }
     private static pbr::FileDescriptor descriptor;
 
-    static Helloworld() {
+    static HelloworldReflection() {
       byte[] descriptorData = global::System.Convert.FromBase64String(
           string.Concat(
-            "ChBoZWxsb3dvcmxkLnByb3RvEgpoZWxsb3dvcmxkIhwKDEhlbGxvUmVxdWVz", 
-            "dBIMCgRuYW1lGAEgASgJIh0KCkhlbGxvUmVwbHkSDwoHbWVzc2FnZRgBIAEo", 
-            "CTJJCgdHcmVldGVyEj4KCFNheUhlbGxvEhguaGVsbG93b3JsZC5IZWxsb1Jl", 
-            "cXVlc3QaFi5oZWxsb3dvcmxkLkhlbGxvUmVwbHkiAEIYChBpby5ncnBjLmV4", 
+            "ChBoZWxsb3dvcmxkLnByb3RvEgpoZWxsb3dvcmxkIhwKDEhlbGxvUmVxdWVz",
+            "dBIMCgRuYW1lGAEgASgJIh0KCkhlbGxvUmVwbHkSDwoHbWVzc2FnZRgBIAEo",
+            "CTJJCgdHcmVldGVyEj4KCFNheUhlbGxvEhguaGVsbG93b3JsZC5IZWxsb1Jl",
+            "cXVlc3QaFi5oZWxsb3dvcmxkLkhlbGxvUmVwbHkiAEIYChBpby5ncnBjLmV4",
             "YW1wbGVzogIDSExXYgZwcm90bzM="));
-      descriptor = pbr::FileDescriptor.InternalBuildGeneratedFileFrom(descriptorData,
+      descriptor = pbr::FileDescriptor.FromGeneratedCode(descriptorData,
           new pbr::FileDescriptor[] { },
           new pbr::GeneratedCodeInfo(null, new pbr::GeneratedCodeInfo[] {
-            new pbr::GeneratedCodeInfo(typeof(global::Helloworld.HelloRequest), new[]{ "Name" }, null, null, null),
-            new pbr::GeneratedCodeInfo(typeof(global::Helloworld.HelloReply), new[]{ "Message" }, null, null, null)
+            new pbr::GeneratedCodeInfo(typeof(global::Helloworld.HelloRequest), global::Helloworld.HelloRequest.Parser, new[]{ "Name" }, null, null, null),
+            new pbr::GeneratedCodeInfo(typeof(global::Helloworld.HelloReply), global::Helloworld.HelloReply.Parser, new[]{ "Message" }, null, null, null)
           }));
     }
     #endregion
 
   }
   #region Messages
+  /// <summary>
+  ///  The request message containing the user's name.
+  /// </summary>
   [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
   public sealed partial class HelloRequest : pb::IMessage<HelloRequest> {
     private static readonly pb::MessageParser<HelloRequest> _parser = new pb::MessageParser<HelloRequest>(() => new HelloRequest());
     public static pb::MessageParser<HelloRequest> Parser { get { return _parser; } }
 
     public static pbr::MessageDescriptor Descriptor {
-      get { return global::Helloworld.Helloworld.Descriptor.MessageTypes[0]; }
+      get { return global::Helloworld.HelloworldReflection.Descriptor.MessageTypes[0]; }
     }
 
     pbr::MessageDescriptor pb::IMessage.Descriptor {
@@ -64,6 +69,7 @@ namespace Helloworld {
       return new HelloRequest(this);
     }
 
+    /// <summary>Field number for the "name" field.</summary>
     public const int NameFieldNumber = 1;
     private string name_ = "";
     public string Name {
@@ -95,7 +101,7 @@ namespace Helloworld {
     }
 
     public override string ToString() {
-      return pb::JsonFormatter.Default.Format(this);
+      return pb::JsonFormatter.ToDiagnosticString(this);
     }
 
     public void WriteTo(pb::CodedOutputStream output) {
@@ -139,13 +145,16 @@ namespace Helloworld {
 
   }
 
+  /// <summary>
+  ///  The response message containing the greetings
+  /// </summary>
   [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
   public sealed partial class HelloReply : pb::IMessage<HelloReply> {
     private static readonly pb::MessageParser<HelloReply> _parser = new pb::MessageParser<HelloReply>(() => new HelloReply());
     public static pb::MessageParser<HelloReply> Parser { get { return _parser; } }
 
     public static pbr::MessageDescriptor Descriptor {
-      get { return global::Helloworld.Helloworld.Descriptor.MessageTypes[1]; }
+      get { return global::Helloworld.HelloworldReflection.Descriptor.MessageTypes[1]; }
     }
 
     pbr::MessageDescriptor pb::IMessage.Descriptor {
@@ -166,6 +175,7 @@ namespace Helloworld {
       return new HelloReply(this);
     }
 
+    /// <summary>Field number for the "message" field.</summary>
     public const int MessageFieldNumber = 1;
     private string message_ = "";
     public string Message {
@@ -197,7 +207,7 @@ namespace Helloworld {
     }
 
     public override string ToString() {
-      return pb::JsonFormatter.Default.Format(this);
+      return pb::JsonFormatter.ToDiagnosticString(this);
     }
 
     public void WriteTo(pb::CodedOutputStream output) {
diff --git a/examples/csharp/helloworld/Greeter/HelloworldGrpc.cs b/examples/csharp/helloworld/Greeter/HelloworldGrpc.cs
index edfe4d22574d9af323bdbfddc8c1a65a62c23e6f..4014bc21e32c0e5c763a8b666bbfdb6b3ed56e2e 100644
--- a/examples/csharp/helloworld/Greeter/HelloworldGrpc.cs
+++ b/examples/csharp/helloworld/Greeter/HelloworldGrpc.cs
@@ -25,7 +25,7 @@ namespace Helloworld {
     // service descriptor
     public static global::Google.Protobuf.Reflection.ServiceDescriptor Descriptor
     {
-      get { return global::Helloworld.Helloworld.Descriptor.Services[0]; }
+      get { return global::Helloworld.HelloworldReflection.Descriptor.Services[0]; }
     }
 
     // client interface
diff --git a/examples/csharp/helloworld/Greeter/packages.config b/examples/csharp/helloworld/Greeter/packages.config
index cabcadc78f2a7119945c60e53a1ea4feb0573999..abe9ad085073e8a5bd795840370a9ff01eeeb560 100644
--- a/examples/csharp/helloworld/Greeter/packages.config
+++ b/examples/csharp/helloworld/Greeter/packages.config
@@ -1,10 +1,8 @@
 <?xml version="1.0" encoding="utf-8"?>
 <packages>
-  <package id="Google.Protobuf" version="3.0.0-alpha4" targetFramework="net45" />
-  <package id="Grpc" version="0.12.0" targetFramework="net45" />
-  <package id="Grpc.Core" version="0.12.0" targetFramework="net45" />
-  <package id="grpc.dependencies.openssl.redist" version="1.0.204.1" targetFramework="net45" />
-  <package id="grpc.dependencies.zlib.redist" version="1.2.8.10" targetFramework="net45" />
-  <package id="grpc.native.csharp" version="0.12.0" targetFramework="net45" />
-  <package id="Ix-Async" version="1.2.3" targetFramework="net45" />
+  <package id="Google.Protobuf" version="3.0.0-beta2" targetFramework="net45" />
+  <package id="Grpc" version="0.13.0" targetFramework="net45" />
+  <package id="Grpc.Core" version="0.13.0" targetFramework="net45" />
+  <package id="grpc.native.csharp" version="0.13.0" targetFramework="net45" />
+  <package id="Ix-Async" version="1.2.5" targetFramework="net45" />
 </packages>
\ No newline at end of file
diff --git a/examples/csharp/helloworld/GreeterClient/GreeterClient.csproj b/examples/csharp/helloworld/GreeterClient/GreeterClient.csproj
index 164a6165eff1b941fc6fee959b6c8b134e65a7e1..a71cfeeef33127cd5ca1a7709e417b9c015949bf 100644
--- a/examples/csharp/helloworld/GreeterClient/GreeterClient.csproj
+++ b/examples/csharp/helloworld/GreeterClient/GreeterClient.csproj
@@ -10,7 +10,7 @@
     <RootNamespace>GreeterClient</RootNamespace>
     <AssemblyName>GreeterClient</AssemblyName>
     <TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
-    <NuGetPackageImportStamp>29206d49</NuGetPackageImportStamp>
+    <NuGetPackageImportStamp>dcebbc77</NuGetPackageImportStamp>
   </PropertyGroup>
   <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
     <DebugSymbols>true</DebugSymbols>
@@ -31,15 +31,18 @@
     <Externalconsole>true</Externalconsole>
   </PropertyGroup>
   <ItemGroup>
-    <Reference Include="Google.Protobuf">
-      <HintPath>..\packages\Google.Protobuf.3.0.0-alpha4\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
+    <Reference Include="Google.Protobuf, Version=3.0.0.0, Culture=neutral, PublicKeyToken=a7d26565bac4d604, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Google.Protobuf.3.0.0-beta2\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
     </Reference>
-    <Reference Include="Grpc.Core">
-      <HintPath>..\packages\Grpc.Core.0.12.0\lib\net45\Grpc.Core.dll</HintPath>
+    <Reference Include="Grpc.Core, Version=0.13.0.0, Culture=neutral, PublicKeyToken=d754f35622e28bad, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Grpc.Core.0.13.0\lib\net45\Grpc.Core.dll</HintPath>
     </Reference>
     <Reference Include="System" />
-    <Reference Include="System.Interactive.Async">
-      <HintPath>..\packages\Ix-Async.1.2.3\lib\net45\System.Interactive.Async.dll</HintPath>
+    <Reference Include="System.Interactive.Async, Version=1.2.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Ix-Async.1.2.5\lib\net45\System.Interactive.Async.dll</HintPath>
     </Reference>
   </ItemGroup>
   <ItemGroup>
@@ -56,15 +59,11 @@
   <ItemGroup>
     <None Include="packages.config" />
   </ItemGroup>
-  <Import Project="..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets" Condition="Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" />
+  <Import Project="..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
   <Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
     <PropertyGroup>
       <ErrorText>This project references NuGet package(s) that are missing on this computer. Enable NuGet Package Restore to download them.  For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
     </PropertyGroup>
-    <Error Condition="!Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
+    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
   </Target>
-  <Import Project="..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets" Condition="Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" />
-  <Import Project="..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
 </Project>
\ No newline at end of file
diff --git a/examples/csharp/helloworld/GreeterClient/packages.config b/examples/csharp/helloworld/GreeterClient/packages.config
index cabcadc78f2a7119945c60e53a1ea4feb0573999..abe9ad085073e8a5bd795840370a9ff01eeeb560 100644
--- a/examples/csharp/helloworld/GreeterClient/packages.config
+++ b/examples/csharp/helloworld/GreeterClient/packages.config
@@ -1,10 +1,8 @@
 <?xml version="1.0" encoding="utf-8"?>
 <packages>
-  <package id="Google.Protobuf" version="3.0.0-alpha4" targetFramework="net45" />
-  <package id="Grpc" version="0.12.0" targetFramework="net45" />
-  <package id="Grpc.Core" version="0.12.0" targetFramework="net45" />
-  <package id="grpc.dependencies.openssl.redist" version="1.0.204.1" targetFramework="net45" />
-  <package id="grpc.dependencies.zlib.redist" version="1.2.8.10" targetFramework="net45" />
-  <package id="grpc.native.csharp" version="0.12.0" targetFramework="net45" />
-  <package id="Ix-Async" version="1.2.3" targetFramework="net45" />
+  <package id="Google.Protobuf" version="3.0.0-beta2" targetFramework="net45" />
+  <package id="Grpc" version="0.13.0" targetFramework="net45" />
+  <package id="Grpc.Core" version="0.13.0" targetFramework="net45" />
+  <package id="grpc.native.csharp" version="0.13.0" targetFramework="net45" />
+  <package id="Ix-Async" version="1.2.5" targetFramework="net45" />
 </packages>
\ No newline at end of file
diff --git a/examples/csharp/helloworld/GreeterServer/GreeterServer.csproj b/examples/csharp/helloworld/GreeterServer/GreeterServer.csproj
index 56436d3834cf01c04092232277dec5299ac8b77c..34eea8c246d0204d611d0b080f069d73430f86ee 100644
--- a/examples/csharp/helloworld/GreeterServer/GreeterServer.csproj
+++ b/examples/csharp/helloworld/GreeterServer/GreeterServer.csproj
@@ -10,7 +10,7 @@
     <RootNamespace>GreeterServer</RootNamespace>
     <AssemblyName>GreeterServer</AssemblyName>
     <TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
-    <NuGetPackageImportStamp>8a2cae0f</NuGetPackageImportStamp>
+    <NuGetPackageImportStamp>2ea5dfd0</NuGetPackageImportStamp>
   </PropertyGroup>
   <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
     <DebugSymbols>true</DebugSymbols>
@@ -31,15 +31,18 @@
     <Externalconsole>true</Externalconsole>
   </PropertyGroup>
   <ItemGroup>
-    <Reference Include="Google.Protobuf">
-      <HintPath>..\packages\Google.Protobuf.3.0.0-alpha4\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
+    <Reference Include="Google.Protobuf, Version=3.0.0.0, Culture=neutral, PublicKeyToken=a7d26565bac4d604, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Google.Protobuf.3.0.0-beta2\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
     </Reference>
-    <Reference Include="Grpc.Core">
-      <HintPath>..\packages\Grpc.Core.0.12.0\lib\net45\Grpc.Core.dll</HintPath>
+    <Reference Include="Grpc.Core, Version=0.13.0.0, Culture=neutral, PublicKeyToken=d754f35622e28bad, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Grpc.Core.0.13.0\lib\net45\Grpc.Core.dll</HintPath>
     </Reference>
     <Reference Include="System" />
-    <Reference Include="System.Interactive.Async">
-      <HintPath>..\packages\Ix-Async.1.2.3\lib\net45\System.Interactive.Async.dll</HintPath>
+    <Reference Include="System.Interactive.Async, Version=1.2.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Ix-Async.1.2.5\lib\net45\System.Interactive.Async.dll</HintPath>
     </Reference>
   </ItemGroup>
   <ItemGroup>
@@ -56,15 +59,11 @@
   <ItemGroup>
     <None Include="packages.config" />
   </ItemGroup>
-  <Import Project="..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets" Condition="Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" />
+  <Import Project="..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
   <Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
     <PropertyGroup>
       <ErrorText>This project references NuGet package(s) that are missing on this computer. Enable NuGet Package Restore to download them.  For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
     </PropertyGroup>
-    <Error Condition="!Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
+    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
   </Target>
-  <Import Project="..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets" Condition="Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" />
-  <Import Project="..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
 </Project>
\ No newline at end of file
diff --git a/examples/csharp/helloworld/GreeterServer/packages.config b/examples/csharp/helloworld/GreeterServer/packages.config
index cabcadc78f2a7119945c60e53a1ea4feb0573999..abe9ad085073e8a5bd795840370a9ff01eeeb560 100644
--- a/examples/csharp/helloworld/GreeterServer/packages.config
+++ b/examples/csharp/helloworld/GreeterServer/packages.config
@@ -1,10 +1,8 @@
 <?xml version="1.0" encoding="utf-8"?>
 <packages>
-  <package id="Google.Protobuf" version="3.0.0-alpha4" targetFramework="net45" />
-  <package id="Grpc" version="0.12.0" targetFramework="net45" />
-  <package id="Grpc.Core" version="0.12.0" targetFramework="net45" />
-  <package id="grpc.dependencies.openssl.redist" version="1.0.204.1" targetFramework="net45" />
-  <package id="grpc.dependencies.zlib.redist" version="1.2.8.10" targetFramework="net45" />
-  <package id="grpc.native.csharp" version="0.12.0" targetFramework="net45" />
-  <package id="Ix-Async" version="1.2.3" targetFramework="net45" />
+  <package id="Google.Protobuf" version="3.0.0-beta2" targetFramework="net45" />
+  <package id="Grpc" version="0.13.0" targetFramework="net45" />
+  <package id="Grpc.Core" version="0.13.0" targetFramework="net45" />
+  <package id="grpc.native.csharp" version="0.13.0" targetFramework="net45" />
+  <package id="Ix-Async" version="1.2.5" targetFramework="net45" />
 </packages>
\ No newline at end of file
diff --git a/examples/csharp/helloworld/README.md b/examples/csharp/helloworld/README.md
index f1af1f6793c0585ddf1e5c533f52fe0f75c19c7a..63131ed98c0004ff464c36e91a1549318890e557 100644
--- a/examples/csharp/helloworld/README.md
+++ b/examples/csharp/helloworld/README.md
@@ -16,35 +16,17 @@ PREREQUISITES
 - Visual Studio 2013 or 2015
 
 **Linux**
-- Mono
-- Monodevelop 5.9 with NuGet Add-in installed
+- Mono 4.0+
+- Monodevelop 5.9+ (with NuGet plugin installed)
 
 **Mac OS X**
-- Xamarin Studio (with NuGet plugin installed)
+- Xamarin Studio 5.9+
 - [homebrew][]
 
 BUILD
 -------
 
-**Windows**
-
-- Open solution `Greeter.sln` with Visual Studio
-
-- Build the solution (this will automatically download NuGet dependencies)
-
-**Linux (Debian)**
-
-- Install gRPC C core and C# native extension using [How to use gRPC C#][] instructions
-
-- Open solution `Greeter.sln` in MonoDevelop.
-
-- Build the solution (you need to manually restore dependencies by using `mono nuget.exe restore` if you don't have NuGet add-in)
-
-**Mac OS X**
-
-- Install gRPC C core and C# native extension using [How to use gRPC C#][] instructions
-
-- Open solution `Greeter.sln` with Xamarin Studio
+- Open solution `Greeter.sln` with Visual Studio, Monodevelop (on Linux) or Xamarin Studio (on Mac OS X)
 
 - Build the solution (this will automatically download NuGet dependencies)
 
@@ -65,7 +47,7 @@ Try it!
   > GreeterClient.exe
   ```
 
-You can also run the server and client directly from Visual Studio.
+You can also run the server and client directly from the IDE.
 
 On Linux or Mac, use `mono GreeterServer.exe` and `mono GreeterClient.exe` to run the server and client.
 
@@ -76,5 +58,4 @@ You can find a more detailed tutorial in [gRPC Basics: C#][]
 
 [homebrew]:http://brew.sh
 [helloworld.proto]:../../protos/helloworld.proto
-[How to use gRPC C#]:../../../src/csharp#how-to-use
 [gRPC Basics: C#]:http://www.grpc.io/docs/tutorials/basic/csharp.html
diff --git a/examples/csharp/helloworld/generate_protos.bat b/examples/csharp/helloworld/generate_protos.bat
index 8ba2c2e936fa779fd5ae833679967783a7673cbb..7f3654c8da0331f58671721d517bc7d9d27f515c 100644
--- a/examples/csharp/helloworld/generate_protos.bat
+++ b/examples/csharp/helloworld/generate_protos.bat
@@ -5,6 +5,6 @@ setlocal
 @rem enter this directory
 cd /d %~dp0
 
-packages\Google.Protobuf.3.0.0-alpha4\tools\protoc.exe -I../../protos --csharp_out Greeter  ../../protos/helloworld.proto --grpc_out Greeter --plugin=protoc-gen-grpc=packages\Grpc.Tools.0.12.0\tools\grpc_csharp_plugin.exe
+packages\Google.Protobuf.3.0.0-beta2\tools\protoc.exe -I../../protos --csharp_out Greeter  ../../protos/helloworld.proto --grpc_out Greeter --plugin=protoc-gen-grpc=packages\Grpc.Tools.0.13.0\tools\grpc_csharp_plugin.exe
 
 endlocal
\ No newline at end of file
diff --git a/examples/csharp/route_guide/.nuget/packages.config b/examples/csharp/route_guide/.nuget/packages.config
index 1cbe7e1d65ffdc21cef806cb81315acd267de100..fb778311d1f77f07aa041cf5a28cdc8113dcf799 100644
--- a/examples/csharp/route_guide/.nuget/packages.config
+++ b/examples/csharp/route_guide/.nuget/packages.config
@@ -1,4 +1,4 @@
 <?xml version="1.0" encoding="utf-8"?>
 <packages>
-  <package id="Grpc.Tools" version="0.12.0" />
+  <package id="Grpc.Tools" version="0.13.0" />
 </packages>
\ No newline at end of file
diff --git a/examples/csharp/route_guide/RouteGuide/RouteGuide.cs b/examples/csharp/route_guide/RouteGuide/RouteGuide.cs
index deb97e1b2d75cb5280420f969b93fb3adae84631..3bd79df418935b9a39c97b6e4614be086baf046c 100644
--- a/examples/csharp/route_guide/RouteGuide/RouteGuide.cs
+++ b/examples/csharp/route_guide/RouteGuide/RouteGuide.cs
@@ -9,57 +9,62 @@ using pbr = global::Google.Protobuf.Reflection;
 using scg = global::System.Collections.Generic;
 namespace Routeguide {
 
-  namespace Proto {
-
-    [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
-    public static partial class RouteGuide {
-
-      #region Descriptor
-      public static pbr::FileDescriptor Descriptor {
-        get { return descriptor; }
-      }
-      private static pbr::FileDescriptor descriptor;
-
-      static RouteGuide() {
-        byte[] descriptorData = global::System.Convert.FromBase64String(
-            string.Concat(
-              "ChFyb3V0ZV9ndWlkZS5wcm90bxIKcm91dGVndWlkZSIsCgVQb2ludBIQCghs", 
-              "YXRpdHVkZRgBIAEoBRIRCglsb25naXR1ZGUYAiABKAUiSQoJUmVjdGFuZ2xl", 
-              "Eh0KAmxvGAEgASgLMhEucm91dGVndWlkZS5Qb2ludBIdCgJoaRgCIAEoCzIR", 
-              "LnJvdXRlZ3VpZGUuUG9pbnQiPAoHRmVhdHVyZRIMCgRuYW1lGAEgASgJEiMK", 
-              "CGxvY2F0aW9uGAIgASgLMhEucm91dGVndWlkZS5Qb2ludCJBCglSb3V0ZU5v", 
-              "dGUSIwoIbG9jYXRpb24YASABKAsyES5yb3V0ZWd1aWRlLlBvaW50Eg8KB21l", 
-              "c3NhZ2UYAiABKAkiYgoMUm91dGVTdW1tYXJ5EhMKC3BvaW50X2NvdW50GAEg", 
-              "ASgFEhUKDWZlYXR1cmVfY291bnQYAiABKAUSEAoIZGlzdGFuY2UYAyABKAUS", 
-              "FAoMZWxhcHNlZF90aW1lGAQgASgFMoUCCgpSb3V0ZUd1aWRlEjYKCkdldEZl", 
-              "YXR1cmUSES5yb3V0ZWd1aWRlLlBvaW50GhMucm91dGVndWlkZS5GZWF0dXJl", 
-              "IgASPgoMTGlzdEZlYXR1cmVzEhUucm91dGVndWlkZS5SZWN0YW5nbGUaEy5y", 
-              "b3V0ZWd1aWRlLkZlYXR1cmUiADABEj4KC1JlY29yZFJvdXRlEhEucm91dGVn", 
-              "dWlkZS5Qb2ludBoYLnJvdXRlZ3VpZGUuUm91dGVTdW1tYXJ5IgAoARI/CglS", 
-              "b3V0ZUNoYXQSFS5yb3V0ZWd1aWRlLlJvdXRlTm90ZRoVLnJvdXRlZ3VpZGUu", 
-              "Um91dGVOb3RlIgAoATABQg8KB2V4LmdycGOiAgNSVEdiBnByb3RvMw=="));
-        descriptor = pbr::FileDescriptor.InternalBuildGeneratedFileFrom(descriptorData,
-            new pbr::FileDescriptor[] { },
-            new pbr::GeneratedCodeInfo(null, new pbr::GeneratedCodeInfo[] {
-              new pbr::GeneratedCodeInfo(typeof(global::Routeguide.Point), new[]{ "Latitude", "Longitude" }, null, null, null),
-              new pbr::GeneratedCodeInfo(typeof(global::Routeguide.Rectangle), new[]{ "Lo", "Hi" }, null, null, null),
-              new pbr::GeneratedCodeInfo(typeof(global::Routeguide.Feature), new[]{ "Name", "Location" }, null, null, null),
-              new pbr::GeneratedCodeInfo(typeof(global::Routeguide.RouteNote), new[]{ "Location", "Message" }, null, null, null),
-              new pbr::GeneratedCodeInfo(typeof(global::Routeguide.RouteSummary), new[]{ "PointCount", "FeatureCount", "Distance", "ElapsedTime" }, null, null, null)
-            }));
-      }
-      #endregion
+  /// <summary>Holder for reflection information generated from route_guide.proto</summary>
+  [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
+  public static partial class RouteGuideReflection {
+
+    #region Descriptor
+    /// <summary>File descriptor for route_guide.proto</summary>
+    public static pbr::FileDescriptor Descriptor {
+      get { return descriptor; }
+    }
+    private static pbr::FileDescriptor descriptor;
+
+    static RouteGuideReflection() {
+      byte[] descriptorData = global::System.Convert.FromBase64String(
+          string.Concat(
+            "ChFyb3V0ZV9ndWlkZS5wcm90bxIKcm91dGVndWlkZSIsCgVQb2ludBIQCghs",
+            "YXRpdHVkZRgBIAEoBRIRCglsb25naXR1ZGUYAiABKAUiSQoJUmVjdGFuZ2xl",
+            "Eh0KAmxvGAEgASgLMhEucm91dGVndWlkZS5Qb2ludBIdCgJoaRgCIAEoCzIR",
+            "LnJvdXRlZ3VpZGUuUG9pbnQiPAoHRmVhdHVyZRIMCgRuYW1lGAEgASgJEiMK",
+            "CGxvY2F0aW9uGAIgASgLMhEucm91dGVndWlkZS5Qb2ludCJBCglSb3V0ZU5v",
+            "dGUSIwoIbG9jYXRpb24YASABKAsyES5yb3V0ZWd1aWRlLlBvaW50Eg8KB21l",
+            "c3NhZ2UYAiABKAkiYgoMUm91dGVTdW1tYXJ5EhMKC3BvaW50X2NvdW50GAEg",
+            "ASgFEhUKDWZlYXR1cmVfY291bnQYAiABKAUSEAoIZGlzdGFuY2UYAyABKAUS",
+            "FAoMZWxhcHNlZF90aW1lGAQgASgFMoUCCgpSb3V0ZUd1aWRlEjYKCkdldEZl",
+            "YXR1cmUSES5yb3V0ZWd1aWRlLlBvaW50GhMucm91dGVndWlkZS5GZWF0dXJl",
+            "IgASPgoMTGlzdEZlYXR1cmVzEhUucm91dGVndWlkZS5SZWN0YW5nbGUaEy5y",
+            "b3V0ZWd1aWRlLkZlYXR1cmUiADABEj4KC1JlY29yZFJvdXRlEhEucm91dGVn",
+            "dWlkZS5Qb2ludBoYLnJvdXRlZ3VpZGUuUm91dGVTdW1tYXJ5IgAoARI/CglS",
+            "b3V0ZUNoYXQSFS5yb3V0ZWd1aWRlLlJvdXRlTm90ZRoVLnJvdXRlZ3VpZGUu",
+            "Um91dGVOb3RlIgAoATABQg8KB2V4LmdycGOiAgNSVEdiBnByb3RvMw=="));
+      descriptor = pbr::FileDescriptor.FromGeneratedCode(descriptorData,
+          new pbr::FileDescriptor[] { },
+          new pbr::GeneratedCodeInfo(null, new pbr::GeneratedCodeInfo[] {
+            new pbr::GeneratedCodeInfo(typeof(global::Routeguide.Point), global::Routeguide.Point.Parser, new[]{ "Latitude", "Longitude" }, null, null, null),
+            new pbr::GeneratedCodeInfo(typeof(global::Routeguide.Rectangle), global::Routeguide.Rectangle.Parser, new[]{ "Lo", "Hi" }, null, null, null),
+            new pbr::GeneratedCodeInfo(typeof(global::Routeguide.Feature), global::Routeguide.Feature.Parser, new[]{ "Name", "Location" }, null, null, null),
+            new pbr::GeneratedCodeInfo(typeof(global::Routeguide.RouteNote), global::Routeguide.RouteNote.Parser, new[]{ "Location", "Message" }, null, null, null),
+            new pbr::GeneratedCodeInfo(typeof(global::Routeguide.RouteSummary), global::Routeguide.RouteSummary.Parser, new[]{ "PointCount", "FeatureCount", "Distance", "ElapsedTime" }, null, null, null)
+          }));
+    }
+    #endregion
 
-    }
   }
   #region Messages
+  /// <summary>
+  ///  Points are represented as latitude-longitude pairs in the E7 representation
+  ///  (degrees multiplied by 10**7 and rounded to the nearest integer).
+  ///  Latitudes should be in the range +/- 90 degrees and longitude should be in
+  ///  the range +/- 180 degrees (inclusive).
+  /// </summary>
   [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
   public sealed partial class Point : pb::IMessage<Point> {
     private static readonly pb::MessageParser<Point> _parser = new pb::MessageParser<Point>(() => new Point());
     public static pb::MessageParser<Point> Parser { get { return _parser; } }
 
     public static pbr::MessageDescriptor Descriptor {
-      get { return global::Routeguide.Proto.RouteGuide.Descriptor.MessageTypes[0]; }
+      get { return global::Routeguide.RouteGuideReflection.Descriptor.MessageTypes[0]; }
     }
 
     pbr::MessageDescriptor pb::IMessage.Descriptor {
@@ -81,6 +86,7 @@ namespace Routeguide {
       return new Point(this);
     }
 
+    /// <summary>Field number for the "latitude" field.</summary>
     public const int LatitudeFieldNumber = 1;
     private int latitude_;
     public int Latitude {
@@ -90,6 +96,7 @@ namespace Routeguide {
       }
     }
 
+    /// <summary>Field number for the "longitude" field.</summary>
     public const int LongitudeFieldNumber = 2;
     private int longitude_;
     public int Longitude {
@@ -123,7 +130,7 @@ namespace Routeguide {
     }
 
     public override string ToString() {
-      return pb::JsonFormatter.Default.Format(this);
+      return pb::JsonFormatter.ToDiagnosticString(this);
     }
 
     public void WriteTo(pb::CodedOutputStream output) {
@@ -181,13 +188,17 @@ namespace Routeguide {
 
   }
 
+  /// <summary>
+  ///  A latitude-longitude rectangle, represented as two diagonally opposite
+  ///  points "lo" and "hi".
+  /// </summary>
   [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
   public sealed partial class Rectangle : pb::IMessage<Rectangle> {
     private static readonly pb::MessageParser<Rectangle> _parser = new pb::MessageParser<Rectangle>(() => new Rectangle());
     public static pb::MessageParser<Rectangle> Parser { get { return _parser; } }
 
     public static pbr::MessageDescriptor Descriptor {
-      get { return global::Routeguide.Proto.RouteGuide.Descriptor.MessageTypes[1]; }
+      get { return global::Routeguide.RouteGuideReflection.Descriptor.MessageTypes[1]; }
     }
 
     pbr::MessageDescriptor pb::IMessage.Descriptor {
@@ -209,8 +220,12 @@ namespace Routeguide {
       return new Rectangle(this);
     }
 
+    /// <summary>Field number for the "lo" field.</summary>
     public const int LoFieldNumber = 1;
     private global::Routeguide.Point lo_;
+    /// <summary>
+    ///  One corner of the rectangle.
+    /// </summary>
     public global::Routeguide.Point Lo {
       get { return lo_; }
       set {
@@ -218,8 +233,12 @@ namespace Routeguide {
       }
     }
 
+    /// <summary>Field number for the "hi" field.</summary>
     public const int HiFieldNumber = 2;
     private global::Routeguide.Point hi_;
+    /// <summary>
+    ///  The other corner of the rectangle.
+    /// </summary>
     public global::Routeguide.Point Hi {
       get { return hi_; }
       set {
@@ -251,7 +270,7 @@ namespace Routeguide {
     }
 
     public override string ToString() {
-      return pb::JsonFormatter.Default.Format(this);
+      return pb::JsonFormatter.ToDiagnosticString(this);
     }
 
     public void WriteTo(pb::CodedOutputStream output) {
@@ -321,13 +340,18 @@ namespace Routeguide {
 
   }
 
+  /// <summary>
+  ///  A feature names something at a given point.
+  ///
+  ///  If a feature could not be named, the name is empty.
+  /// </summary>
   [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
   public sealed partial class Feature : pb::IMessage<Feature> {
     private static readonly pb::MessageParser<Feature> _parser = new pb::MessageParser<Feature>(() => new Feature());
     public static pb::MessageParser<Feature> Parser { get { return _parser; } }
 
     public static pbr::MessageDescriptor Descriptor {
-      get { return global::Routeguide.Proto.RouteGuide.Descriptor.MessageTypes[2]; }
+      get { return global::Routeguide.RouteGuideReflection.Descriptor.MessageTypes[2]; }
     }
 
     pbr::MessageDescriptor pb::IMessage.Descriptor {
@@ -349,8 +373,12 @@ namespace Routeguide {
       return new Feature(this);
     }
 
+    /// <summary>Field number for the "name" field.</summary>
     public const int NameFieldNumber = 1;
     private string name_ = "";
+    /// <summary>
+    ///  The name of the feature.
+    /// </summary>
     public string Name {
       get { return name_; }
       set {
@@ -358,8 +386,12 @@ namespace Routeguide {
       }
     }
 
+    /// <summary>Field number for the "location" field.</summary>
     public const int LocationFieldNumber = 2;
     private global::Routeguide.Point location_;
+    /// <summary>
+    ///  The point where the feature is detected.
+    /// </summary>
     public global::Routeguide.Point Location {
       get { return location_; }
       set {
@@ -391,7 +423,7 @@ namespace Routeguide {
     }
 
     public override string ToString() {
-      return pb::JsonFormatter.Default.Format(this);
+      return pb::JsonFormatter.ToDiagnosticString(this);
     }
 
     public void WriteTo(pb::CodedOutputStream output) {
@@ -455,13 +487,16 @@ namespace Routeguide {
 
   }
 
+  /// <summary>
+  ///  A RouteNote is a message sent while at a given point.
+  /// </summary>
   [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
   public sealed partial class RouteNote : pb::IMessage<RouteNote> {
     private static readonly pb::MessageParser<RouteNote> _parser = new pb::MessageParser<RouteNote>(() => new RouteNote());
     public static pb::MessageParser<RouteNote> Parser { get { return _parser; } }
 
     public static pbr::MessageDescriptor Descriptor {
-      get { return global::Routeguide.Proto.RouteGuide.Descriptor.MessageTypes[3]; }
+      get { return global::Routeguide.RouteGuideReflection.Descriptor.MessageTypes[3]; }
     }
 
     pbr::MessageDescriptor pb::IMessage.Descriptor {
@@ -483,8 +518,12 @@ namespace Routeguide {
       return new RouteNote(this);
     }
 
+    /// <summary>Field number for the "location" field.</summary>
     public const int LocationFieldNumber = 1;
     private global::Routeguide.Point location_;
+    /// <summary>
+    ///  The location from which the message is sent.
+    /// </summary>
     public global::Routeguide.Point Location {
       get { return location_; }
       set {
@@ -492,8 +531,12 @@ namespace Routeguide {
       }
     }
 
+    /// <summary>Field number for the "message" field.</summary>
     public const int MessageFieldNumber = 2;
     private string message_ = "";
+    /// <summary>
+    ///  The message to be sent.
+    /// </summary>
     public string Message {
       get { return message_; }
       set {
@@ -525,7 +568,7 @@ namespace Routeguide {
     }
 
     public override string ToString() {
-      return pb::JsonFormatter.Default.Format(this);
+      return pb::JsonFormatter.ToDiagnosticString(this);
     }
 
     public void WriteTo(pb::CodedOutputStream output) {
@@ -589,13 +632,20 @@ namespace Routeguide {
 
   }
 
+  /// <summary>
+  ///  A RouteSummary is received in response to a RecordRoute rpc.
+  ///
+  ///  It contains the number of individual points received, the number of
+  ///  detected features, and the total distance covered as the cumulative sum of
+  ///  the distance between each point.
+  /// </summary>
   [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
   public sealed partial class RouteSummary : pb::IMessage<RouteSummary> {
     private static readonly pb::MessageParser<RouteSummary> _parser = new pb::MessageParser<RouteSummary>(() => new RouteSummary());
     public static pb::MessageParser<RouteSummary> Parser { get { return _parser; } }
 
     public static pbr::MessageDescriptor Descriptor {
-      get { return global::Routeguide.Proto.RouteGuide.Descriptor.MessageTypes[4]; }
+      get { return global::Routeguide.RouteGuideReflection.Descriptor.MessageTypes[4]; }
     }
 
     pbr::MessageDescriptor pb::IMessage.Descriptor {
@@ -619,8 +669,12 @@ namespace Routeguide {
       return new RouteSummary(this);
     }
 
+    /// <summary>Field number for the "point_count" field.</summary>
     public const int PointCountFieldNumber = 1;
     private int pointCount_;
+    /// <summary>
+    ///  The number of points received.
+    /// </summary>
     public int PointCount {
       get { return pointCount_; }
       set {
@@ -628,8 +682,12 @@ namespace Routeguide {
       }
     }
 
+    /// <summary>Field number for the "feature_count" field.</summary>
     public const int FeatureCountFieldNumber = 2;
     private int featureCount_;
+    /// <summary>
+    ///  The number of known features passed while traversing the route.
+    /// </summary>
     public int FeatureCount {
       get { return featureCount_; }
       set {
@@ -637,8 +695,12 @@ namespace Routeguide {
       }
     }
 
+    /// <summary>Field number for the "distance" field.</summary>
     public const int DistanceFieldNumber = 3;
     private int distance_;
+    /// <summary>
+    ///  The distance covered in metres.
+    /// </summary>
     public int Distance {
       get { return distance_; }
       set {
@@ -646,8 +708,12 @@ namespace Routeguide {
       }
     }
 
+    /// <summary>Field number for the "elapsed_time" field.</summary>
     public const int ElapsedTimeFieldNumber = 4;
     private int elapsedTime_;
+    /// <summary>
+    ///  The duration of the traversal in seconds.
+    /// </summary>
     public int ElapsedTime {
       get { return elapsedTime_; }
       set {
@@ -683,7 +749,7 @@ namespace Routeguide {
     }
 
     public override string ToString() {
-      return pb::JsonFormatter.Default.Format(this);
+      return pb::JsonFormatter.ToDiagnosticString(this);
     }
 
     public void WriteTo(pb::CodedOutputStream output) {
diff --git a/examples/csharp/route_guide/RouteGuide/RouteGuide.csproj b/examples/csharp/route_guide/RouteGuide/RouteGuide.csproj
index 3a2a29cface182483fa8a2451d655be521ee1d8b..1fbf1ce1831fa4f76b01288d606ecac59041411b 100644
--- a/examples/csharp/route_guide/RouteGuide/RouteGuide.csproj
+++ b/examples/csharp/route_guide/RouteGuide/RouteGuide.csproj
@@ -11,7 +11,7 @@
     <AssemblyName>RouteGuide</AssemblyName>
     <TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
     <FileAlignment>512</FileAlignment>
-    <NuGetPackageImportStamp>68b3dd23</NuGetPackageImportStamp>
+    <NuGetPackageImportStamp>5b6d924a</NuGetPackageImportStamp>
   </PropertyGroup>
   <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
     <DebugSymbols>true</DebugSymbols>
@@ -31,11 +31,13 @@
     <WarningLevel>4</WarningLevel>
   </PropertyGroup>
   <ItemGroup>
-    <Reference Include="Google.Protobuf">
-      <HintPath>..\packages\Google.Protobuf.3.0.0-alpha4\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
+    <Reference Include="Google.Protobuf, Version=3.0.0.0, Culture=neutral, PublicKeyToken=a7d26565bac4d604, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Google.Protobuf.3.0.0-beta2\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
     </Reference>
-    <Reference Include="Grpc.Core">
-      <HintPath>..\packages\Grpc.Core.0.12.0\lib\net45\Grpc.Core.dll</HintPath>
+    <Reference Include="Grpc.Core, Version=0.12.0.0, Culture=neutral, PublicKeyToken=d754f35622e28bad, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Grpc.Core.0.13.0\lib\net45\Grpc.Core.dll</HintPath>
     </Reference>
     <Reference Include="Newtonsoft.Json, Version=7.0.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL">
       <SpecificVersion>False</SpecificVersion>
@@ -65,17 +67,13 @@
     </None>
   </ItemGroup>
   <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
-  <Import Project="..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets" Condition="Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" />
+  <Import Project="..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
   <Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
     <PropertyGroup>
       <ErrorText>This project references NuGet package(s) that are missing on this computer. Enable NuGet Package Restore to download them.  For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
     </PropertyGroup>
-    <Error Condition="!Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
+    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
   </Target>
-  <Import Project="..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets" Condition="Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" />
-  <Import Project="..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
   <!-- To modify your build process, add your task inside one of the targets below and uncomment it. 
        Other similar extension points exist, see Microsoft.Common.targets.
   <Target Name="BeforeBuild">
diff --git a/examples/csharp/route_guide/RouteGuide/RouteGuideGrpc.cs b/examples/csharp/route_guide/RouteGuide/RouteGuideGrpc.cs
index d60256fff6520f5a60b0f5774fda9c603214e4b8..66d1c07978656805ab7bd7c9ea003b755c566027 100644
--- a/examples/csharp/route_guide/RouteGuide/RouteGuideGrpc.cs
+++ b/examples/csharp/route_guide/RouteGuide/RouteGuideGrpc.cs
@@ -49,7 +49,7 @@ namespace Routeguide {
     // service descriptor
     public static global::Google.Protobuf.Reflection.ServiceDescriptor Descriptor
     {
-      get { return global::Routeguide.Proto.RouteGuide.Descriptor.Services[0]; }
+      get { return global::Routeguide.RouteGuideReflection.Descriptor.Services[0]; }
     }
 
     // client interface
diff --git a/examples/csharp/route_guide/RouteGuide/packages.config b/examples/csharp/route_guide/RouteGuide/packages.config
index 87173151026cf0e844e4988866dc636431dcdd31..e4e21099494af7eadc885d015d3c53020f761961 100644
--- a/examples/csharp/route_guide/RouteGuide/packages.config
+++ b/examples/csharp/route_guide/RouteGuide/packages.config
@@ -1,11 +1,9 @@
 <?xml version="1.0" encoding="utf-8"?>
 <packages>
-  <package id="Google.Protobuf" version="3.0.0-alpha4" targetFramework="net45" />
-  <package id="Grpc" version="0.12.0" targetFramework="net45" />
-  <package id="Grpc.Core" version="0.12.0" targetFramework="net45" />
-  <package id="grpc.dependencies.openssl.redist" version="1.0.204.1" targetFramework="net45" />
-  <package id="grpc.dependencies.zlib.redist" version="1.2.8.10" targetFramework="net45" />
-  <package id="grpc.native.csharp" version="0.12.0" targetFramework="net45" />
+  <package id="Google.Protobuf" version="3.0.0-beta2" targetFramework="net45" />
+  <package id="Grpc" version="0.13.0" targetFramework="net45" />
+  <package id="Grpc.Core" version="0.13.0" targetFramework="net45" />
+  <package id="grpc.native.csharp" version="0.13.0" targetFramework="net45" />
   <package id="Ix-Async" version="1.2.3" targetFramework="net45" />
   <package id="Newtonsoft.Json" version="7.0.1" targetFramework="net45" />
 </packages>
\ No newline at end of file
diff --git a/examples/csharp/route_guide/RouteGuideClient/RouteGuideClient.csproj b/examples/csharp/route_guide/RouteGuideClient/RouteGuideClient.csproj
index 89e5025df838ffcbbcf546abe6ca01d81d58a8ee..f55627ed5ca48e4529618139d9d3d3a756bf3567 100644
--- a/examples/csharp/route_guide/RouteGuideClient/RouteGuideClient.csproj
+++ b/examples/csharp/route_guide/RouteGuideClient/RouteGuideClient.csproj
@@ -11,7 +11,7 @@
     <AssemblyName>RouteGuideClient</AssemblyName>
     <TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
     <FileAlignment>512</FileAlignment>
-    <NuGetPackageImportStamp>f5579f73</NuGetPackageImportStamp>
+    <NuGetPackageImportStamp>69015b00</NuGetPackageImportStamp>
   </PropertyGroup>
   <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
     <PlatformTarget>AnyCPU</PlatformTarget>
@@ -33,11 +33,13 @@
     <WarningLevel>4</WarningLevel>
   </PropertyGroup>
   <ItemGroup>
-    <Reference Include="Google.Protobuf">
-      <HintPath>..\packages\Google.Protobuf.3.0.0-alpha4\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
+    <Reference Include="Google.Protobuf, Version=3.0.0.0, Culture=neutral, PublicKeyToken=a7d26565bac4d604, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Google.Protobuf.3.0.0-beta2\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
     </Reference>
-    <Reference Include="Grpc.Core">
-      <HintPath>..\packages\Grpc.Core.0.12.0\lib\net45\Grpc.Core.dll</HintPath>
+    <Reference Include="Grpc.Core, Version=0.12.0.0, Culture=neutral, PublicKeyToken=d754f35622e28bad, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Grpc.Core.0.13.0\lib\net45\Grpc.Core.dll</HintPath>
     </Reference>
     <Reference Include="Newtonsoft.Json, Version=7.0.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL">
       <SpecificVersion>False</SpecificVersion>
@@ -68,17 +70,13 @@
     </ProjectReference>
   </ItemGroup>
   <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
-  <Import Project="..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets" Condition="Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" />
+  <Import Project="..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
   <Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
     <PropertyGroup>
       <ErrorText>This project references NuGet package(s) that are missing on this computer. Enable NuGet Package Restore to download them.  For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
     </PropertyGroup>
-    <Error Condition="!Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
+    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
   </Target>
-  <Import Project="..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets" Condition="Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" />
-  <Import Project="..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
   <!-- To modify your build process, add your task inside one of the targets below and uncomment it. 
        Other similar extension points exist, see Microsoft.Common.targets.
   <Target Name="BeforeBuild">
diff --git a/examples/csharp/route_guide/RouteGuideClient/packages.config b/examples/csharp/route_guide/RouteGuideClient/packages.config
index 87173151026cf0e844e4988866dc636431dcdd31..e4e21099494af7eadc885d015d3c53020f761961 100644
--- a/examples/csharp/route_guide/RouteGuideClient/packages.config
+++ b/examples/csharp/route_guide/RouteGuideClient/packages.config
@@ -1,11 +1,9 @@
 <?xml version="1.0" encoding="utf-8"?>
 <packages>
-  <package id="Google.Protobuf" version="3.0.0-alpha4" targetFramework="net45" />
-  <package id="Grpc" version="0.12.0" targetFramework="net45" />
-  <package id="Grpc.Core" version="0.12.0" targetFramework="net45" />
-  <package id="grpc.dependencies.openssl.redist" version="1.0.204.1" targetFramework="net45" />
-  <package id="grpc.dependencies.zlib.redist" version="1.2.8.10" targetFramework="net45" />
-  <package id="grpc.native.csharp" version="0.12.0" targetFramework="net45" />
+  <package id="Google.Protobuf" version="3.0.0-beta2" targetFramework="net45" />
+  <package id="Grpc" version="0.13.0" targetFramework="net45" />
+  <package id="Grpc.Core" version="0.13.0" targetFramework="net45" />
+  <package id="grpc.native.csharp" version="0.13.0" targetFramework="net45" />
   <package id="Ix-Async" version="1.2.3" targetFramework="net45" />
   <package id="Newtonsoft.Json" version="7.0.1" targetFramework="net45" />
 </packages>
\ No newline at end of file
diff --git a/examples/csharp/route_guide/RouteGuideServer/RouteGuideServer.csproj b/examples/csharp/route_guide/RouteGuideServer/RouteGuideServer.csproj
index 2e930625c42c403e22de636be5ee4a0f94822106..873556d65c6d7dd5cdec0c4310136a335b6406f4 100644
--- a/examples/csharp/route_guide/RouteGuideServer/RouteGuideServer.csproj
+++ b/examples/csharp/route_guide/RouteGuideServer/RouteGuideServer.csproj
@@ -11,7 +11,7 @@
     <AssemblyName>RouteGuideServer</AssemblyName>
     <TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
     <FileAlignment>512</FileAlignment>
-    <NuGetPackageImportStamp>89e15444</NuGetPackageImportStamp>
+    <NuGetPackageImportStamp>656158d8</NuGetPackageImportStamp>
   </PropertyGroup>
   <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
     <PlatformTarget>AnyCPU</PlatformTarget>
@@ -33,11 +33,13 @@
     <WarningLevel>4</WarningLevel>
   </PropertyGroup>
   <ItemGroup>
-    <Reference Include="Google.Protobuf">
-      <HintPath>..\packages\Google.Protobuf.3.0.0-alpha4\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
+    <Reference Include="Google.Protobuf, Version=3.0.0.0, Culture=neutral, PublicKeyToken=a7d26565bac4d604, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Google.Protobuf.3.0.0-beta2\lib\portable-net45+netcore45+wpa81+wp8\Google.Protobuf.dll</HintPath>
     </Reference>
-    <Reference Include="Grpc.Core">
-      <HintPath>..\packages\Grpc.Core.0.12.0\lib\net45\Grpc.Core.dll</HintPath>
+    <Reference Include="Grpc.Core, Version=0.12.0.0, Culture=neutral, PublicKeyToken=d754f35622e28bad, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\packages\Grpc.Core.0.13.0\lib\net45\Grpc.Core.dll</HintPath>
     </Reference>
     <Reference Include="Newtonsoft.Json, Version=7.0.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL">
       <SpecificVersion>False</SpecificVersion>
@@ -69,17 +71,13 @@
     </ProjectReference>
   </ItemGroup>
   <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
-  <Import Project="..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets" Condition="Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" />
+  <Import Project="..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
   <Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
     <PropertyGroup>
       <ErrorText>This project references NuGet package(s) that are missing on this computer. Enable NuGet Package Restore to download them.  For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
     </PropertyGroup>
-    <Error Condition="!Exists('..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.zlib.redist.1.2.8.10\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.zlib.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets'))" />
-    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
+    <Error Condition="!Exists('..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\grpc.native.csharp.0.13.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets'))" />
   </Target>
-  <Import Project="..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets" Condition="Exists('..\packages\grpc.dependencies.openssl.redist.1.0.204.1\build\portable-net45+netcore45+wpa81+wp8\grpc.dependencies.openssl.redist.targets')" />
-  <Import Project="..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets" Condition="Exists('..\packages\grpc.native.csharp.0.12.0\build\portable-net45+netcore45+wpa81+wp8\grpc.native.csharp.targets')" />
   <!-- To modify your build process, add your task inside one of the targets below and uncomment it. 
        Other similar extension points exist, see Microsoft.Common.targets.
   <Target Name="BeforeBuild">
diff --git a/examples/csharp/route_guide/RouteGuideServer/packages.config b/examples/csharp/route_guide/RouteGuideServer/packages.config
index 87173151026cf0e844e4988866dc636431dcdd31..e4e21099494af7eadc885d015d3c53020f761961 100644
--- a/examples/csharp/route_guide/RouteGuideServer/packages.config
+++ b/examples/csharp/route_guide/RouteGuideServer/packages.config
@@ -1,11 +1,9 @@
 <?xml version="1.0" encoding="utf-8"?>
 <packages>
-  <package id="Google.Protobuf" version="3.0.0-alpha4" targetFramework="net45" />
-  <package id="Grpc" version="0.12.0" targetFramework="net45" />
-  <package id="Grpc.Core" version="0.12.0" targetFramework="net45" />
-  <package id="grpc.dependencies.openssl.redist" version="1.0.204.1" targetFramework="net45" />
-  <package id="grpc.dependencies.zlib.redist" version="1.2.8.10" targetFramework="net45" />
-  <package id="grpc.native.csharp" version="0.12.0" targetFramework="net45" />
+  <package id="Google.Protobuf" version="3.0.0-beta2" targetFramework="net45" />
+  <package id="Grpc" version="0.13.0" targetFramework="net45" />
+  <package id="Grpc.Core" version="0.13.0" targetFramework="net45" />
+  <package id="grpc.native.csharp" version="0.13.0" targetFramework="net45" />
   <package id="Ix-Async" version="1.2.3" targetFramework="net45" />
   <package id="Newtonsoft.Json" version="7.0.1" targetFramework="net45" />
 </packages>
\ No newline at end of file
diff --git a/examples/csharp/route_guide/generate_protos.bat b/examples/csharp/route_guide/generate_protos.bat
index fad63ef0aeba4904c3387d0c72e29e337fcb201d..d9cd021a917ce7993b4e9b0e22081be76a5a76b0 100644
--- a/examples/csharp/route_guide/generate_protos.bat
+++ b/examples/csharp/route_guide/generate_protos.bat
@@ -5,6 +5,6 @@ setlocal
 @rem enter this directory
 cd /d %~dp0
 
-packages\Google.Protobuf.3.0.0-alpha4\tools\protoc.exe -I../../protos --csharp_out RouteGuide  ../../protos/route_guide.proto --grpc_out RouteGuide --plugin=protoc-gen-grpc=packages\Grpc.Tools.0.12.0\tools\grpc_csharp_plugin.exe
+packages\Google.Protobuf.3.0.0-beta2\tools\protoc.exe -I../../protos --csharp_out RouteGuide  ../../protos/route_guide.proto --grpc_out RouteGuide --plugin=protoc-gen-grpc=packages\Grpc.Tools.0.13.0\tools\grpc_csharp_plugin.exe
 
 endlocal
\ No newline at end of file
diff --git a/examples/python/README.md b/examples/python/README.md
index 7b48c824baea41fa358c5a5c9a1d7426902de900..b57da8f6428846027b455e842828c792f0bd7852 100644
--- a/examples/python/README.md
+++ b/examples/python/README.md
@@ -6,24 +6,18 @@ Background
 For this sample, we've already generated the server and client stubs from
 [helloworld.proto][] and we'll be using a specific reference platform.
 
-Prerequisites
--------------
-
-- Debian 8.2 "Jessie" platform with `root` access
-- `git`
-- `python2.7`
-- `pip`
-- Python development headers
 
-Set-up
--------
+Install gRPC:
   ```sh
-  $ # install the gRPC Core:
-  $ sudo apt-get install libgrpc-dev
-  $ # install gRPC Python:
-  $ sudo pip install -U grpcio==0.11.0b1
-  $ # Since this "hello, world" example uses protocol buffers:
-  $ sudo pip install -U protobuf==3.0.0a3
+  $ pip install grpcio
+```
+Or, to install it system wide:
+```sh
+	$ sudo pip install grpcio
+```
+
+Download the example
+```sh
   $ # Clone the repository to get the example code:
   $ git clone https://github.com/grpc/grpc
   $ # Navigate to the "hello, world" Python example:
diff --git a/examples/python/helloworld/run_client.sh b/examples/python/helloworld/run_client.sh
deleted file mode 100755
index 1c0ce020ee2f3617edbe47a0b3fb0a2b38f43f59..0000000000000000000000000000000000000000
--- a/examples/python/helloworld/run_client.sh
+++ /dev/null
@@ -1,36 +0,0 @@
-#!/bin/bash
-# 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.
-
-# This is where you have cloned out the https://github.com/grpc/grpc repository
-# And built gRPC Python.
-# ADJUST THIS PATH TO WHERE YOUR ACTUAL LOCATION IS
-GRPC_ROOT=~/github/grpc
-
-$GRPC_ROOT/python2.7_virtual_environment/bin/python greeter_client.py
diff --git a/examples/python/helloworld/run_server.sh b/examples/python/helloworld/run_server.sh
deleted file mode 100755
index 82ebb1f86867e8c8a9770d90ef12dcc62b3aedb6..0000000000000000000000000000000000000000
--- a/examples/python/helloworld/run_server.sh
+++ /dev/null
@@ -1,37 +0,0 @@
-#!/bin/bash
-# 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.
-
-# This is where you have cloned out the https://github.com/grpc/grpc repository
-# And built gRPC Python.
-# ADJUST THIS PATH TO WHERE YOUR ACTUAL LOCATION IS
-GRPC_ROOT=~/github/grpc
-
-$GRPC_ROOT/python2.7_virtual_environment/bin/python greeter_server.py
-
diff --git a/examples/python/route_guide/run_client.sh b/examples/python/route_guide/run_client.sh
deleted file mode 100755
index e5fd383859e70114bf53e85a53d0fc094641882b..0000000000000000000000000000000000000000
--- a/examples/python/route_guide/run_client.sh
+++ /dev/null
@@ -1,36 +0,0 @@
-#!/bin/bash
-# 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.
-
-# This is where you have cloned out the https://github.com/grpc/grpc repository
-# And built gRPC Python.
-# ADJUST THIS PATH TO WHERE YOUR ACTUAL LOCATION IS
-GRPC_ROOT=~/github/grpc
-
-$GRPC_ROOT/python2.7_virtual_environment/bin/python -B route_guide_client.py
diff --git a/examples/python/route_guide/run_server.sh b/examples/python/route_guide/run_server.sh
deleted file mode 100755
index 7b1a764c061b4e2899ceec3d9962e7f410a67eb7..0000000000000000000000000000000000000000
--- a/examples/python/route_guide/run_server.sh
+++ /dev/null
@@ -1,36 +0,0 @@
-#!/bin/bash
-# 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.
-
-# This is where you have cloned out the https://github.com/grpc/grpc repository
-# And built gRPC Python.
-# ADJUST THIS PATH TO WHERE YOUR ACTUAL LOCATION IS
-GRPC_ROOT=~/github/grpc
-
-$GRPC_ROOT/python2.7_virtual_environment/bin/python -B route_guide_server.py
diff --git a/include/grpc++/alarm.h b/include/grpc++/alarm.h
index 9979c34e4f13190ea70333af35a80ad5aec2f6e3..3b8104d135700fc45bd8418eaa002f38ddf75fc8 100644
--- a/include/grpc++/alarm.h
+++ b/include/grpc++/alarm.h
@@ -36,9 +36,12 @@
 #ifndef GRPCXX_ALARM_H
 #define GRPCXX_ALARM_H
 
+#include <grpc++/impl/codegen/completion_queue.h>
 #include <grpc++/impl/codegen/completion_queue_tag.h>
 #include <grpc++/impl/codegen/grpc_library.h>
 #include <grpc++/impl/codegen/time.h>
+#include <grpc++/impl/grpc_library.h>
+#include <grpc/grpc.h>
 
 struct grpc_alarm;
 
@@ -54,14 +57,22 @@ class Alarm : private GrpcLibrary {
   /// Once the alarm expires (at \a deadline) or it's cancelled (see \a Cancel),
   /// an event with tag \a tag will be added to \a cq. If the alarm expired, the
   /// event's success bit will be true, false otherwise (ie, upon cancellation).
-  Alarm(CompletionQueue* cq, gpr_timespec deadline, void* tag);
+  /// \internal We rely on the presence of \a cq for grpc initialization. If \a
+  /// cq were ever to be removed, a reference to a static
+  /// internal::GrpcLibraryInitializer instance would need to be introduced
+  /// here. \endinternal.
+  template <typename T>
+  Alarm(CompletionQueue* cq, const T& deadline, void* tag)
+      : tag_(tag),
+        alarm_(grpc_alarm_create(cq->cq(), TimePoint<T>(deadline).raw_time(),
+                                 static_cast<void*>(&tag_))) {}
 
   /// Destroy the given completion queue alarm, cancelling it in the process.
-  ~Alarm();
+  ~Alarm() { grpc_alarm_destroy(alarm_); }
 
   /// Cancel a completion queue alarm. Calling this function over an alarm that
   /// has already fired has no effect.
-  void Cancel();
+  void Cancel() { grpc_alarm_cancel(alarm_); }
 
  private:
   class AlarmEntry : public CompletionQueueTag {
diff --git a/package.xml b/package.xml
index 28287c6fa7d48a205db48d170ac2cd500279dc19..e61e49c2add136287d7ceb655aad82d510d55fa0 100644
--- a/package.xml
+++ b/package.xml
@@ -10,7 +10,7 @@
   <email>grpc-packages@google.com</email>
   <active>yes</active>
  </lead>
- <date>2016-02-25</date>
+ <date>2016-02-24</date>
  <time>16:06:07</time>
  <version>
   <release>0.8.0</release>
@@ -854,32 +854,6 @@
     <file baseinstalldir="/" name="third_party/boringssl/ssl/t1_enc.c" role="src" />
     <file baseinstalldir="/" name="third_party/boringssl/ssl/t1_lib.c" role="src" />
     <file baseinstalldir="/" name="third_party/boringssl/ssl/tls_record.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/crc32.h" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/deflate.h" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/gzguts.h" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/inffast.h" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/inffixed.h" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/inflate.h" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/inftrees.h" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/trees.h" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/zconf.h" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/zlib.h" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/zutil.h" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/adler32.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/compress.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/crc32.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/deflate.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/gzclose.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/gzlib.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/gzread.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/gzwrite.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/infback.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/inffast.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/inflate.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/inftrees.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/trees.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/uncompr.c" role="src" />
-    <file baseinstalldir="/" name="third_party/zlib/zutil.c" role="src" />
   </dir>
  </contents>
  <dependencies>
@@ -987,7 +961,7 @@ Update to wrap gRPC C Core version 0.10.0
     <release>beta</release>
     <api>beta</api>
    </stability>
-   <date>2016-02-25</date>
+   <date>2016-02-24</date>
    <license>BSD</license>
    <notes>
 - Simplify gRPC PHP installation #4517
diff --git a/setup.py b/setup.py
index 5b9f9b6c662f606cc10e791a471fdad8c951ff29..cfb578e21581645985c72e23c6acd820a470c041 100644
--- a/setup.py
+++ b/setup.py
@@ -208,7 +208,6 @@ PACKAGE_DATA = {
         '_credentials/roots.pem',
         '_windows/grpc_c.32.python',
         '_windows/grpc_c.64.python',
-        'cygrpc.so',
     ],
 }
 if INSTALL_TESTS:
diff --git a/src/core/client_config/lb_policy.c b/src/core/client_config/lb_policy.c
index 5ff623e0069d64eed9d487eb9c2c4c1164ebc93b..0d8b0073369c32812ba64b0925ea34ecbfce141a 100644
--- a/src/core/client_config/lb_policy.c
+++ b/src/core/client_config/lb_policy.c
@@ -1,6 +1,6 @@
 /*
  *
- * Copyright 2015, Google Inc.
+ * Copyright 2015-2016, Google Inc.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
diff --git a/src/core/client_config/lb_policy.h b/src/core/client_config/lb_policy.h
index 4fbb12da3946decc7029faac78f983d830a68243..345739060682c0fb96fbd7f41c81a00546ab84b2 100644
--- a/src/core/client_config/lb_policy.h
+++ b/src/core/client_config/lb_policy.h
@@ -1,6 +1,6 @@
 /*
  *
- * Copyright 2015, Google Inc.
+ * Copyright 2015-2016, Google Inc.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
diff --git a/src/core/httpcli/httpcli.c b/src/core/httpcli/httpcli.c
index 63f37252192100f76c47fc67ba02e771b5c412cf..1219c444c715ce99aebf82944c84cce3ba85df4d 100644
--- a/src/core/httpcli/httpcli.c
+++ b/src/core/httpcli/httpcli.c
@@ -39,6 +39,7 @@
 #include <grpc/support/alloc.h>
 #include <grpc/support/log.h>
 #include <grpc/support/string_util.h>
+
 #include "src/core/httpcli/format_request.h"
 #include "src/core/httpcli/parser.h"
 #include "src/core/iomgr/endpoint.h"
diff --git a/src/core/httpcli/httpcli.h b/src/core/httpcli/httpcli.h
index 86e17c1d6978743019005a6067696ac464eb689b..c9cd987c794f505dd8258a3af74a00dbad2e10aa 100644
--- a/src/core/httpcli/httpcli.h
+++ b/src/core/httpcli/httpcli.h
@@ -1,6 +1,6 @@
 /*
  *
- * Copyright 2015, Google Inc.
+ * Copyright 2015-2016, Google Inc.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
diff --git a/src/core/httpcli/httpcli_security_connector.c b/src/core/httpcli/httpcli_security_connector.c
index 41ad1de6c00dba11c869a70ad71d4986e0ffc092..156961a377a5abced49e4d7e8dead5b8b1a857af 100644
--- a/src/core/httpcli/httpcli_security_connector.c
+++ b/src/core/httpcli/httpcli_security_connector.c
@@ -59,7 +59,7 @@ static void httpcli_ssl_destroy(grpc_security_connector *sc) {
 }
 
 static void httpcli_ssl_do_handshake(grpc_exec_ctx *exec_ctx,
-                                     grpc_security_connector *sc,
+                                     grpc_channel_security_connector *sc,
                                      grpc_endpoint *nonsecure_endpoint,
                                      grpc_security_handshake_done_cb cb,
                                      void *user_data) {
@@ -78,8 +78,8 @@ static void httpcli_ssl_do_handshake(grpc_exec_ctx *exec_ctx,
             tsi_result_to_string(result));
     cb(exec_ctx, user_data, GRPC_SECURITY_ERROR, NULL, NULL);
   } else {
-    grpc_do_security_handshake(exec_ctx, handshaker, sc, nonsecure_endpoint, cb,
-                               user_data);
+    grpc_do_security_handshake(exec_ctx, handshaker, &sc->base, true,
+                               nonsecure_endpoint, cb, user_data);
   }
 }
 
@@ -103,7 +103,7 @@ static void httpcli_ssl_check_peer(grpc_exec_ctx *exec_ctx,
 }
 
 static grpc_security_connector_vtable httpcli_ssl_vtable = {
-    httpcli_ssl_destroy, httpcli_ssl_do_handshake, httpcli_ssl_check_peer};
+    httpcli_ssl_destroy, httpcli_ssl_check_peer};
 
 static grpc_security_status httpcli_ssl_channel_security_connector_create(
     const unsigned char *pem_root_certs, size_t pem_root_certs_size,
@@ -121,7 +121,6 @@ static grpc_security_status httpcli_ssl_channel_security_connector_create(
   memset(c, 0, sizeof(grpc_httpcli_ssl_channel_security_connector));
 
   gpr_ref_init(&c->base.base.refcount, 1);
-  c->base.base.is_client_side = 1;
   c->base.base.vtable = &httpcli_ssl_vtable;
   if (secure_peer_name != NULL) {
     c->secure_peer_name = gpr_strdup(secure_peer_name);
@@ -136,6 +135,7 @@ static grpc_security_status httpcli_ssl_channel_security_connector_create(
     *sc = NULL;
     return GRPC_SECURITY_ERROR;
   }
+  c->base.do_handshake = httpcli_ssl_do_handshake;
   *sc = &c->base;
   return GRPC_SECURITY_OK;
 }
@@ -180,8 +180,8 @@ static void ssl_handshake(grpc_exec_ctx *exec_ctx, void *arg,
   GPR_ASSERT(httpcli_ssl_channel_security_connector_create(
                  pem_root_certs, pem_root_certs_size, host, &sc) ==
              GRPC_SECURITY_OK);
-  grpc_security_connector_do_handshake(exec_ctx, &sc->base, tcp,
-                                       on_secure_transport_setup_done, c);
+  grpc_channel_security_connector_do_handshake(
+      exec_ctx, sc, tcp, on_secure_transport_setup_done, c);
   GRPC_SECURITY_CONNECTOR_UNREF(&sc->base, "httpcli");
 }
 
diff --git a/src/core/iomgr/ev_poll_and_epoll_posix.c b/src/core/iomgr/ev_poll_and_epoll_posix.c
index 7de8c665e239adb0f89ee8444e08df2305a01154..5ff02bb21647ad24ec81f67a5f701973d8407234 100644
--- a/src/core/iomgr/ev_poll_and_epoll_posix.c
+++ b/src/core/iomgr/ev_poll_and_epoll_posix.c
@@ -152,13 +152,6 @@ static void fd_end_poll(grpc_exec_ctx *exec_ctx, grpc_fd_watcher *rec,
 /* Return 1 if this fd is orphaned, 0 otherwise */
 static bool fd_is_orphaned(grpc_fd *fd);
 
-/* Notification from the poller to an fd that it has become readable or
-   writable.
-   If allow_synchronous_callback is 1, allow running the fd callback inline
-   in this callstack, otherwise register an asynchronous callback and return */
-static void fd_become_readable(grpc_exec_ctx *exec_ctx, grpc_fd *fd);
-static void fd_become_writable(grpc_exec_ctx *exec_ctx, grpc_fd *fd);
-
 /* Reference counting for fds */
 /*#define GRPC_FD_REF_COUNT_DEBUG*/
 #ifdef GRPC_FD_REF_COUNT_DEBUG
@@ -205,7 +198,7 @@ struct grpc_pollset {
      For example, we may choose a poll() based implementation on linux for
      few fds, and an epoll() based implementation for many fds */
   const grpc_pollset_vtable *vtable;
-  gpr_mu *mu;
+  gpr_mu mu;
   grpc_pollset_worker root_worker;
   int in_flight_cbs;
   int shutting_down;
@@ -421,11 +414,11 @@ static bool fd_is_orphaned(grpc_fd *fd) {
 }
 
 static void pollset_kick_locked(grpc_fd_watcher *watcher) {
-  gpr_mu_lock(watcher->pollset->mu);
+  gpr_mu_lock(&watcher->pollset->mu);
   GPR_ASSERT(watcher->worker);
   pollset_kick_ext(watcher->pollset, watcher->worker,
                    GRPC_POLLSET_REEVALUATE_POLLING_ON_WAKEUP);
-  gpr_mu_unlock(watcher->pollset->mu);
+  gpr_mu_unlock(&watcher->pollset->mu);
 }
 
 static void maybe_wake_one_watcher_locked(grpc_fd *fd) {
@@ -550,14 +543,6 @@ static int set_ready_locked(grpc_exec_ctx *exec_ctx, grpc_fd *fd,
   }
 }
 
-static void set_ready(grpc_exec_ctx *exec_ctx, grpc_fd *fd, grpc_closure **st) {
-  /* only one set_ready can be active at once (but there may be a racing
-     notify_on) */
-  gpr_mu_lock(&fd->mu);
-  set_ready_locked(exec_ctx, fd, st);
-  gpr_mu_unlock(&fd->mu);
-}
-
 static void fd_shutdown(grpc_exec_ctx *exec_ctx, grpc_fd *fd) {
   gpr_mu_lock(&fd->mu);
   GPR_ASSERT(!fd->shutdown);
@@ -686,14 +671,6 @@ static void fd_end_poll(grpc_exec_ctx *exec_ctx, grpc_fd_watcher *watcher,
   GRPC_FD_UNREF(fd, "poll");
 }
 
-static void fd_become_readable(grpc_exec_ctx *exec_ctx, grpc_fd *fd) {
-  set_ready(exec_ctx, fd, &fd->read_closure);
-}
-
-static void fd_become_writable(grpc_exec_ctx *exec_ctx, grpc_fd *fd) {
-  set_ready(exec_ctx, fd, &fd->write_closure);
-}
-
 /*******************************************************************************
  * pollset_posix.c
  */
@@ -828,8 +805,9 @@ static void kick_poller(void) { grpc_wakeup_fd_wakeup(&grpc_global_wakeup_fd); }
 
 static void become_basic_pollset(grpc_pollset *pollset, grpc_fd *fd_or_null);
 
-static void pollset_init(grpc_pollset *pollset, gpr_mu *mu) {
-  pollset->mu = mu;
+static void pollset_init(grpc_pollset *pollset, gpr_mu **mu) {
+  gpr_mu_init(&pollset->mu);
+  *mu = &pollset->mu;
   pollset->root_worker.next = pollset->root_worker.prev = &pollset->root_worker;
   pollset->in_flight_cbs = 0;
   pollset->shutting_down = 0;
@@ -852,6 +830,7 @@ static void pollset_destroy(grpc_pollset *pollset) {
     gpr_free(pollset->local_wakeup_cache);
     pollset->local_wakeup_cache = next;
   }
+  gpr_mu_destroy(&pollset->mu);
 }
 
 static void pollset_reset(grpc_pollset *pollset) {
@@ -868,15 +847,15 @@ static void pollset_reset(grpc_pollset *pollset) {
 
 static void pollset_add_fd(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
                            grpc_fd *fd) {
-  gpr_mu_lock(pollset->mu);
+  gpr_mu_lock(&pollset->mu);
   pollset->vtable->add_fd(exec_ctx, pollset, fd, 1);
 /* the following (enabled only in debug) will reacquire and then release
    our lock - meaning that if the unlocking flag passed to add_fd above is
    not respected, the code will deadlock (in a way that we have a chance of
    debugging) */
 #ifndef NDEBUG
-  gpr_mu_lock(pollset->mu);
-  gpr_mu_unlock(pollset->mu);
+  gpr_mu_lock(&pollset->mu);
+  gpr_mu_unlock(&pollset->mu);
 #endif
 }
 
@@ -925,7 +904,7 @@ static void pollset_work(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
   /* Give do_promote priority so we don't starve it out */
   if (pollset->in_flight_cbs) {
     GPR_TIMER_MARK("pollset_work.in_flight_cbs", 0);
-    gpr_mu_unlock(pollset->mu);
+    gpr_mu_unlock(&pollset->mu);
     locked = 0;
     goto done;
   }
@@ -959,7 +938,7 @@ static void pollset_work(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
   done:
     if (!locked) {
       queued_work |= grpc_exec_ctx_flush(exec_ctx);
-      gpr_mu_lock(pollset->mu);
+      gpr_mu_lock(&pollset->mu);
       locked = 1;
     }
     /* If we're forced to re-evaluate polling (via pollset_kick with
@@ -989,19 +968,19 @@ static void pollset_work(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
       pollset_kick(pollset, NULL);
     } else if (!pollset->called_shutdown && pollset->in_flight_cbs == 0) {
       pollset->called_shutdown = 1;
-      gpr_mu_unlock(pollset->mu);
+      gpr_mu_unlock(&pollset->mu);
       finish_shutdown(exec_ctx, pollset);
       grpc_exec_ctx_flush(exec_ctx);
       /* Continuing to access pollset here is safe -- it is the caller's
        * responsibility to not destroy when it has outstanding calls to
        * pollset_work.
        * TODO(dklempner): Can we refactor the shutdown logic to avoid this? */
-      gpr_mu_lock(pollset->mu);
+      gpr_mu_lock(&pollset->mu);
     } else if (!grpc_closure_list_empty(pollset->idle_jobs)) {
       grpc_exec_ctx_enqueue_list(exec_ctx, &pollset->idle_jobs, NULL);
-      gpr_mu_unlock(pollset->mu);
+      gpr_mu_unlock(&pollset->mu);
       grpc_exec_ctx_flush(exec_ctx);
-      gpr_mu_lock(pollset->mu);
+      gpr_mu_lock(&pollset->mu);
     }
   }
   *worker_hdl = NULL;
@@ -1069,7 +1048,7 @@ static void basic_do_promote(grpc_exec_ctx *exec_ctx, void *args,
    * 4. The pollset may be shutting down.
    */
 
-  gpr_mu_lock(pollset->mu);
+  gpr_mu_lock(&pollset->mu);
   /* First we need to ensure that nobody is polling concurrently */
   GPR_ASSERT(!pollset_has_workers(pollset));
 
@@ -1109,7 +1088,7 @@ static void basic_do_promote(grpc_exec_ctx *exec_ctx, void *args,
     }
   }
 
-  gpr_mu_unlock(pollset->mu);
+  gpr_mu_unlock(&pollset->mu);
 
   /* Matching ref in basic_pollset_add_fd */
   GRPC_FD_UNREF(fd, "basicpoll_add");
@@ -1161,7 +1140,7 @@ static void basic_pollset_add_fd(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
 
 exit:
   if (and_unlock_pollset) {
-    gpr_mu_unlock(pollset->mu);
+    gpr_mu_unlock(&pollset->mu);
   }
 }
 
@@ -1197,14 +1176,14 @@ static void basic_pollset_maybe_work_and_unlock(grpc_exec_ctx *exec_ctx,
     pfd[2].fd = fd->fd;
     pfd[2].revents = 0;
     GRPC_FD_REF(fd, "basicpoll_begin");
-    gpr_mu_unlock(pollset->mu);
+    gpr_mu_unlock(&pollset->mu);
     pfd[2].events =
         (short)fd_begin_poll(fd, pollset, worker, POLLIN, POLLOUT, &fd_watcher);
     if (pfd[2].events != 0) {
       nfds++;
     }
   } else {
-    gpr_mu_unlock(pollset->mu);
+    gpr_mu_unlock(&pollset->mu);
   }
 
   /* TODO(vpai): Consider first doing a 0 timeout poll here to avoid
@@ -1302,7 +1281,7 @@ static void multipoll_with_poll_pollset_add_fd(grpc_exec_ctx *exec_ctx,
   GRPC_FD_REF(fd, "multipoller");
 exit:
   if (and_unlock_pollset) {
-    gpr_mu_unlock(pollset->mu);
+    gpr_mu_unlock(&pollset->mu);
   }
 }
 
@@ -1354,7 +1333,7 @@ static void multipoll_with_poll_pollset_maybe_work_and_unlock(
   }
   h->del_count = 0;
   h->fd_count = fd_count;
-  gpr_mu_unlock(pollset->mu);
+  gpr_mu_unlock(&pollset->mu);
 
   for (i = 2; i < pfd_count; i++) {
     pfds[i].events = (short)fd_begin_poll(watchers[i].fd, pollset, worker,
@@ -1467,6 +1446,22 @@ static void poll_become_multipoller(grpc_exec_ctx *exec_ctx,
 #include "src/core/profiling/timers.h"
 #include "src/core/support/block_annotate.h"
 
+static void set_ready(grpc_exec_ctx *exec_ctx, grpc_fd *fd, grpc_closure **st) {
+  /* only one set_ready can be active at once (but there may be a racing
+     notify_on) */
+  gpr_mu_lock(&fd->mu);
+  set_ready_locked(exec_ctx, fd, st);
+  gpr_mu_unlock(&fd->mu);
+}
+
+static void fd_become_readable(grpc_exec_ctx *exec_ctx, grpc_fd *fd) {
+  set_ready(exec_ctx, fd, &fd->read_closure);
+}
+
+static void fd_become_writable(grpc_exec_ctx *exec_ctx, grpc_fd *fd) {
+  set_ready(exec_ctx, fd, &fd->write_closure);
+}
+
 struct epoll_fd_list {
   int *epoll_fds;
   size_t count;
@@ -1567,7 +1562,7 @@ static void perform_delayed_add(grpc_exec_ctx *exec_ctx, void *arg,
     finally_add_fd(exec_ctx, da->pollset, da->fd);
   }
 
-  gpr_mu_lock(da->pollset->mu);
+  gpr_mu_lock(&da->pollset->mu);
   da->pollset->in_flight_cbs--;
   if (da->pollset->shutting_down) {
     /* We don't care about this pollset anymore. */
@@ -1576,7 +1571,7 @@ static void perform_delayed_add(grpc_exec_ctx *exec_ctx, void *arg,
       grpc_exec_ctx_enqueue(exec_ctx, da->pollset->shutdown_done, true, NULL);
     }
   }
-  gpr_mu_unlock(da->pollset->mu);
+  gpr_mu_unlock(&da->pollset->mu);
 
   GRPC_FD_UNREF(da->fd, "delayed_add");
 
@@ -1588,7 +1583,7 @@ static void multipoll_with_epoll_pollset_add_fd(grpc_exec_ctx *exec_ctx,
                                                 grpc_fd *fd,
                                                 int and_unlock_pollset) {
   if (and_unlock_pollset) {
-    gpr_mu_unlock(pollset->mu);
+    gpr_mu_unlock(&pollset->mu);
     finally_add_fd(exec_ctx, pollset, fd);
   } else {
     delayed_add *da = gpr_malloc(sizeof(*da));
@@ -1620,7 +1615,7 @@ static void multipoll_with_epoll_pollset_maybe_work_and_unlock(
    * here.
    */
 
-  gpr_mu_unlock(pollset->mu);
+  gpr_mu_unlock(&pollset->mu);
 
   timeout_ms = poll_deadline_to_millis_timeout(deadline, now);
 
diff --git a/src/core/iomgr/ev_poll_posix.c b/src/core/iomgr/ev_poll_posix.c
index e2b0b08ac34b37d97d7d461ff2dbe2c997c9e099..989461f2ae68ef401a98a81990416c2b6317af86 100644
--- a/src/core/iomgr/ev_poll_posix.c
+++ b/src/core/iomgr/ev_poll_posix.c
@@ -31,17 +31,6 @@
  *
  */
 
-/* This file will be removed shortly: it's here to keep refactoring
- * steps simple and auditable.
- * It's the combination of the old files:
- *  - fd_posix.{h,c}
- *  - pollset_posix.{h,c}
- *  - pullset_multipoller_with_{poll,epoll}.{h,c}
- * The new version will be split into:
- *  - ev_poll_posix.{h,c}
- *  - ev_epoll_posix.{h,c}
- */
-
 #include <grpc/support/port_platform.h>
 
 #ifdef GPR_POSIX_SOCKET
@@ -186,7 +175,7 @@ struct grpc_pollset_worker {
 };
 
 struct grpc_pollset {
-  gpr_mu *mu;
+  gpr_mu mu;
   grpc_pollset_worker root_worker;
   int in_flight_cbs;
   int shutting_down;
@@ -337,11 +326,11 @@ static bool fd_is_orphaned(grpc_fd *fd) {
 }
 
 static void pollset_kick_locked(grpc_fd_watcher *watcher) {
-  gpr_mu_lock(watcher->pollset->mu);
+  gpr_mu_lock(&watcher->pollset->mu);
   GPR_ASSERT(watcher->worker);
   pollset_kick_ext(watcher->pollset, watcher->worker,
                    GRPC_POLLSET_REEVALUATE_POLLING_ON_WAKEUP);
-  gpr_mu_unlock(watcher->pollset->mu);
+  gpr_mu_unlock(&watcher->pollset->mu);
 }
 
 static void maybe_wake_one_watcher_locked(grpc_fd *fd) {
@@ -718,8 +707,9 @@ static void kick_poller(void) { grpc_wakeup_fd_wakeup(&grpc_global_wakeup_fd); }
 
 /* main interface */
 
-static void pollset_init(grpc_pollset *pollset, gpr_mu *mu) {
-  pollset->mu = mu;
+static void pollset_init(grpc_pollset *pollset, gpr_mu **mu) {
+  gpr_mu_init(&pollset->mu);
+  *mu = &pollset->mu;
   pollset->root_worker.next = pollset->root_worker.prev = &pollset->root_worker;
   pollset->in_flight_cbs = 0;
   pollset->shutting_down = 0;
@@ -746,6 +736,7 @@ static void pollset_destroy(grpc_pollset *pollset) {
   }
   gpr_free(pollset->fds);
   gpr_free(pollset->dels);
+  gpr_mu_destroy(&pollset->mu);
 }
 
 static void pollset_reset(grpc_pollset *pollset) {
@@ -762,7 +753,7 @@ static void pollset_reset(grpc_pollset *pollset) {
 
 static void pollset_add_fd(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
                            grpc_fd *fd) {
-  gpr_mu_lock(pollset->mu);
+  gpr_mu_lock(&pollset->mu);
   size_t i;
   /* TODO(ctiller): this is O(num_fds^2); maybe switch to a hash set here */
   for (i = 0; i < pollset->fd_count; i++) {
@@ -777,7 +768,7 @@ static void pollset_add_fd(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
   pollset->fds[pollset->fd_count++] = fd;
   GRPC_FD_REF(fd, "multipoller");
 exit:
-  gpr_mu_unlock(pollset->mu);
+  gpr_mu_unlock(&pollset->mu);
 }
 
 static void finish_shutdown(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset) {
@@ -833,7 +824,7 @@ static void pollset_work(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
   /* Give do_promote priority so we don't starve it out */
   if (pollset->in_flight_cbs) {
     GPR_TIMER_MARK("pollset_work.in_flight_cbs", 0);
-    gpr_mu_unlock(pollset->mu);
+    gpr_mu_unlock(&pollset->mu);
     locked = 0;
     goto done;
   }
@@ -895,7 +886,7 @@ static void pollset_work(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
       }
       pollset->del_count = 0;
       pollset->fd_count = fd_count;
-      gpr_mu_unlock(pollset->mu);
+      gpr_mu_unlock(&pollset->mu);
 
       for (i = 2; i < pfd_count; i++) {
         pfds[i].events = (short)fd_begin_poll(watchers[i].fd, pollset, &worker,
@@ -952,7 +943,7 @@ static void pollset_work(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
   done:
     if (!locked) {
       queued_work |= grpc_exec_ctx_flush(exec_ctx);
-      gpr_mu_lock(pollset->mu);
+      gpr_mu_lock(&pollset->mu);
       locked = 1;
     }
     /* If we're forced to re-evaluate polling (via pollset_kick with
@@ -982,19 +973,19 @@ static void pollset_work(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
       pollset_kick(pollset, NULL);
     } else if (!pollset->called_shutdown && pollset->in_flight_cbs == 0) {
       pollset->called_shutdown = 1;
-      gpr_mu_unlock(pollset->mu);
+      gpr_mu_unlock(&pollset->mu);
       finish_shutdown(exec_ctx, pollset);
       grpc_exec_ctx_flush(exec_ctx);
       /* Continuing to access pollset here is safe -- it is the caller's
        * responsibility to not destroy when it has outstanding calls to
        * pollset_work.
        * TODO(dklempner): Can we refactor the shutdown logic to avoid this? */
-      gpr_mu_lock(pollset->mu);
+      gpr_mu_lock(&pollset->mu);
     } else if (!grpc_closure_list_empty(pollset->idle_jobs)) {
       grpc_exec_ctx_enqueue_list(exec_ctx, &pollset->idle_jobs, NULL);
-      gpr_mu_unlock(pollset->mu);
+      gpr_mu_unlock(&pollset->mu);
       grpc_exec_ctx_flush(exec_ctx);
-      gpr_mu_lock(pollset->mu);
+      gpr_mu_lock(&pollset->mu);
     }
   }
   *worker_hdl = NULL;
diff --git a/src/core/iomgr/ev_posix.c b/src/core/iomgr/ev_posix.c
index d7681769c3daed0bdeea224ba391200da63eb60b..fbfa13c3479be72b420ce3247285072a7346c01c 100644
--- a/src/core/iomgr/ev_posix.c
+++ b/src/core/iomgr/ev_posix.c
@@ -163,7 +163,7 @@ void grpc_fd_notify_on_write(grpc_exec_ctx *exec_ctx, grpc_fd *fd,
 
 size_t grpc_pollset_size(void) { return g_event_engine->pollset_size; }
 
-void grpc_pollset_init(grpc_pollset *pollset, gpr_mu *mu) {
+void grpc_pollset_init(grpc_pollset *pollset, gpr_mu **mu) {
   g_event_engine->pollset_init(pollset, mu);
 }
 
diff --git a/src/core/iomgr/ev_posix.h b/src/core/iomgr/ev_posix.h
index 9d1f64652dc1f4908ced86c58429c77475ed3cc4..ad881a188c12b5c0e7c2a27d76bf37c4f17dbb62 100644
--- a/src/core/iomgr/ev_posix.h
+++ b/src/core/iomgr/ev_posix.h
@@ -56,7 +56,7 @@ typedef struct grpc_event_engine_vtable {
   void (*fd_notify_on_write)(grpc_exec_ctx *exec_ctx, grpc_fd *fd,
                              grpc_closure *closure);
 
-  void (*pollset_init)(grpc_pollset *pollset, gpr_mu *mu);
+  void (*pollset_init)(grpc_pollset *pollset, gpr_mu **mu);
   void (*pollset_shutdown)(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
                            grpc_closure *closure);
   void (*pollset_reset)(grpc_pollset *pollset);
diff --git a/src/core/iomgr/iomgr_internal.h b/src/core/iomgr/iomgr_internal.h
index 5623223913380e28e6fdcee56906f21870eb92bf..ccf0dee3a4fc40fe46852f9a6c2cfdef8293763a 100644
--- a/src/core/iomgr/iomgr_internal.h
+++ b/src/core/iomgr/iomgr_internal.h
@@ -1,6 +1,6 @@
 /*
  *
- * Copyright 2015, Google Inc.
+ * Copyright 2015-2016, Google Inc.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
diff --git a/src/core/iomgr/iomgr_posix.c b/src/core/iomgr/iomgr_posix.c
index 6e8e09a8514bf5df4269571c03e21844b69eb726..baf3bd5db8fc57398baca93c730120e90dc1176a 100644
--- a/src/core/iomgr/iomgr_posix.c
+++ b/src/core/iomgr/iomgr_posix.c
@@ -1,6 +1,6 @@
 /*
  *
- * Copyright 2015, Google Inc.
+ * Copyright 2015-2016, Google Inc.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
diff --git a/src/core/iomgr/pollset.h b/src/core/iomgr/pollset.h
index 39e4ff2440837f7b2878c6d0407f7ef74f7df945..92a0374ddd4067d1844300e960100aa40d72462d 100644
--- a/src/core/iomgr/pollset.h
+++ b/src/core/iomgr/pollset.h
@@ -53,7 +53,7 @@ typedef struct grpc_pollset grpc_pollset;
 typedef struct grpc_pollset_worker grpc_pollset_worker;
 
 size_t grpc_pollset_size(void);
-void grpc_pollset_init(grpc_pollset *pollset, gpr_mu *mu);
+void grpc_pollset_init(grpc_pollset *pollset, gpr_mu **mu);
 /* Begin shutting down the pollset, and call closure when done.
  * GRPC_POLLSET_MU(pollset) must be held */
 void grpc_pollset_shutdown(grpc_exec_ctx *exec_ctx, grpc_pollset *pollset,
diff --git a/src/core/iomgr/pollset_set.h b/src/core/iomgr/pollset_set.h
index 9591bf0d32c705a86172e110b7505e0ca99eb725..dddcd8313f220a63ba0c934b69f2fd53b1026e33 100644
--- a/src/core/iomgr/pollset_set.h
+++ b/src/core/iomgr/pollset_set.h
@@ -1,6 +1,6 @@
 /*
  *
- * Copyright 2015, Google Inc.
+ * Copyright 2015-2016, Google Inc.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
diff --git a/src/core/iomgr/pollset_set_windows.c b/src/core/iomgr/pollset_set_windows.c
index 9cf8fd4472f49674f9a59f044ec794ac05db3461..3b8eca28e61f75e09fb26ab73d37b04e083beb7f 100644
--- a/src/core/iomgr/pollset_set_windows.c
+++ b/src/core/iomgr/pollset_set_windows.c
@@ -1,6 +1,6 @@
 /*
  *
- * Copyright 2015, Google Inc.
+ * Copyright 2015-2016, Google Inc.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
diff --git a/src/core/iomgr/pollset_set_windows.h b/src/core/iomgr/pollset_set_windows.h
index aa5abe91338425d79857392d7ec5720480157fbe..9661cd2c3987223efbbe44f0f5a0ff2abc4425c9 100644
--- a/src/core/iomgr/pollset_set_windows.h
+++ b/src/core/iomgr/pollset_set_windows.h
@@ -1,6 +1,6 @@
 /*
  *
- * Copyright 2015, Google Inc.
+ * Copyright 2015-2016, Google Inc.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
diff --git a/src/core/iomgr/pollset_windows.c b/src/core/iomgr/pollset_windows.c
index bbce23b46a76d6c1dc2bf21bc84a39b22d9da1e6..c7f30f435fab7ed5bb42b893f885a018b87bf09d 100644
--- a/src/core/iomgr/pollset_windows.c
+++ b/src/core/iomgr/pollset_windows.c
@@ -89,12 +89,15 @@ static void push_front_worker(grpc_pollset_worker *root,
       worker->links[type].next->links[type].prev = worker;
 }
 
+size_t grpc_pollset_size(void) { return sizeof(grpc_pollset); }
+
 /* There isn't really any such thing as a pollset under Windows, due to the
    nature of the IO completion ports. We're still going to provide a minimal
    set of features for the sake of the rest of grpc. But grpc_pollset_work
    won't actually do any polling, and return as quickly as possible. */
 
-void grpc_pollset_init(grpc_pollset *pollset) {
+void grpc_pollset_init(grpc_pollset *pollset, gpr_mu **mu) {
+  *mu = &grpc_polling_mu;
   memset(pollset, 0, sizeof(*pollset));
   pollset->root_worker.links[GRPC_POLLSET_WORKER_LINK_POLLSET].next =
       pollset->root_worker.links[GRPC_POLLSET_WORKER_LINK_POLLSET].prev =
diff --git a/src/core/iomgr/pollset_windows.h b/src/core/iomgr/pollset_windows.h
index c2f13fdfa8bfc901655310729d3919c67f5e7518..dc0b7a4104bd8ada3c4d0301044465d1e3e204fc 100644
--- a/src/core/iomgr/pollset_windows.h
+++ b/src/core/iomgr/pollset_windows.h
@@ -72,6 +72,4 @@ struct grpc_pollset {
   grpc_closure *on_shutdown;
 };
 
-extern gpr_mu grpc_polling_mu;
-
 #endif /* GRPC_INTERNAL_CORE_IOMGR_POLLSET_WINDOWS_H */
diff --git a/src/core/iomgr/udp_server.c b/src/core/iomgr/udp_server.c
index ab38611056d090a38a518b94bf70ca4a3950adbf..cb3923123ff06389742d7564872e7c7abd1b265e 100644
--- a/src/core/iomgr/udp_server.c
+++ b/src/core/iomgr/udp_server.c
@@ -56,7 +56,6 @@
 #include <unistd.h>
 
 #include "src/core/iomgr/ev_posix.h"
-#include "src/core/iomgr/pollset_posix.h"
 #include "src/core/iomgr/resolve_address.h"
 #include "src/core/iomgr/sockaddr_utils.h"
 #include "src/core/iomgr/socket_utils_posix.h"
diff --git a/src/core/security/client_auth_filter.c b/src/core/security/client_auth_filter.c
index 57b367d00fffee7121de1207ce922155c3021e33..332d4259d2843fee3f8cf013339beb83f1859c6f 100644
--- a/src/core/security/client_auth_filter.c
+++ b/src/core/security/client_auth_filter.c
@@ -310,7 +310,6 @@ static void init_channel_elem(grpc_exec_ctx *exec_ctx,
   GPR_ASSERT(auth_context != NULL);
 
   /* initialize members */
-  GPR_ASSERT(sc->is_client_side);
   chand->security_connector =
       (grpc_channel_security_connector *)GRPC_SECURITY_CONNECTOR_REF(
           sc, "client_auth_filter");
diff --git a/src/core/security/credentials.c b/src/core/security/credentials.c
index c58574bd6d86ba3f416124be6f38ac5f2a75fecc..b4fa616fa7ebe955ebd180f4f16e028bf9c44035 100644
--- a/src/core/security/credentials.c
+++ b/src/core/security/credentials.c
@@ -166,7 +166,7 @@ void grpc_server_credentials_release(grpc_server_credentials *creds) {
 }
 
 grpc_security_status grpc_server_credentials_create_security_connector(
-    grpc_server_credentials *creds, grpc_security_connector **sc) {
+    grpc_server_credentials *creds, grpc_server_security_connector **sc) {
   if (creds == NULL || creds->vtable->create_security_connector == NULL) {
     gpr_log(GPR_ERROR, "Server credentials cannot create security context.");
     return GRPC_SECURITY_ERROR;
@@ -298,7 +298,7 @@ static grpc_security_status ssl_create_security_connector(
 }
 
 static grpc_security_status ssl_server_create_security_connector(
-    grpc_server_credentials *creds, grpc_security_connector **sc) {
+    grpc_server_credentials *creds, grpc_server_security_connector **sc) {
   grpc_ssl_server_credentials *c = (grpc_ssl_server_credentials *)creds;
   return grpc_ssl_server_security_connector_create(&c->config, sc);
 }
@@ -894,7 +894,7 @@ static grpc_security_status fake_transport_security_create_security_connector(
 
 static grpc_security_status
 fake_transport_security_server_create_security_connector(
-    grpc_server_credentials *c, grpc_security_connector **sc) {
+    grpc_server_credentials *c, grpc_server_security_connector **sc) {
   *sc = grpc_fake_server_security_connector_create();
   return GRPC_SECURITY_OK;
 }
diff --git a/src/core/security/credentials.h b/src/core/security/credentials.h
index 3cd652cd574db505e471c7f229e1430e28715bbc..0de4cd94689b2fb69c377c6febe13838fbb09705 100644
--- a/src/core/security/credentials.h
+++ b/src/core/security/credentials.h
@@ -1,6 +1,6 @@
 /*
  *
- * Copyright 2015, Google Inc.
+ * Copyright 2015-2016, Google Inc.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -234,7 +234,7 @@ grpc_refresh_token_credentials_create_from_auth_refresh_token(
 typedef struct {
   void (*destruct)(grpc_server_credentials *c);
   grpc_security_status (*create_security_connector)(
-      grpc_server_credentials *c, grpc_security_connector **sc);
+      grpc_server_credentials *c, grpc_server_security_connector **sc);
 } grpc_server_credentials_vtable;
 
 struct grpc_server_credentials {
@@ -245,7 +245,7 @@ struct grpc_server_credentials {
 };
 
 grpc_security_status grpc_server_credentials_create_security_connector(
-    grpc_server_credentials *creds, grpc_security_connector **sc);
+    grpc_server_credentials *creds, grpc_server_security_connector **sc);
 
 grpc_server_credentials *grpc_server_credentials_ref(
     grpc_server_credentials *creds);
diff --git a/src/core/security/google_default_credentials.c b/src/core/security/google_default_credentials.c
index 3b3e38882a6734c77279c616e3aa7adad4b4c061..1f4f3e4aa52ef8dc3758db6dac08097859ad5560 100644
--- a/src/core/security/google_default_credentials.c
+++ b/src/core/security/google_default_credentials.c
@@ -52,10 +52,11 @@
 
 static grpc_channel_credentials *default_credentials = NULL;
 static int compute_engine_detection_done = 0;
-static gpr_mu g_mu;
+static gpr_mu g_state_mu;
+static gpr_mu *g_polling_mu;
 static gpr_once g_once = GPR_ONCE_INIT;
 
-static void init_default_credentials(void) { gpr_mu_init(&g_mu); }
+static void init_default_credentials(void) { gpr_mu_init(&g_state_mu); }
 
 typedef struct {
   grpc_pollset *pollset;
@@ -80,10 +81,10 @@ static void on_compute_engine_detection_http_response(
       }
     }
   }
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_polling_mu);
   detector->is_done = 1;
   grpc_pollset_kick(detector->pollset, NULL);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_polling_mu);
 }
 
 static void destroy_pollset(grpc_exec_ctx *exec_ctx, void *p, bool s) {
@@ -102,7 +103,7 @@ static int is_stack_running_on_compute_engine(void) {
   gpr_timespec max_detection_delay = gpr_time_from_seconds(1, GPR_TIMESPAN);
 
   detector.pollset = gpr_malloc(grpc_pollset_size());
-  grpc_pollset_init(detector.pollset, &g_mu);
+  grpc_pollset_init(detector.pollset, &g_polling_mu);
   detector.is_done = 0;
   detector.success = 0;
 
@@ -121,19 +122,20 @@ static int is_stack_running_on_compute_engine(void) {
 
   /* 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(&g_mu);
+  gpr_mu_lock(g_polling_mu);
   while (!detector.is_done) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, detector.pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       gpr_inf_future(GPR_CLOCK_MONOTONIC));
   }
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_polling_mu);
 
   grpc_httpcli_context_destroy(&context);
-  grpc_closure_init(&destroy_closure, destroy_pollset, &detector.pollset);
+  grpc_closure_init(&destroy_closure, destroy_pollset, detector.pollset);
   grpc_pollset_shutdown(&exec_ctx, detector.pollset, &destroy_closure);
   grpc_exec_ctx_finish(&exec_ctx);
+  g_polling_mu = NULL;
 
   gpr_free(detector.pollset);
 
@@ -187,7 +189,7 @@ grpc_channel_credentials *grpc_google_default_credentials_create(void) {
 
   gpr_once_init(&g_once, init_default_credentials);
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(&g_state_mu);
 
   if (default_credentials != NULL) {
     result = grpc_channel_credentials_ref(default_credentials);
@@ -233,19 +235,19 @@ end:
       gpr_log(GPR_ERROR, "Could not create google default credentials.");
     }
   }
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(&g_state_mu);
   return result;
 }
 
 void grpc_flush_cached_google_default_credentials(void) {
   gpr_once_init(&g_once, init_default_credentials);
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(&g_state_mu);
   if (default_credentials != NULL) {
     grpc_channel_credentials_unref(default_credentials);
     default_credentials = NULL;
   }
   compute_engine_detection_done = 0;
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(&g_state_mu);
 }
 
 /* -- Well known credentials path. -- */
diff --git a/src/core/security/handshake.c b/src/core/security/handshake.c
index a8b2fef6297035c3a998c7bebb4850cebbce84d3..b5bb6667a71f075a7ec5c37a08c9d056c4f0ccf1 100644
--- a/src/core/security/handshake.c
+++ b/src/core/security/handshake.c
@@ -33,6 +33,7 @@
 
 #include "src/core/security/handshake.h"
 
+#include <stdbool.h>
 #include <string.h>
 
 #include "src/core/security/security_context.h"
@@ -46,6 +47,7 @@
 typedef struct {
   grpc_security_connector *connector;
   tsi_handshaker *handshaker;
+  bool is_client_side;
   unsigned char *handshake_buffer;
   size_t handshake_buffer_size;
   grpc_endpoint *wrapped_endpoint;
@@ -67,9 +69,11 @@ static void on_handshake_data_sent_to_peer(grpc_exec_ctx *exec_ctx, void *setup,
                                            bool success);
 
 static void security_connector_remove_handshake(grpc_security_handshake *h) {
+  GPR_ASSERT(!h->is_client_side);
   grpc_security_connector_handshake_list *node;
   grpc_security_connector_handshake_list *tmp;
-  grpc_security_connector *sc = h->connector;
+  grpc_server_security_connector *sc =
+      (grpc_server_security_connector *)h->connector;
   gpr_mu_lock(&sc->mu);
   node = sc->handshaking_handshakes;
   if (node && node->handshake == h) {
@@ -94,7 +98,7 @@ static void security_connector_remove_handshake(grpc_security_handshake *h) {
 static void security_handshake_done(grpc_exec_ctx *exec_ctx,
                                     grpc_security_handshake *h,
                                     int is_success) {
-  if (!h->connector->is_client_side) {
+  if (!h->is_client_side) {
     security_connector_remove_handshake(h);
   }
   if (is_success) {
@@ -290,6 +294,7 @@ static void on_handshake_data_sent_to_peer(grpc_exec_ctx *exec_ctx,
 void grpc_do_security_handshake(grpc_exec_ctx *exec_ctx,
                                 tsi_handshaker *handshaker,
                                 grpc_security_connector *connector,
+                                bool is_client_side,
                                 grpc_endpoint *nonsecure_endpoint,
                                 grpc_security_handshake_done_cb cb,
                                 void *user_data) {
@@ -298,6 +303,7 @@ void grpc_do_security_handshake(grpc_exec_ctx *exec_ctx,
   memset(h, 0, sizeof(grpc_security_handshake));
   h->handshaker = handshaker;
   h->connector = GRPC_SECURITY_CONNECTOR_REF(connector, "handshake");
+  h->is_client_side = is_client_side;
   h->handshake_buffer_size = GRPC_INITIAL_HANDSHAKE_BUFFER_SIZE;
   h->handshake_buffer = gpr_malloc(h->handshake_buffer_size);
   h->wrapped_endpoint = nonsecure_endpoint;
@@ -310,13 +316,15 @@ void grpc_do_security_handshake(grpc_exec_ctx *exec_ctx,
   gpr_slice_buffer_init(&h->left_overs);
   gpr_slice_buffer_init(&h->outgoing);
   gpr_slice_buffer_init(&h->incoming);
-  if (!connector->is_client_side) {
+  if (!is_client_side) {
+    grpc_server_security_connector *server_connector =
+        (grpc_server_security_connector *)connector;
     handshake_node = gpr_malloc(sizeof(grpc_security_connector_handshake_list));
     handshake_node->handshake = h;
-    gpr_mu_lock(&connector->mu);
-    handshake_node->next = connector->handshaking_handshakes;
-    connector->handshaking_handshakes = handshake_node;
-    gpr_mu_unlock(&connector->mu);
+    gpr_mu_lock(&server_connector->mu);
+    handshake_node->next = server_connector->handshaking_handshakes;
+    server_connector->handshaking_handshakes = handshake_node;
+    gpr_mu_unlock(&server_connector->mu);
   }
   send_handshake_bytes_to_peer(exec_ctx, h);
 }
diff --git a/src/core/security/handshake.h b/src/core/security/handshake.h
index 44215d16ef0e005ea881f587b7b5569d92d081d7..db8b3749215b95a1a79b0775d1a6e15d8e2eb64f 100644
--- a/src/core/security/handshake.h
+++ b/src/core/security/handshake.h
@@ -1,6 +1,6 @@
 /*
  *
- * Copyright 2015, Google Inc.
+ * Copyright 2015-2016, Google Inc.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -41,6 +41,7 @@
 void grpc_do_security_handshake(grpc_exec_ctx *exec_ctx,
                                 tsi_handshaker *handshaker,
                                 grpc_security_connector *connector,
+                                bool is_client_side,
                                 grpc_endpoint *nonsecure_endpoint,
                                 grpc_security_handshake_done_cb cb,
                                 void *user_data);
diff --git a/src/core/security/security_connector.c b/src/core/security/security_connector.c
index 51a99b4492d6c5b1d3418d13056c62332fc0774b..33c62a20c2094fba3c0446d9233f8818f311c088 100644
--- a/src/core/security/security_connector.c
+++ b/src/core/security/security_connector.c
@@ -33,6 +33,7 @@
 
 #include "src/core/security/security_connector.h"
 
+#include <stdbool.h>
 #include <string.h>
 
 #include <grpc/support/alloc.h>
@@ -110,31 +111,39 @@ const tsi_peer_property *tsi_peer_get_property_by_name(const tsi_peer *peer,
   return NULL;
 }
 
-void grpc_security_connector_shutdown(grpc_exec_ctx *exec_ctx,
-                                      grpc_security_connector *connector) {
+void grpc_server_security_connector_shutdown(
+    grpc_exec_ctx *exec_ctx, grpc_server_security_connector *connector) {
   grpc_security_connector_handshake_list *tmp;
-  if (!connector->is_client_side) {
-    gpr_mu_lock(&connector->mu);
-    while (connector->handshaking_handshakes) {
-      tmp = connector->handshaking_handshakes;
-      grpc_security_handshake_shutdown(
-          exec_ctx, connector->handshaking_handshakes->handshake);
-      connector->handshaking_handshakes = tmp->next;
-      gpr_free(tmp);
-    }
-    gpr_mu_unlock(&connector->mu);
+  gpr_mu_lock(&connector->mu);
+  while (connector->handshaking_handshakes) {
+    tmp = connector->handshaking_handshakes;
+    grpc_security_handshake_shutdown(
+        exec_ctx, connector->handshaking_handshakes->handshake);
+    connector->handshaking_handshakes = tmp->next;
+    gpr_free(tmp);
+  }
+  gpr_mu_unlock(&connector->mu);
+}
+
+void grpc_channel_security_connector_do_handshake(
+    grpc_exec_ctx *exec_ctx, grpc_channel_security_connector *sc,
+    grpc_endpoint *nonsecure_endpoint, grpc_security_handshake_done_cb cb,
+    void *user_data) {
+  if (sc == NULL || nonsecure_endpoint == NULL) {
+    cb(exec_ctx, user_data, GRPC_SECURITY_ERROR, NULL, NULL);
+  } else {
+    sc->do_handshake(exec_ctx, sc, nonsecure_endpoint, cb, user_data);
   }
 }
 
-void grpc_security_connector_do_handshake(grpc_exec_ctx *exec_ctx,
-                                          grpc_security_connector *sc,
-                                          grpc_endpoint *nonsecure_endpoint,
-                                          grpc_security_handshake_done_cb cb,
-                                          void *user_data) {
+void grpc_server_security_connector_do_handshake(
+    grpc_exec_ctx *exec_ctx, grpc_server_security_connector *sc,
+    grpc_tcp_server_acceptor *acceptor, grpc_endpoint *nonsecure_endpoint,
+    grpc_security_handshake_done_cb cb, void *user_data) {
   if (sc == NULL || nonsecure_endpoint == NULL) {
     cb(exec_ctx, user_data, GRPC_SECURITY_ERROR, NULL, NULL);
   } else {
-    sc->vtable->do_handshake(exec_ctx, sc, nonsecure_endpoint, cb, user_data);
+    sc->do_handshake(exec_ctx, sc, acceptor, nonsecure_endpoint, cb, user_data);
   }
 }
 
@@ -248,7 +257,8 @@ static void fake_channel_destroy(grpc_security_connector *sc) {
 }
 
 static void fake_server_destroy(grpc_security_connector *sc) {
-  gpr_mu_destroy(&sc->mu);
+  grpc_server_security_connector *c = (grpc_server_security_connector *)sc;
+  gpr_mu_destroy(&c->mu);
   gpr_free(sc);
 }
 
@@ -298,49 +308,52 @@ static void fake_channel_check_call_host(grpc_exec_ctx *exec_ctx,
 }
 
 static void fake_channel_do_handshake(grpc_exec_ctx *exec_ctx,
-                                      grpc_security_connector *sc,
+                                      grpc_channel_security_connector *sc,
                                       grpc_endpoint *nonsecure_endpoint,
                                       grpc_security_handshake_done_cb cb,
                                       void *user_data) {
-  grpc_do_security_handshake(exec_ctx, tsi_create_fake_handshaker(1), sc,
-                             nonsecure_endpoint, cb, user_data);
+  grpc_do_security_handshake(exec_ctx, tsi_create_fake_handshaker(1), &sc->base,
+                             true, nonsecure_endpoint, cb, user_data);
 }
 
 static void fake_server_do_handshake(grpc_exec_ctx *exec_ctx,
-                                     grpc_security_connector *sc,
+                                     grpc_server_security_connector *sc,
+                                     grpc_tcp_server_acceptor *acceptor,
                                      grpc_endpoint *nonsecure_endpoint,
                                      grpc_security_handshake_done_cb cb,
                                      void *user_data) {
-  grpc_do_security_handshake(exec_ctx, tsi_create_fake_handshaker(0), sc,
-                             nonsecure_endpoint, cb, user_data);
+  grpc_do_security_handshake(exec_ctx, tsi_create_fake_handshaker(0), &sc->base,
+                             false, nonsecure_endpoint, cb, user_data);
 }
 
 static grpc_security_connector_vtable fake_channel_vtable = {
-    fake_channel_destroy, fake_channel_do_handshake, fake_check_peer};
+    fake_channel_destroy, fake_check_peer};
 
-static grpc_security_connector_vtable fake_server_vtable = {
-    fake_server_destroy, fake_server_do_handshake, fake_check_peer};
+static grpc_security_connector_vtable fake_server_vtable = {fake_server_destroy,
+                                                            fake_check_peer};
 
 grpc_channel_security_connector *grpc_fake_channel_security_connector_create(
     grpc_call_credentials *request_metadata_creds) {
   grpc_channel_security_connector *c = gpr_malloc(sizeof(*c));
   memset(c, 0, sizeof(*c));
   gpr_ref_init(&c->base.refcount, 1);
-  c->base.is_client_side = 1;
   c->base.url_scheme = GRPC_FAKE_SECURITY_URL_SCHEME;
   c->base.vtable = &fake_channel_vtable;
   c->request_metadata_creds = grpc_call_credentials_ref(request_metadata_creds);
   c->check_call_host = fake_channel_check_call_host;
+  c->do_handshake = fake_channel_do_handshake;
   return c;
 }
 
-grpc_security_connector *grpc_fake_server_security_connector_create(void) {
-  grpc_security_connector *c = gpr_malloc(sizeof(grpc_security_connector));
-  memset(c, 0, sizeof(grpc_security_connector));
-  gpr_ref_init(&c->refcount, 1);
-  c->is_client_side = 0;
-  c->vtable = &fake_server_vtable;
-  c->url_scheme = GRPC_FAKE_SECURITY_URL_SCHEME;
+grpc_server_security_connector *grpc_fake_server_security_connector_create(
+    void) {
+  grpc_server_security_connector *c =
+      gpr_malloc(sizeof(grpc_server_security_connector));
+  memset(c, 0, sizeof(*c));
+  gpr_ref_init(&c->base.refcount, 1);
+  c->base.vtable = &fake_server_vtable;
+  c->base.url_scheme = GRPC_FAKE_SECURITY_URL_SCHEME;
+  c->do_handshake = fake_server_do_handshake;
   gpr_mu_init(&c->mu);
   return c;
 }
@@ -355,7 +368,7 @@ typedef struct {
 } grpc_ssl_channel_security_connector;
 
 typedef struct {
-  grpc_security_connector base;
+  grpc_server_security_connector base;
   tsi_ssl_handshaker_factory *handshaker_factory;
 } grpc_ssl_server_security_connector;
 
@@ -378,12 +391,12 @@ static void ssl_server_destroy(grpc_security_connector *sc) {
   if (c->handshaker_factory != NULL) {
     tsi_ssl_handshaker_factory_destroy(c->handshaker_factory);
   }
-  gpr_mu_destroy(&sc->mu);
+  gpr_mu_destroy(&c->base.mu);
   gpr_free(sc);
 }
 
 static grpc_security_status ssl_create_handshaker(
-    tsi_ssl_handshaker_factory *handshaker_factory, int is_client,
+    tsi_ssl_handshaker_factory *handshaker_factory, bool is_client,
     const char *peer_name, tsi_handshaker **handshaker) {
   tsi_result result = TSI_OK;
   if (handshaker_factory == NULL) return GRPC_SECURITY_ERROR;
@@ -398,7 +411,7 @@ static grpc_security_status ssl_create_handshaker(
 }
 
 static void ssl_channel_do_handshake(grpc_exec_ctx *exec_ctx,
-                                     grpc_security_connector *sc,
+                                     grpc_channel_security_connector *sc,
                                      grpc_endpoint *nonsecure_endpoint,
                                      grpc_security_handshake_done_cb cb,
                                      void *user_data) {
@@ -406,20 +419,21 @@ static void ssl_channel_do_handshake(grpc_exec_ctx *exec_ctx,
       (grpc_ssl_channel_security_connector *)sc;
   tsi_handshaker *handshaker;
   grpc_security_status status = ssl_create_handshaker(
-      c->handshaker_factory, 1,
+      c->handshaker_factory, true,
       c->overridden_target_name != NULL ? c->overridden_target_name
                                         : c->target_name,
       &handshaker);
   if (status != GRPC_SECURITY_OK) {
     cb(exec_ctx, user_data, status, NULL, NULL);
   } else {
-    grpc_do_security_handshake(exec_ctx, handshaker, sc, nonsecure_endpoint, cb,
-                               user_data);
+    grpc_do_security_handshake(exec_ctx, handshaker, &sc->base, true,
+                               nonsecure_endpoint, cb, user_data);
   }
 }
 
 static void ssl_server_do_handshake(grpc_exec_ctx *exec_ctx,
-                                    grpc_security_connector *sc,
+                                    grpc_server_security_connector *sc,
+                                    grpc_tcp_server_acceptor *acceptor,
                                     grpc_endpoint *nonsecure_endpoint,
                                     grpc_security_handshake_done_cb cb,
                                     void *user_data) {
@@ -427,12 +441,12 @@ static void ssl_server_do_handshake(grpc_exec_ctx *exec_ctx,
       (grpc_ssl_server_security_connector *)sc;
   tsi_handshaker *handshaker;
   grpc_security_status status =
-      ssl_create_handshaker(c->handshaker_factory, 0, NULL, &handshaker);
+      ssl_create_handshaker(c->handshaker_factory, false, NULL, &handshaker);
   if (status != GRPC_SECURITY_OK) {
     cb(exec_ctx, user_data, status, NULL, NULL);
   } else {
-    grpc_do_security_handshake(exec_ctx, handshaker, sc, nonsecure_endpoint, cb,
-                               user_data);
+    grpc_do_security_handshake(exec_ctx, handshaker, &sc->base, false,
+                               nonsecure_endpoint, cb, user_data);
   }
 }
 
@@ -603,10 +617,10 @@ static void ssl_channel_check_call_host(grpc_exec_ctx *exec_ctx,
 }
 
 static grpc_security_connector_vtable ssl_channel_vtable = {
-    ssl_channel_destroy, ssl_channel_do_handshake, ssl_channel_check_peer};
+    ssl_channel_destroy, ssl_channel_check_peer};
 
 static grpc_security_connector_vtable ssl_server_vtable = {
-    ssl_server_destroy, ssl_server_do_handshake, ssl_server_check_peer};
+    ssl_server_destroy, ssl_server_check_peer};
 
 static gpr_slice compute_default_pem_root_certs_once(void) {
   gpr_slice result = gpr_empty_slice();
@@ -700,11 +714,11 @@ grpc_security_status grpc_ssl_channel_security_connector_create(
 
   gpr_ref_init(&c->base.base.refcount, 1);
   c->base.base.vtable = &ssl_channel_vtable;
-  c->base.base.is_client_side = 1;
   c->base.base.url_scheme = GRPC_SSL_URL_SCHEME;
   c->base.request_metadata_creds =
       grpc_call_credentials_ref(request_metadata_creds);
   c->base.check_call_host = ssl_channel_check_call_host;
+  c->base.do_handshake = ssl_channel_do_handshake;
   gpr_split_host_port(target_name, &c->target_name, &port);
   gpr_free(port);
   if (overridden_target_name != NULL) {
@@ -735,7 +749,7 @@ error:
 }
 
 grpc_security_status grpc_ssl_server_security_connector_create(
-    const grpc_ssl_server_config *config, grpc_security_connector **sc) {
+    const grpc_ssl_server_config *config, grpc_server_security_connector **sc) {
   size_t num_alpn_protocols = grpc_chttp2_num_alpn_versions();
   const unsigned char **alpn_protocol_strings =
       gpr_malloc(sizeof(const char *) * num_alpn_protocols);
@@ -759,9 +773,9 @@ grpc_security_status grpc_ssl_server_security_connector_create(
   c = gpr_malloc(sizeof(grpc_ssl_server_security_connector));
   memset(c, 0, sizeof(grpc_ssl_server_security_connector));
 
-  gpr_ref_init(&c->base.refcount, 1);
-  c->base.url_scheme = GRPC_SSL_URL_SCHEME;
-  c->base.vtable = &ssl_server_vtable;
+  gpr_ref_init(&c->base.base.refcount, 1);
+  c->base.base.url_scheme = GRPC_SSL_URL_SCHEME;
+  c->base.base.vtable = &ssl_server_vtable;
   result = tsi_create_ssl_server_handshaker_factory(
       (const unsigned char **)config->pem_private_keys,
       config->pem_private_keys_sizes,
@@ -774,11 +788,12 @@ grpc_security_status grpc_ssl_server_security_connector_create(
   if (result != TSI_OK) {
     gpr_log(GPR_ERROR, "Handshaker factory creation failed with %s.",
             tsi_result_to_string(result));
-    ssl_server_destroy(&c->base);
+    ssl_server_destroy(&c->base.base);
     *sc = NULL;
     goto error;
   }
   gpr_mu_init(&c->base.mu);
+  c->base.do_handshake = ssl_server_do_handshake;
   *sc = &c->base;
   gpr_free((void *)alpn_protocol_strings);
   gpr_free(alpn_protocol_string_lengths);
diff --git a/src/core/security/security_connector.h b/src/core/security/security_connector.h
index 39df7821f0c72c79aab3f11e75d96773e809aeb2..1e35d3f9b7ce8f5f98ab1ff8b59bb04650159914 100644
--- a/src/core/security/security_connector.h
+++ b/src/core/security/security_connector.h
@@ -36,6 +36,7 @@
 
 #include <grpc/grpc_security.h>
 #include "src/core/iomgr/endpoint.h"
+#include "src/core/iomgr/tcp_server.h"
 #include "src/core/tsi/transport_security_interface.h"
 
 /* --- status enum. --- */
@@ -68,9 +69,6 @@ typedef void (*grpc_security_handshake_done_cb)(
 
 typedef struct {
   void (*destroy)(grpc_security_connector *sc);
-  void (*do_handshake)(grpc_exec_ctx *exec_ctx, grpc_security_connector *sc,
-                       grpc_endpoint *nonsecure_endpoint,
-                       grpc_security_handshake_done_cb cb, void *user_data);
   void (*check_peer)(grpc_exec_ctx *exec_ctx, grpc_security_connector *sc,
                      tsi_peer peer, grpc_security_peer_check_cb cb,
                      void *user_data);
@@ -84,13 +82,7 @@ typedef struct grpc_security_connector_handshake_list {
 struct grpc_security_connector {
   const grpc_security_connector_vtable *vtable;
   gpr_refcount refcount;
-  int is_client_side;
   const char *url_scheme;
-  /* Used on server side only. */
-  /* TODO(yangg): Create a grpc_server_security_connector with these. */
-  gpr_mu mu;
-  grpc_security_connector_handshake_list *handshaking_handshakes;
-  const grpc_channel_args *channel_args;
 };
 
 /* Refcounting. */
@@ -113,13 +105,6 @@ grpc_security_connector *grpc_security_connector_ref(
 void grpc_security_connector_unref(grpc_security_connector *policy);
 #endif
 
-/* Handshake. */
-void grpc_security_connector_do_handshake(grpc_exec_ctx *exec_ctx,
-                                          grpc_security_connector *connector,
-                                          grpc_endpoint *nonsecure_endpoint,
-                                          grpc_security_handshake_done_cb cb,
-                                          void *user_data);
-
 /* Check the peer. Callee takes ownership of the peer object.
    The callback will include the resulting auth_context. */
 void grpc_security_connector_check_peer(grpc_exec_ctx *exec_ctx,
@@ -128,9 +113,6 @@ void grpc_security_connector_check_peer(grpc_exec_ctx *exec_ctx,
                                         grpc_security_peer_check_cb cb,
                                         void *user_data);
 
-void grpc_security_connector_shutdown(grpc_exec_ctx *exec_ctx,
-                                      grpc_security_connector *connector);
-
 /* Util to encapsulate the connector in a channel arg. */
 grpc_arg grpc_security_connector_to_arg(grpc_security_connector *sc);
 
@@ -153,12 +135,16 @@ typedef void (*grpc_security_call_host_check_cb)(grpc_exec_ctx *exec_ctx,
                                                  grpc_security_status status);
 
 struct grpc_channel_security_connector {
-  grpc_security_connector base; /* requires is_client_side to be non 0. */
+  grpc_security_connector base;
   grpc_call_credentials *request_metadata_creds;
   void (*check_call_host)(grpc_exec_ctx *exec_ctx,
                           grpc_channel_security_connector *sc, const char *host,
                           grpc_auth_context *auth_context,
                           grpc_security_call_host_check_cb cb, void *user_data);
+  void (*do_handshake)(grpc_exec_ctx *exec_ctx,
+                       grpc_channel_security_connector *sc,
+                       grpc_endpoint *nonsecure_endpoint,
+                       grpc_security_handshake_done_cb cb, void *user_data);
 };
 
 /* Checks that the host that will be set for a call is acceptable. */
@@ -167,6 +153,39 @@ void grpc_channel_security_connector_check_call_host(
     const char *host, grpc_auth_context *auth_context,
     grpc_security_call_host_check_cb cb, void *user_data);
 
+/* Handshake. */
+void grpc_channel_security_connector_do_handshake(
+    grpc_exec_ctx *exec_ctx, grpc_channel_security_connector *connector,
+    grpc_endpoint *nonsecure_endpoint, grpc_security_handshake_done_cb cb,
+    void *user_data);
+
+/* --- server_security_connector object. ---
+
+    A server security connector object represents away to configure the
+    underlying transport security mechanism on the server side.  */
+
+typedef struct grpc_server_security_connector grpc_server_security_connector;
+
+struct grpc_server_security_connector {
+  grpc_security_connector base;
+  gpr_mu mu;
+  grpc_security_connector_handshake_list *handshaking_handshakes;
+  const grpc_channel_args *channel_args;
+  void (*do_handshake)(grpc_exec_ctx *exec_ctx,
+                       grpc_server_security_connector *sc,
+                       grpc_tcp_server_acceptor *acceptor,
+                       grpc_endpoint *nonsecure_endpoint,
+                       grpc_security_handshake_done_cb cb, void *user_data);
+};
+
+void grpc_server_security_connector_do_handshake(
+    grpc_exec_ctx *exec_ctx, grpc_server_security_connector *sc,
+    grpc_tcp_server_acceptor *acceptor, grpc_endpoint *nonsecure_endpoint,
+    grpc_security_handshake_done_cb cb, void *user_data);
+
+void grpc_server_security_connector_shutdown(
+    grpc_exec_ctx *exec_ctx, grpc_server_security_connector *connector);
+
 /* --- Creation security connectors. --- */
 
 /* For TESTING ONLY!
@@ -176,7 +195,8 @@ grpc_channel_security_connector *grpc_fake_channel_security_connector_create(
 
 /* For TESTING ONLY!
    Creates a fake connector that emulates real server security.  */
-grpc_security_connector *grpc_fake_server_security_connector_create(void);
+grpc_server_security_connector *grpc_fake_server_security_connector_create(
+    void);
 
 /* Config for ssl clients. */
 typedef struct {
@@ -231,7 +251,7 @@ typedef struct {
   specific error code otherwise.
 */
 grpc_security_status grpc_ssl_server_security_connector_create(
-    const grpc_ssl_server_config *config, grpc_security_connector **sc);
+    const grpc_ssl_server_config *config, grpc_server_security_connector **sc);
 
 /* Util. */
 const tsi_peer_property *tsi_peer_get_property_by_name(const tsi_peer *peer,
diff --git a/src/core/security/server_secure_chttp2.c b/src/core/security/server_secure_chttp2.c
index 84a883390c2a19a7fdb5d756501e9cd44ad8e540..91547eb26e91ce168aff8fb57b4ca71bd1ad5c69 100644
--- a/src/core/security/server_secure_chttp2.c
+++ b/src/core/security/server_secure_chttp2.c
@@ -55,7 +55,7 @@
 typedef struct grpc_server_secure_state {
   grpc_server *server;
   grpc_tcp_server *tcp;
-  grpc_security_connector *sc;
+  grpc_server_security_connector *sc;
   grpc_server_credentials *creds;
   int is_shutdown;
   gpr_mu mu;
@@ -74,7 +74,7 @@ static void state_unref(grpc_server_secure_state *state) {
     gpr_mu_lock(&state->mu);
     gpr_mu_unlock(&state->mu);
     /* clean up */
-    GRPC_SECURITY_CONNECTOR_UNREF(state->sc, "server");
+    GRPC_SECURITY_CONNECTOR_UNREF(&state->sc->base, "server");
     grpc_server_credentials_unref(state->creds);
     gpr_free(state);
   }
@@ -130,8 +130,8 @@ static void on_accept(grpc_exec_ctx *exec_ctx, void *statep, grpc_endpoint *tcp,
                       grpc_tcp_server_acceptor *acceptor) {
   grpc_server_secure_state *state = statep;
   state_ref(state);
-  grpc_security_connector_do_handshake(exec_ctx, state->sc, tcp,
-                                       on_secure_handshake_done, state);
+  grpc_server_security_connector_do_handshake(
+      exec_ctx, state->sc, acceptor, tcp, on_secure_handshake_done, state);
 }
 
 /* Server callback: start listening on our ports */
@@ -148,7 +148,7 @@ static void destroy_done(grpc_exec_ctx *exec_ctx, void *statep, bool success) {
     state->destroy_callback->cb(exec_ctx, state->destroy_callback->cb_arg,
                                 success);
   }
-  grpc_security_connector_shutdown(exec_ctx, state->sc);
+  grpc_server_security_connector_shutdown(exec_ctx, state->sc);
   state_unref(state);
 }
 
@@ -176,7 +176,7 @@ int grpc_server_add_secure_http2_port(grpc_server *server, const char *addr,
   int port_num = -1;
   int port_temp;
   grpc_security_status status = GRPC_SECURITY_ERROR;
-  grpc_security_connector *sc = NULL;
+  grpc_server_security_connector *sc = NULL;
   grpc_exec_ctx exec_ctx = GRPC_EXEC_CTX_INIT;
 
   GRPC_API_TRACE(
@@ -256,7 +256,7 @@ error:
     grpc_tcp_server_unref(&exec_ctx, tcp);
   } else {
     if (sc) {
-      GRPC_SECURITY_CONNECTOR_UNREF(sc, "server");
+      GRPC_SECURITY_CONNECTOR_UNREF(&sc->base, "server");
     }
     if (state) {
       gpr_free(state);
diff --git a/src/core/surface/alarm.c b/src/core/surface/alarm.c
index fb496f6c474ace029a792b43dada119c2d7b2706..8169ede065511111a326a992623e4eefccef947d 100644
--- a/src/core/surface/alarm.c
+++ b/src/core/surface/alarm.c
@@ -64,8 +64,9 @@ grpc_alarm *grpc_alarm_create(grpc_completion_queue *cq, gpr_timespec deadline,
   alarm->tag = tag;
 
   grpc_cq_begin_op(cq, tag);
-  grpc_timer_init(&exec_ctx, &alarm->alarm, deadline, alarm_cb, alarm,
-                  gpr_now(GPR_CLOCK_MONOTONIC));
+  grpc_timer_init(&exec_ctx, &alarm->alarm,
+                  gpr_convert_clock_type(deadline, GPR_CLOCK_MONOTONIC),
+                  alarm_cb, alarm, gpr_now(GPR_CLOCK_MONOTONIC));
   grpc_exec_ctx_finish(&exec_ctx);
   return alarm;
 }
diff --git a/src/core/surface/completion_queue.c b/src/core/surface/completion_queue.c
index 41449fb4a6b3f8d9e66deb489fe8ae4e05ca277e..f6a95ebbd3ffd23f38a50b88e851f0d99b96c8b8 100644
--- a/src/core/surface/completion_queue.c
+++ b/src/core/surface/completion_queue.c
@@ -57,7 +57,8 @@ typedef struct {
 
 /* Completion queue structure */
 struct grpc_completion_queue {
-  gpr_mu mu;
+  /** owned by pollset */
+  gpr_mu *mu;
   /** completed events */
   grpc_cq_completion completed_head;
   grpc_cq_completion *completed_tail;
@@ -97,7 +98,6 @@ void grpc_cq_global_shutdown(void) {
   while (g_freelist) {
     grpc_completion_queue *next = g_freelist->next_free;
     grpc_pollset_destroy(POLLSET_FROM_CQ(g_freelist));
-    gpr_mu_destroy(&g_freelist->mu);
 #ifndef NDEBUG
     gpr_free(g_freelist->outstanding_tags);
 #endif
@@ -128,7 +128,6 @@ grpc_completion_queue *grpc_completion_queue_create(void *reserved) {
     gpr_mu_unlock(&g_freelist_mu);
 
     cc = gpr_malloc(sizeof(grpc_completion_queue) + grpc_pollset_size());
-    gpr_mu_init(&cc->mu);
     grpc_pollset_init(POLLSET_FROM_CQ(cc), &cc->mu);
 #ifndef NDEBUG
     cc->outstanding_tags = NULL;
@@ -198,7 +197,7 @@ void grpc_cq_internal_unref(grpc_completion_queue *cc) {
 
 void grpc_cq_begin_op(grpc_completion_queue *cc, void *tag) {
 #ifndef NDEBUG
-  gpr_mu_lock(&cc->mu);
+  gpr_mu_lock(cc->mu);
   GPR_ASSERT(!cc->shutdown_called);
   if (cc->outstanding_tag_count == cc->outstanding_tag_capacity) {
     cc->outstanding_tag_capacity = GPR_MAX(4, 2 * cc->outstanding_tag_capacity);
@@ -207,7 +206,7 @@ void grpc_cq_begin_op(grpc_completion_queue *cc, void *tag) {
                                               cc->outstanding_tag_capacity);
   }
   cc->outstanding_tags[cc->outstanding_tag_count++] = tag;
-  gpr_mu_unlock(&cc->mu);
+  gpr_mu_unlock(cc->mu);
 #endif
   gpr_ref(&cc->pending_events);
 }
@@ -235,7 +234,7 @@ void grpc_cq_end_op(grpc_exec_ctx *exec_ctx, grpc_completion_queue *cc,
   storage->next =
       ((uintptr_t)&cc->completed_head) | ((uintptr_t)(success != 0));
 
-  gpr_mu_lock(&cc->mu);
+  gpr_mu_lock(cc->mu);
 #ifndef NDEBUG
   for (i = 0; i < (int)cc->outstanding_tag_count; i++) {
     if (cc->outstanding_tags[i] == tag) {
@@ -261,7 +260,7 @@ void grpc_cq_end_op(grpc_exec_ctx *exec_ctx, grpc_completion_queue *cc,
       }
     }
     grpc_pollset_kick(POLLSET_FROM_CQ(cc), pluck_worker);
-    gpr_mu_unlock(&cc->mu);
+    gpr_mu_unlock(cc->mu);
   } else {
     cc->completed_tail->next =
         ((uintptr_t)storage) | (1u & (uintptr_t)cc->completed_tail->next);
@@ -271,7 +270,7 @@ void grpc_cq_end_op(grpc_exec_ctx *exec_ctx, grpc_completion_queue *cc,
     cc->shutdown = 1;
     grpc_pollset_shutdown(exec_ctx, POLLSET_FROM_CQ(cc),
                           &cc->pollset_shutdown_done);
-    gpr_mu_unlock(&cc->mu);
+    gpr_mu_unlock(cc->mu);
   }
 
   GPR_TIMER_END("grpc_cq_end_op", 0);
@@ -299,7 +298,7 @@ grpc_event grpc_completion_queue_next(grpc_completion_queue *cc,
   deadline = gpr_convert_clock_type(deadline, GPR_CLOCK_MONOTONIC);
 
   GRPC_CQ_INTERNAL_REF(cc, "next");
-  gpr_mu_lock(&cc->mu);
+  gpr_mu_lock(cc->mu);
   for (;;) {
     if (cc->completed_tail != &cc->completed_head) {
       grpc_cq_completion *c = (grpc_cq_completion *)cc->completed_head.next;
@@ -307,7 +306,7 @@ grpc_event grpc_completion_queue_next(grpc_completion_queue *cc,
       if (c == cc->completed_tail) {
         cc->completed_tail = &cc->completed_head;
       }
-      gpr_mu_unlock(&cc->mu);
+      gpr_mu_unlock(cc->mu);
       ret.type = GRPC_OP_COMPLETE;
       ret.success = c->next & 1u;
       ret.tag = c->tag;
@@ -315,14 +314,14 @@ grpc_event grpc_completion_queue_next(grpc_completion_queue *cc,
       break;
     }
     if (cc->shutdown) {
-      gpr_mu_unlock(&cc->mu);
+      gpr_mu_unlock(cc->mu);
       memset(&ret, 0, sizeof(ret));
       ret.type = GRPC_QUEUE_SHUTDOWN;
       break;
     }
     now = gpr_now(GPR_CLOCK_MONOTONIC);
     if (!first_loop && gpr_time_cmp(now, deadline) >= 0) {
-      gpr_mu_unlock(&cc->mu);
+      gpr_mu_unlock(cc->mu);
       memset(&ret, 0, sizeof(ret));
       ret.type = GRPC_QUEUE_TIMEOUT;
       break;
@@ -335,9 +334,9 @@ grpc_event grpc_completion_queue_next(grpc_completion_queue *cc,
     gpr_timespec iteration_deadline = deadline;
     if (grpc_timer_check(&exec_ctx, now, &iteration_deadline)) {
       GPR_TIMER_MARK("alarm_triggered", 0);
-      gpr_mu_unlock(&cc->mu);
+      gpr_mu_unlock(cc->mu);
       grpc_exec_ctx_flush(&exec_ctx);
-      gpr_mu_lock(&cc->mu);
+      gpr_mu_lock(cc->mu);
       continue;
     } else {
       grpc_pollset_work(&exec_ctx, POLLSET_FROM_CQ(cc), &worker, now,
@@ -401,7 +400,7 @@ grpc_event grpc_completion_queue_pluck(grpc_completion_queue *cc, void *tag,
   deadline = gpr_convert_clock_type(deadline, GPR_CLOCK_MONOTONIC);
 
   GRPC_CQ_INTERNAL_REF(cc, "pluck");
-  gpr_mu_lock(&cc->mu);
+  gpr_mu_lock(cc->mu);
   for (;;) {
     prev = &cc->completed_head;
     while ((c = (grpc_cq_completion *)(prev->next & ~(uintptr_t)1)) !=
@@ -411,7 +410,7 @@ grpc_event grpc_completion_queue_pluck(grpc_completion_queue *cc, void *tag,
         if (c == cc->completed_tail) {
           cc->completed_tail = prev;
         }
-        gpr_mu_unlock(&cc->mu);
+        gpr_mu_unlock(cc->mu);
         ret.type = GRPC_OP_COMPLETE;
         ret.success = c->next & 1u;
         ret.tag = c->tag;
@@ -421,7 +420,7 @@ grpc_event grpc_completion_queue_pluck(grpc_completion_queue *cc, void *tag,
       prev = c;
     }
     if (cc->shutdown) {
-      gpr_mu_unlock(&cc->mu);
+      gpr_mu_unlock(cc->mu);
       memset(&ret, 0, sizeof(ret));
       ret.type = GRPC_QUEUE_SHUTDOWN;
       break;
@@ -431,7 +430,7 @@ grpc_event grpc_completion_queue_pluck(grpc_completion_queue *cc, void *tag,
               "Too many outstanding grpc_completion_queue_pluck calls: maximum "
               "is %d",
               GRPC_MAX_COMPLETION_QUEUE_PLUCKERS);
-      gpr_mu_unlock(&cc->mu);
+      gpr_mu_unlock(cc->mu);
       memset(&ret, 0, sizeof(ret));
       /* TODO(ctiller): should we use a different result here */
       ret.type = GRPC_QUEUE_TIMEOUT;
@@ -440,7 +439,7 @@ grpc_event grpc_completion_queue_pluck(grpc_completion_queue *cc, void *tag,
     now = gpr_now(GPR_CLOCK_MONOTONIC);
     if (!first_loop && gpr_time_cmp(now, deadline) >= 0) {
       del_plucker(cc, tag, &worker);
-      gpr_mu_unlock(&cc->mu);
+      gpr_mu_unlock(cc->mu);
       memset(&ret, 0, sizeof(ret));
       ret.type = GRPC_QUEUE_TIMEOUT;
       break;
@@ -453,10 +452,9 @@ grpc_event grpc_completion_queue_pluck(grpc_completion_queue *cc, void *tag,
     gpr_timespec iteration_deadline = deadline;
     if (grpc_timer_check(&exec_ctx, now, &iteration_deadline)) {
       GPR_TIMER_MARK("alarm_triggered", 0);
-      gpr_mu_unlock(&cc->mu);
+      gpr_mu_unlock(cc->mu);
       grpc_exec_ctx_flush(&exec_ctx);
-      gpr_mu_lock(&cc->mu);
-      continue;
+      gpr_mu_lock(cc->mu);
     } else {
       grpc_pollset_work(&exec_ctx, POLLSET_FROM_CQ(cc), &worker, now,
                         iteration_deadline);
@@ -479,9 +477,9 @@ void grpc_completion_queue_shutdown(grpc_completion_queue *cc) {
   grpc_exec_ctx exec_ctx = GRPC_EXEC_CTX_INIT;
   GPR_TIMER_BEGIN("grpc_completion_queue_shutdown", 0);
   GRPC_API_TRACE("grpc_completion_queue_shutdown(cc=%p)", 1, (cc));
-  gpr_mu_lock(&cc->mu);
+  gpr_mu_lock(cc->mu);
   if (cc->shutdown_called) {
-    gpr_mu_unlock(&cc->mu);
+    gpr_mu_unlock(cc->mu);
     GPR_TIMER_END("grpc_completion_queue_shutdown", 0);
     return;
   }
@@ -492,7 +490,7 @@ void grpc_completion_queue_shutdown(grpc_completion_queue *cc) {
     grpc_pollset_shutdown(&exec_ctx, POLLSET_FROM_CQ(cc),
                           &cc->pollset_shutdown_done);
   }
-  gpr_mu_unlock(&cc->mu);
+  gpr_mu_unlock(cc->mu);
   grpc_exec_ctx_finish(&exec_ctx);
   GPR_TIMER_END("grpc_completion_queue_shutdown", 0);
 }
diff --git a/src/core/surface/secure_channel_create.c b/src/core/surface/secure_channel_create.c
index 9c04426d8720c990f134a3b283a719f0ea7c0669..aadfac4c91f6367b18177696399ec41649f7061a 100644
--- a/src/core/surface/secure_channel_create.c
+++ b/src/core/surface/secure_channel_create.c
@@ -130,9 +130,9 @@ static void on_secure_handshake_done(grpc_exec_ctx *exec_ctx, void *arg,
 static void on_initial_connect_string_sent(grpc_exec_ctx *exec_ctx, void *arg,
                                            bool success) {
   connector *c = arg;
-  grpc_security_connector_do_handshake(exec_ctx, &c->security_connector->base,
-                                       c->connecting_endpoint,
-                                       on_secure_handshake_done, c);
+  grpc_channel_security_connector_do_handshake(exec_ctx, c->security_connector,
+                                               c->connecting_endpoint,
+                                               on_secure_handshake_done, c);
 }
 
 static void connected(grpc_exec_ctx *exec_ctx, void *arg, bool success) {
@@ -153,9 +153,8 @@ static void connected(grpc_exec_ctx *exec_ctx, void *arg, bool success) {
       grpc_endpoint_write(exec_ctx, tcp, &c->initial_string_buffer,
                           &c->initial_string_sent);
     } else {
-      grpc_security_connector_do_handshake(exec_ctx,
-                                           &c->security_connector->base, tcp,
-                                           on_secure_handshake_done, c);
+      grpc_channel_security_connector_do_handshake(
+          exec_ctx, c->security_connector, tcp, on_secure_handshake_done, c);
     }
   } else {
     memset(c->result, 0, sizeof(*c->result));
diff --git a/src/cpp/common/alarm.cc b/src/cpp/common/alarm.cc
deleted file mode 100644
index a2896887682aeea4e258ffe5a4dbcfca01b64052..0000000000000000000000000000000000000000
--- a/src/cpp/common/alarm.cc
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright 2015-2016, 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++/alarm.h>
-#include <grpc++/completion_queue.h>
-#include <grpc++/impl/grpc_library.h>
-#include <grpc/grpc.h>
-
-namespace grpc {
-
-static internal::GrpcLibraryInitializer g_gli_initializer;
-Alarm::Alarm(CompletionQueue* cq, gpr_timespec deadline, void* tag)
-    : tag_(tag),
-      alarm_(grpc_alarm_create(cq->cq(), deadline, static_cast<void*>(&tag_))) {
-  g_gli_initializer.summon();
-}
-
-Alarm::~Alarm() { grpc_alarm_destroy(alarm_); }
-
-void Alarm::Cancel() { grpc_alarm_cancel(alarm_); }
-
-}  // namespace grpc
diff --git a/src/csharp/Grpc.Core/Internal/PlatformApis.cs b/src/csharp/Grpc.Core/Internal/PlatformApis.cs
index f0c5b0f63f61e1d15d0d04137f279c64477d1e5d..fb1acfb607b23925900c2d211746fa0bed32e365 100644
--- a/src/csharp/Grpc.Core/Internal/PlatformApis.cs
+++ b/src/csharp/Grpc.Core/Internal/PlatformApis.cs
@@ -53,12 +53,18 @@ namespace Grpc.Core.Internal
 
         static PlatformApis()
         {
+#if DNXCORE50
+            isLinux = RuntimeInformation.IsOSPlatform(OSPlatform.Linux);
+            isMacOSX = RuntimeInformation.IsOSPlatform(OSPlatform.OSX);
+            isWindows = RuntimeInformation.IsOSPlatform(OSPlatform.Windows);
+#else
             var platform = Environment.OSVersion.Platform;
 
             // PlatformID.MacOSX is never returned, commonly used trick is to identify Mac is by using uname.
             isMacOSX = (platform == PlatformID.Unix && GetUname() == "Darwin");
             isLinux = (platform == PlatformID.Unix && !isMacOSX);
             isWindows = (platform == PlatformID.Win32NT || platform == PlatformID.Win32S || platform == PlatformID.Win32Windows);
+#endif
             isMono = Type.GetType("Mono.Runtime") != null;
         }
 
diff --git a/src/csharp/Grpc.HealthCheck.Tests/HealthClientServerTest.cs b/src/csharp/Grpc.HealthCheck.Tests/HealthClientServerTest.cs
index a8a76c749229468a56bd246d39ca2c7cdc19e087..c3fac05324c8245694c425eb88cab306dcc7f641 100644
--- a/src/csharp/Grpc.HealthCheck.Tests/HealthClientServerTest.cs
+++ b/src/csharp/Grpc.HealthCheck.Tests/HealthClientServerTest.cs
@@ -36,7 +36,7 @@ using System.Text;
 using System.Threading.Tasks;
 
 using Grpc.Core;
-using Grpc.Health.V1Alpha;
+using Grpc.Health.V1;
 using NUnit.Framework;
 
 namespace Grpc.HealthCheck.Tests
@@ -49,7 +49,7 @@ namespace Grpc.HealthCheck.Tests
         const string Host = "localhost";
         Server server;
         Channel channel;
-        Grpc.Health.V1Alpha.Health.IHealthClient client;
+        Grpc.Health.V1.Health.IHealthClient client;
         Grpc.HealthCheck.HealthServiceImpl serviceImpl;
 
         [TestFixtureSetUp]
@@ -59,13 +59,13 @@ namespace Grpc.HealthCheck.Tests
 
             server = new Server
             {
-                Services = { Grpc.Health.V1Alpha.Health.BindService(serviceImpl) },
+                Services = { Grpc.Health.V1.Health.BindService(serviceImpl) },
                 Ports = { { Host, ServerPort.PickUnused, ServerCredentials.Insecure } }
             };
             server.Start();
             channel = new Channel(Host, server.Ports.Single().BoundPort, ChannelCredentials.Insecure);
 
-            client = Grpc.Health.V1Alpha.Health.NewClient(channel);
+            client = Grpc.Health.V1.Health.NewClient(channel);
         }
 
         [TestFixtureTearDown]
@@ -79,16 +79,16 @@ namespace Grpc.HealthCheck.Tests
         [Test]
         public void ServiceIsRunning()
         {
-            serviceImpl.SetStatus("", "", HealthCheckResponse.Types.ServingStatus.SERVING);
+            serviceImpl.SetStatus("", HealthCheckResponse.Types.ServingStatus.SERVING);
 
-            var response = client.Check(new HealthCheckRequest { Host = "", Service = "" });
+            var response = client.Check(new HealthCheckRequest { Service = "" });
             Assert.AreEqual(HealthCheckResponse.Types.ServingStatus.SERVING, response.Status);
         }
 
         [Test]
         public void ServiceDoesntExist()
         {
-            Assert.Throws(Is.TypeOf(typeof(RpcException)).And.Property("Status").Property("StatusCode").EqualTo(StatusCode.NotFound), () => client.Check(new HealthCheckRequest { Host = "", Service = "nonexistent.service" }));
+            Assert.Throws(Is.TypeOf(typeof(RpcException)).And.Property("Status").Property("StatusCode").EqualTo(StatusCode.NotFound), () => client.Check(new HealthCheckRequest { Service = "nonexistent.service" }));
         }
 
         // TODO(jtattermusch): add test with timeout once timeouts are supported
diff --git a/src/csharp/Grpc.HealthCheck.Tests/HealthServiceImplTest.cs b/src/csharp/Grpc.HealthCheck.Tests/HealthServiceImplTest.cs
index 2097c0dc8cf7daa2c79f72a4706299af0ee76d0d..47e4b7c2a70194bb84232f42db9588756c6dffca 100644
--- a/src/csharp/Grpc.HealthCheck.Tests/HealthServiceImplTest.cs
+++ b/src/csharp/Grpc.HealthCheck.Tests/HealthServiceImplTest.cs
@@ -1,5 +1,5 @@
 #region Copyright notice and license
-// Copyright 2015, Google Inc.
+// Copyright 2015-2016, Google Inc.
 // All rights reserved.
 //
 // Redistribution and use in source and binary forms, with or without
@@ -36,7 +36,7 @@ using System.Text;
 using System.Threading.Tasks;
 
 using Grpc.Core;
-using Grpc.Health.V1Alpha;
+using Grpc.Health.V1;
 using NUnit.Framework;
 
 namespace Grpc.HealthCheck.Tests
@@ -50,58 +50,56 @@ namespace Grpc.HealthCheck.Tests
         public void SetStatus()
         {
             var impl = new HealthServiceImpl();
-            impl.SetStatus("", "", HealthCheckResponse.Types.ServingStatus.SERVING);
-            Assert.AreEqual(HealthCheckResponse.Types.ServingStatus.SERVING, GetStatusHelper(impl, "", ""));
+            impl.SetStatus("", HealthCheckResponse.Types.ServingStatus.SERVING);
+            Assert.AreEqual(HealthCheckResponse.Types.ServingStatus.SERVING, GetStatusHelper(impl, ""));
 
-            impl.SetStatus("", "", HealthCheckResponse.Types.ServingStatus.NOT_SERVING);
-            Assert.AreEqual(HealthCheckResponse.Types.ServingStatus.NOT_SERVING, GetStatusHelper(impl, "", ""));
+            impl.SetStatus("", HealthCheckResponse.Types.ServingStatus.NOT_SERVING);
+            Assert.AreEqual(HealthCheckResponse.Types.ServingStatus.NOT_SERVING, GetStatusHelper(impl, ""));
 
-            impl.SetStatus("virtual-host", "", HealthCheckResponse.Types.ServingStatus.UNKNOWN);
-            Assert.AreEqual(HealthCheckResponse.Types.ServingStatus.UNKNOWN, GetStatusHelper(impl, "virtual-host", ""));
+            impl.SetStatus("", HealthCheckResponse.Types.ServingStatus.UNKNOWN);
+            Assert.AreEqual(HealthCheckResponse.Types.ServingStatus.UNKNOWN, GetStatusHelper(impl, ""));
 
-            impl.SetStatus("virtual-host", "grpc.test.TestService", HealthCheckResponse.Types.ServingStatus.SERVING);
-            Assert.AreEqual(HealthCheckResponse.Types.ServingStatus.SERVING, GetStatusHelper(impl, "virtual-host", "grpc.test.TestService"));
+            impl.SetStatus("grpc.test.TestService", HealthCheckResponse.Types.ServingStatus.SERVING);
+            Assert.AreEqual(HealthCheckResponse.Types.ServingStatus.SERVING, GetStatusHelper(impl, "grpc.test.TestService"));
         }
 
         [Test]
         public void ClearStatus()
         {
             var impl = new HealthServiceImpl();
-            impl.SetStatus("", "", HealthCheckResponse.Types.ServingStatus.SERVING);
-            impl.SetStatus("virtual-host", "", HealthCheckResponse.Types.ServingStatus.UNKNOWN);
+            impl.SetStatus("", HealthCheckResponse.Types.ServingStatus.SERVING);
+            impl.SetStatus("grpc.test.TestService", HealthCheckResponse.Types.ServingStatus.UNKNOWN);
 
-            impl.ClearStatus("", "");
+            impl.ClearStatus("");
 
-            Assert.Throws(Is.TypeOf(typeof(RpcException)).And.Property("Status").Property("StatusCode").EqualTo(StatusCode.NotFound), () => GetStatusHelper(impl, "", ""));
-            Assert.AreEqual(HealthCheckResponse.Types.ServingStatus.UNKNOWN, GetStatusHelper(impl, "virtual-host", ""));
+            Assert.Throws(Is.TypeOf(typeof(RpcException)).And.Property("Status").Property("StatusCode").EqualTo(StatusCode.NotFound), () => GetStatusHelper(impl, ""));
+            Assert.AreEqual(HealthCheckResponse.Types.ServingStatus.UNKNOWN, GetStatusHelper(impl, "grpc.test.TestService"));
         }
 
         [Test]
         public void ClearAll()
         {
             var impl = new HealthServiceImpl();
-            impl.SetStatus("", "", HealthCheckResponse.Types.ServingStatus.SERVING);
-            impl.SetStatus("virtual-host", "", HealthCheckResponse.Types.ServingStatus.UNKNOWN);
+            impl.SetStatus("", HealthCheckResponse.Types.ServingStatus.SERVING);
+            impl.SetStatus("grpc.test.TestService", HealthCheckResponse.Types.ServingStatus.UNKNOWN);
 
             impl.ClearAll();
-            Assert.Throws(typeof(RpcException), () => GetStatusHelper(impl, "", ""));
-            Assert.Throws(typeof(RpcException), () => GetStatusHelper(impl, "virtual-host", ""));
+            Assert.Throws(typeof(RpcException), () => GetStatusHelper(impl, ""));
+            Assert.Throws(typeof(RpcException), () => GetStatusHelper(impl, "grpc.test.TestService"));
         }
 
         [Test]
         public void NullsRejected()
         {
             var impl = new HealthServiceImpl();
-            Assert.Throws(typeof(ArgumentNullException), () => impl.SetStatus(null, "", HealthCheckResponse.Types.ServingStatus.SERVING));
-            Assert.Throws(typeof(ArgumentNullException), () => impl.SetStatus("", null, HealthCheckResponse.Types.ServingStatus.SERVING));
+            Assert.Throws(typeof(ArgumentNullException), () => impl.SetStatus(null, HealthCheckResponse.Types.ServingStatus.SERVING));
 
-            Assert.Throws(typeof(ArgumentNullException), () => impl.ClearStatus(null, ""));
-            Assert.Throws(typeof(ArgumentNullException), () => impl.ClearStatus("", null));
+            Assert.Throws(typeof(ArgumentNullException), () => impl.ClearStatus(null));
         }
 
-        private static HealthCheckResponse.Types.ServingStatus GetStatusHelper(HealthServiceImpl impl, string host, string service)
+        private static HealthCheckResponse.Types.ServingStatus GetStatusHelper(HealthServiceImpl impl, string service)
         {
-            return impl.Check(new HealthCheckRequest { Host = host, Service = service }, null).Result.Status;
+            return impl.Check(new HealthCheckRequest { Service = service }, null).Result.Status;
         }
     }
 }
diff --git a/src/csharp/Grpc.HealthCheck/Grpc.HealthCheck.nuspec b/src/csharp/Grpc.HealthCheck/Grpc.HealthCheck.nuspec
index 66386288df132f448b0dee70305b15ae41e0c824..7b3b391009eb05ca1ba9a85aceec8b829d22939b 100644
--- a/src/csharp/Grpc.HealthCheck/Grpc.HealthCheck.nuspec
+++ b/src/csharp/Grpc.HealthCheck/Grpc.HealthCheck.nuspec
@@ -4,7 +4,7 @@
     <id>Grpc.HealthCheck</id>
     <title>gRPC C# Healthchecking</title>
     <summary>Implementation of gRPC health service</summary>
-    <description>Example implementation of grpc.health.v1alpha service that can be used for health-checking.</description>
+    <description>Example implementation of grpc.health.v1 service that can be used for health-checking.</description>
     <version>$version$</version>
     <authors>Google Inc.</authors>
     <owners>grpc-packages</owners>
diff --git a/src/csharp/Grpc.HealthCheck/Health.cs b/src/csharp/Grpc.HealthCheck/Health.cs
index 56673f1adf699bef3998cae252799bcbe7d3bfe5..d0d0c0b519665376069e283e7ae90f347c4b127a 100644
--- a/src/csharp/Grpc.HealthCheck/Health.cs
+++ b/src/csharp/Grpc.HealthCheck/Health.cs
@@ -7,7 +7,7 @@ using pb = global::Google.Protobuf;
 using pbc = global::Google.Protobuf.Collections;
 using pbr = global::Google.Protobuf.Reflection;
 using scg = global::System.Collections.Generic;
-namespace Grpc.Health.V1Alpha {
+namespace Grpc.Health.V1 {
 
   /// <summary>Holder for reflection information generated from health.proto</summary>
   [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
@@ -23,20 +23,19 @@ namespace Grpc.Health.V1Alpha {
     static HealthReflection() {
       byte[] descriptorData = global::System.Convert.FromBase64String(
           string.Concat(
-            "CgxoZWFsdGgucHJvdG8SE2dycGMuaGVhbHRoLnYxYWxwaGEiMwoSSGVhbHRo",
-            "Q2hlY2tSZXF1ZXN0EgwKBGhvc3QYASABKAkSDwoHc2VydmljZRgCIAEoCSKZ",
-            "AQoTSGVhbHRoQ2hlY2tSZXNwb25zZRJGCgZzdGF0dXMYASABKA4yNi5ncnBj",
-            "LmhlYWx0aC52MWFscGhhLkhlYWx0aENoZWNrUmVzcG9uc2UuU2VydmluZ1N0",
-            "YXR1cyI6Cg1TZXJ2aW5nU3RhdHVzEgsKB1VOS05PV04QABILCgdTRVJWSU5H",
-            "EAESDwoLTk9UX1NFUlZJTkcQAjJkCgZIZWFsdGgSWgoFQ2hlY2sSJy5ncnBj",
-            "LmhlYWx0aC52MWFscGhhLkhlYWx0aENoZWNrUmVxdWVzdBooLmdycGMuaGVh",
-            "bHRoLnYxYWxwaGEuSGVhbHRoQ2hlY2tSZXNwb25zZUIWqgITR3JwYy5IZWFs",
-            "dGguVjFBbHBoYWIGcHJvdG8z"));
+            "CgxoZWFsdGgucHJvdG8SDmdycGMuaGVhbHRoLnYxIiUKEkhlYWx0aENoZWNr",
+            "UmVxdWVzdBIPCgdzZXJ2aWNlGAEgASgJIpQBChNIZWFsdGhDaGVja1Jlc3Bv",
+            "bnNlEkEKBnN0YXR1cxgBIAEoDjIxLmdycGMuaGVhbHRoLnYxLkhlYWx0aENo",
+            "ZWNrUmVzcG9uc2UuU2VydmluZ1N0YXR1cyI6Cg1TZXJ2aW5nU3RhdHVzEgsK",
+            "B1VOS05PV04QABILCgdTRVJWSU5HEAESDwoLTk9UX1NFUlZJTkcQAjJaCgZI",
+            "ZWFsdGgSUAoFQ2hlY2sSIi5ncnBjLmhlYWx0aC52MS5IZWFsdGhDaGVja1Jl",
+            "cXVlc3QaIy5ncnBjLmhlYWx0aC52MS5IZWFsdGhDaGVja1Jlc3BvbnNlQhGq",
+            "Ag5HcnBjLkhlYWx0aC5WMWIGcHJvdG8z"));
       descriptor = pbr::FileDescriptor.FromGeneratedCode(descriptorData,
           new pbr::FileDescriptor[] { },
           new pbr::GeneratedCodeInfo(null, new pbr::GeneratedCodeInfo[] {
-            new pbr::GeneratedCodeInfo(typeof(global::Grpc.Health.V1Alpha.HealthCheckRequest), global::Grpc.Health.V1Alpha.HealthCheckRequest.Parser, new[]{ "Host", "Service" }, null, null, null),
-            new pbr::GeneratedCodeInfo(typeof(global::Grpc.Health.V1Alpha.HealthCheckResponse), global::Grpc.Health.V1Alpha.HealthCheckResponse.Parser, new[]{ "Status" }, null, new[]{ typeof(global::Grpc.Health.V1Alpha.HealthCheckResponse.Types.ServingStatus) }, null)
+            new pbr::GeneratedCodeInfo(typeof(global::Grpc.Health.V1.HealthCheckRequest), global::Grpc.Health.V1.HealthCheckRequest.Parser, new[]{ "Service" }, null, null, null),
+            new pbr::GeneratedCodeInfo(typeof(global::Grpc.Health.V1.HealthCheckResponse), global::Grpc.Health.V1.HealthCheckResponse.Parser, new[]{ "Status" }, null, new[]{ typeof(global::Grpc.Health.V1.HealthCheckResponse.Types.ServingStatus) }, null)
           }));
     }
     #endregion
@@ -49,7 +48,7 @@ namespace Grpc.Health.V1Alpha {
     public static pb::MessageParser<HealthCheckRequest> Parser { get { return _parser; } }
 
     public static pbr::MessageDescriptor Descriptor {
-      get { return global::Grpc.Health.V1Alpha.HealthReflection.Descriptor.MessageTypes[0]; }
+      get { return global::Grpc.Health.V1.HealthReflection.Descriptor.MessageTypes[0]; }
     }
 
     pbr::MessageDescriptor pb::IMessage.Descriptor {
@@ -63,7 +62,6 @@ namespace Grpc.Health.V1Alpha {
     partial void OnConstruction();
 
     public HealthCheckRequest(HealthCheckRequest other) : this() {
-      host_ = other.host_;
       service_ = other.service_;
     }
 
@@ -71,18 +69,8 @@ namespace Grpc.Health.V1Alpha {
       return new HealthCheckRequest(this);
     }
 
-    /// <summary>Field number for the "host" field.</summary>
-    public const int HostFieldNumber = 1;
-    private string host_ = "";
-    public string Host {
-      get { return host_; }
-      set {
-        host_ = pb::Preconditions.CheckNotNull(value, "value");
-      }
-    }
-
     /// <summary>Field number for the "service" field.</summary>
-    public const int ServiceFieldNumber = 2;
+    public const int ServiceFieldNumber = 1;
     private string service_ = "";
     public string Service {
       get { return service_; }
@@ -102,14 +90,12 @@ namespace Grpc.Health.V1Alpha {
       if (ReferenceEquals(other, this)) {
         return true;
       }
-      if (Host != other.Host) return false;
       if (Service != other.Service) return false;
       return true;
     }
 
     public override int GetHashCode() {
       int hash = 1;
-      if (Host.Length != 0) hash ^= Host.GetHashCode();
       if (Service.Length != 0) hash ^= Service.GetHashCode();
       return hash;
     }
@@ -119,21 +105,14 @@ namespace Grpc.Health.V1Alpha {
     }
 
     public void WriteTo(pb::CodedOutputStream output) {
-      if (Host.Length != 0) {
-        output.WriteRawTag(10);
-        output.WriteString(Host);
-      }
       if (Service.Length != 0) {
-        output.WriteRawTag(18);
+        output.WriteRawTag(10);
         output.WriteString(Service);
       }
     }
 
     public int CalculateSize() {
       int size = 0;
-      if (Host.Length != 0) {
-        size += 1 + pb::CodedOutputStream.ComputeStringSize(Host);
-      }
       if (Service.Length != 0) {
         size += 1 + pb::CodedOutputStream.ComputeStringSize(Service);
       }
@@ -144,9 +123,6 @@ namespace Grpc.Health.V1Alpha {
       if (other == null) {
         return;
       }
-      if (other.Host.Length != 0) {
-        Host = other.Host;
-      }
       if (other.Service.Length != 0) {
         Service = other.Service;
       }
@@ -160,10 +136,6 @@ namespace Grpc.Health.V1Alpha {
             input.SkipLastField();
             break;
           case 10: {
-            Host = input.ReadString();
-            break;
-          }
-          case 18: {
             Service = input.ReadString();
             break;
           }
@@ -179,7 +151,7 @@ namespace Grpc.Health.V1Alpha {
     public static pb::MessageParser<HealthCheckResponse> Parser { get { return _parser; } }
 
     public static pbr::MessageDescriptor Descriptor {
-      get { return global::Grpc.Health.V1Alpha.HealthReflection.Descriptor.MessageTypes[1]; }
+      get { return global::Grpc.Health.V1.HealthReflection.Descriptor.MessageTypes[1]; }
     }
 
     pbr::MessageDescriptor pb::IMessage.Descriptor {
@@ -202,8 +174,8 @@ namespace Grpc.Health.V1Alpha {
 
     /// <summary>Field number for the "status" field.</summary>
     public const int StatusFieldNumber = 1;
-    private global::Grpc.Health.V1Alpha.HealthCheckResponse.Types.ServingStatus status_ = global::Grpc.Health.V1Alpha.HealthCheckResponse.Types.ServingStatus.UNKNOWN;
-    public global::Grpc.Health.V1Alpha.HealthCheckResponse.Types.ServingStatus Status {
+    private global::Grpc.Health.V1.HealthCheckResponse.Types.ServingStatus status_ = global::Grpc.Health.V1.HealthCheckResponse.Types.ServingStatus.UNKNOWN;
+    public global::Grpc.Health.V1.HealthCheckResponse.Types.ServingStatus Status {
       get { return status_; }
       set {
         status_ = value;
@@ -227,7 +199,7 @@ namespace Grpc.Health.V1Alpha {
 
     public override int GetHashCode() {
       int hash = 1;
-      if (Status != global::Grpc.Health.V1Alpha.HealthCheckResponse.Types.ServingStatus.UNKNOWN) hash ^= Status.GetHashCode();
+      if (Status != global::Grpc.Health.V1.HealthCheckResponse.Types.ServingStatus.UNKNOWN) hash ^= Status.GetHashCode();
       return hash;
     }
 
@@ -236,7 +208,7 @@ namespace Grpc.Health.V1Alpha {
     }
 
     public void WriteTo(pb::CodedOutputStream output) {
-      if (Status != global::Grpc.Health.V1Alpha.HealthCheckResponse.Types.ServingStatus.UNKNOWN) {
+      if (Status != global::Grpc.Health.V1.HealthCheckResponse.Types.ServingStatus.UNKNOWN) {
         output.WriteRawTag(8);
         output.WriteEnum((int) Status);
       }
@@ -244,7 +216,7 @@ namespace Grpc.Health.V1Alpha {
 
     public int CalculateSize() {
       int size = 0;
-      if (Status != global::Grpc.Health.V1Alpha.HealthCheckResponse.Types.ServingStatus.UNKNOWN) {
+      if (Status != global::Grpc.Health.V1.HealthCheckResponse.Types.ServingStatus.UNKNOWN) {
         size += 1 + pb::CodedOutputStream.ComputeEnumSize((int) Status);
       }
       return size;
@@ -254,7 +226,7 @@ namespace Grpc.Health.V1Alpha {
       if (other == null) {
         return;
       }
-      if (other.Status != global::Grpc.Health.V1Alpha.HealthCheckResponse.Types.ServingStatus.UNKNOWN) {
+      if (other.Status != global::Grpc.Health.V1.HealthCheckResponse.Types.ServingStatus.UNKNOWN) {
         Status = other.Status;
       }
     }
@@ -267,7 +239,7 @@ namespace Grpc.Health.V1Alpha {
             input.SkipLastField();
             break;
           case 8: {
-            status_ = (global::Grpc.Health.V1Alpha.HealthCheckResponse.Types.ServingStatus) input.ReadEnum();
+            status_ = (global::Grpc.Health.V1.HealthCheckResponse.Types.ServingStatus) input.ReadEnum();
             break;
           }
         }
diff --git a/src/csharp/Grpc.HealthCheck/HealthGrpc.cs b/src/csharp/Grpc.HealthCheck/HealthGrpc.cs
index 882edd56270b6fbb2173c5b6cfcf058a3dd7e8df..68320eb5c2effa410693eec82851005105a854b7 100644
--- a/src/csharp/Grpc.HealthCheck/HealthGrpc.cs
+++ b/src/csharp/Grpc.HealthCheck/HealthGrpc.cs
@@ -7,15 +7,15 @@ using System.Threading;
 using System.Threading.Tasks;
 using Grpc.Core;
 
-namespace Grpc.Health.V1Alpha {
+namespace Grpc.Health.V1 {
   public static class Health
   {
-    static readonly string __ServiceName = "grpc.health.v1alpha.Health";
+    static readonly string __ServiceName = "grpc.health.v1.Health";
 
-    static readonly Marshaller<global::Grpc.Health.V1Alpha.HealthCheckRequest> __Marshaller_HealthCheckRequest = Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Grpc.Health.V1Alpha.HealthCheckRequest.Parser.ParseFrom);
-    static readonly Marshaller<global::Grpc.Health.V1Alpha.HealthCheckResponse> __Marshaller_HealthCheckResponse = Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Grpc.Health.V1Alpha.HealthCheckResponse.Parser.ParseFrom);
+    static readonly Marshaller<global::Grpc.Health.V1.HealthCheckRequest> __Marshaller_HealthCheckRequest = Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Grpc.Health.V1.HealthCheckRequest.Parser.ParseFrom);
+    static readonly Marshaller<global::Grpc.Health.V1.HealthCheckResponse> __Marshaller_HealthCheckResponse = Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Grpc.Health.V1.HealthCheckResponse.Parser.ParseFrom);
 
-    static readonly Method<global::Grpc.Health.V1Alpha.HealthCheckRequest, global::Grpc.Health.V1Alpha.HealthCheckResponse> __Method_Check = new Method<global::Grpc.Health.V1Alpha.HealthCheckRequest, global::Grpc.Health.V1Alpha.HealthCheckResponse>(
+    static readonly Method<global::Grpc.Health.V1.HealthCheckRequest, global::Grpc.Health.V1.HealthCheckResponse> __Method_Check = new Method<global::Grpc.Health.V1.HealthCheckRequest, global::Grpc.Health.V1.HealthCheckResponse>(
         MethodType.Unary,
         __ServiceName,
         "Check",
@@ -25,22 +25,22 @@ namespace Grpc.Health.V1Alpha {
     // service descriptor
     public static global::Google.Protobuf.Reflection.ServiceDescriptor Descriptor
     {
-      get { return global::Grpc.Health.V1Alpha.HealthReflection.Descriptor.Services[0]; }
+      get { return global::Grpc.Health.V1.HealthReflection.Descriptor.Services[0]; }
     }
 
     // client interface
     public interface IHealthClient
     {
-      global::Grpc.Health.V1Alpha.HealthCheckResponse Check(global::Grpc.Health.V1Alpha.HealthCheckRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken));
-      global::Grpc.Health.V1Alpha.HealthCheckResponse Check(global::Grpc.Health.V1Alpha.HealthCheckRequest request, CallOptions options);
-      AsyncUnaryCall<global::Grpc.Health.V1Alpha.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1Alpha.HealthCheckRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken));
-      AsyncUnaryCall<global::Grpc.Health.V1Alpha.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1Alpha.HealthCheckRequest request, CallOptions options);
+      global::Grpc.Health.V1.HealthCheckResponse Check(global::Grpc.Health.V1.HealthCheckRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken));
+      global::Grpc.Health.V1.HealthCheckResponse Check(global::Grpc.Health.V1.HealthCheckRequest request, CallOptions options);
+      AsyncUnaryCall<global::Grpc.Health.V1.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1.HealthCheckRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken));
+      AsyncUnaryCall<global::Grpc.Health.V1.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1.HealthCheckRequest request, CallOptions options);
     }
 
     // server-side interface
     public interface IHealth
     {
-      Task<global::Grpc.Health.V1Alpha.HealthCheckResponse> Check(global::Grpc.Health.V1Alpha.HealthCheckRequest request, ServerCallContext context);
+      Task<global::Grpc.Health.V1.HealthCheckResponse> Check(global::Grpc.Health.V1.HealthCheckRequest request, ServerCallContext context);
     }
 
     // client stub
@@ -49,22 +49,22 @@ namespace Grpc.Health.V1Alpha {
       public HealthClient(Channel channel) : base(channel)
       {
       }
-      public global::Grpc.Health.V1Alpha.HealthCheckResponse Check(global::Grpc.Health.V1Alpha.HealthCheckRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken))
+      public global::Grpc.Health.V1.HealthCheckResponse Check(global::Grpc.Health.V1.HealthCheckRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken))
       {
         var call = CreateCall(__Method_Check, new CallOptions(headers, deadline, cancellationToken));
         return Calls.BlockingUnaryCall(call, request);
       }
-      public global::Grpc.Health.V1Alpha.HealthCheckResponse Check(global::Grpc.Health.V1Alpha.HealthCheckRequest request, CallOptions options)
+      public global::Grpc.Health.V1.HealthCheckResponse Check(global::Grpc.Health.V1.HealthCheckRequest request, CallOptions options)
       {
         var call = CreateCall(__Method_Check, options);
         return Calls.BlockingUnaryCall(call, request);
       }
-      public AsyncUnaryCall<global::Grpc.Health.V1Alpha.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1Alpha.HealthCheckRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken))
+      public AsyncUnaryCall<global::Grpc.Health.V1.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1.HealthCheckRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken))
       {
         var call = CreateCall(__Method_Check, new CallOptions(headers, deadline, cancellationToken));
         return Calls.AsyncUnaryCall(call, request);
       }
-      public AsyncUnaryCall<global::Grpc.Health.V1Alpha.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1Alpha.HealthCheckRequest request, CallOptions options)
+      public AsyncUnaryCall<global::Grpc.Health.V1.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1.HealthCheckRequest request, CallOptions options)
       {
         var call = CreateCall(__Method_Check, options);
         return Calls.AsyncUnaryCall(call, request);
diff --git a/src/csharp/Grpc.HealthCheck/HealthServiceImpl.cs b/src/csharp/Grpc.HealthCheck/HealthServiceImpl.cs
index e2ad1a834bfd57c9943c369e8c7dd91e476f5802..21482b302b4dcc1659e5ea33cb2d08e52f0e1412 100644
--- a/src/csharp/Grpc.HealthCheck/HealthServiceImpl.cs
+++ b/src/csharp/Grpc.HealthCheck/HealthServiceImpl.cs
@@ -37,7 +37,7 @@ using System.Threading.Tasks;
 
 using Grpc.Core;
 using Grpc.Core.Utils;
-using Grpc.Health.V1Alpha;
+using Grpc.Health.V1;
 
 namespace Grpc.HealthCheck
 {
@@ -48,44 +48,42 @@ namespace Grpc.HealthCheck
     /// <code>
     /// var serviceImpl = new HealthServiceImpl();
     /// server = new Server();
-    /// server.AddServiceDefinition(Grpc.Health.V1Alpha.Health.BindService(serviceImpl));
+    /// server.AddServiceDefinition(Grpc.Health.V1.Health.BindService(serviceImpl));
     /// </code>
     /// </summary>
-    public class HealthServiceImpl : Grpc.Health.V1Alpha.Health.IHealth
+    public class HealthServiceImpl : Grpc.Health.V1.Health.IHealth
     {
         private readonly object myLock = new object();
-        private readonly Dictionary<Key, HealthCheckResponse.Types.ServingStatus> statusMap = 
-            new Dictionary<Key, HealthCheckResponse.Types.ServingStatus>();
+        private readonly Dictionary<string, HealthCheckResponse.Types.ServingStatus> statusMap = 
+            new Dictionary<string, HealthCheckResponse.Types.ServingStatus>();
 
         /// <summary>
-        /// Sets the health status for given host and service.
+        /// Sets the health status for given service.
         /// </summary>
-        /// <param name="host">The host. Cannot be null.</param>
         /// <param name="service">The service. Cannot be null.</param>
         /// <param name="status">the health status</param>
-        public void SetStatus(string host, string service, HealthCheckResponse.Types.ServingStatus status)
+        public void SetStatus(string service, HealthCheckResponse.Types.ServingStatus status)
         {
             lock (myLock)
             {
-                statusMap[CreateKey(host, service)] = status;
+                statusMap[service] = status;
             }
         }
 
         /// <summary>
-        /// Clears health status for given host and service.
+        /// Clears health status for given service.
         /// </summary>
-        /// <param name="host">The host. Cannot be null.</param>
         /// <param name="service">The service. Cannot be null.</param>
-        public void ClearStatus(string host, string service)
+        public void ClearStatus(string service)
         {
             lock (myLock)
             {
-                statusMap.Remove(CreateKey(host, service));
+                statusMap.Remove(service);
             }
         }
         
         /// <summary>
-        /// Clears statuses for all hosts and services.
+        /// Clears statuses for all services.
         /// </summary>
         public void ClearAll()
         {
@@ -105,11 +103,10 @@ namespace Grpc.HealthCheck
         {
             lock (myLock)
             {
-                var host = request.Host;
                 var service = request.Service;
 
                 HealthCheckResponse.Types.ServingStatus status;
-                if (!statusMap.TryGetValue(CreateKey(host, service), out status))
+                if (!statusMap.TryGetValue(service, out status))
                 {
                     // TODO(jtattermusch): returning specific status from server handler is not supported yet.
                     throw new RpcException(new Status(StatusCode.NotFound, ""));
@@ -117,22 +114,5 @@ namespace Grpc.HealthCheck
                 return Task.FromResult(new HealthCheckResponse { Status = status });
             }
         }
-
-        private static Key CreateKey(string host, string service)
-        {
-            return new Key(host, service);
-        }
-
-        private struct Key
-        {
-            public Key(string host, string service)
-            {
-                this.Host = GrpcPreconditions.CheckNotNull(host);
-                this.Service = GrpcPreconditions.CheckNotNull(service);
-            }
-
-            readonly string Host;
-            readonly string Service;
-        }
     }
 }
diff --git a/src/csharp/README.md b/src/csharp/README.md
index 65ae0b5efda3ea55d96de1e521a1b42904838129..b4fa945ac988e65a571e4229b87b14342a86204c 100644
--- a/src/csharp/README.md
+++ b/src/csharp/README.md
@@ -12,9 +12,9 @@ Beta
 PREREQUISITES
 --------------
 
-- Windows: .NET Framework 4.5+, Visual Studio 2013 or 2015.
-- Linux: Mono 3.2.8+, MonoDevelop 5.9 with NuGet add-in installed.
-- Mac OS X: [homebrew][], Xamarin Studio with NuGet add-in installed.
+- Windows: .NET Framework 4.5+, Visual Studio 2013 or 2015
+- Linux: Mono 4+, MonoDevelop 5.9+ (with NuGet add-in installed)
+- Mac OS X: Xamarin Studio 5.9+
 
 HOW TO USE
 --------------
@@ -24,66 +24,28 @@ HOW TO USE
 - Open Visual Studio and start a new project/solution.
 
 - Add NuGet package `Grpc` as a dependency (Project options -> Manage NuGet Packages).
-  That will also pull all the transitive dependencies (including the native libraries that
+  That will also pull all the transitive dependencies (including the gRPC native library that
   gRPC C# is using internally).
 
 **Linux (Debian)**
 
-- Add [Debian jessie-backports][] to your `sources.list` file. Example:
-
-  ```sh
-  echo "deb http://http.debian.net/debian jessie-backports main" | \
-  sudo tee -a /etc/apt/sources.list
-  ```
-
-- Install the gRPC Debian package
-
-  ```sh
-  sudo apt-get update
-  sudo apt-get install libgrpc0
-  ```
-
-- gRPC C# depends on native shared library `libgrpc_csharp_ext.so` (Unix flavor of grpc_csharp_ext.dll).
-  This library is not part of the base gRPC debian package and needs to be installed manually from
-  a `.deb` file. Download the debian package `libgrpc_csharp_ext` from corresponding gRPC release on GitHub
-  and install it using `dpkg`.
-
-  ```sh
-  # choose version corresponding to the version of libgrpc you've installed.
-  wget https://github.com/grpc/grpc/releases/download/release-0_11_0/libgrpc-csharp-ext0_0.11.0.0-1_amd64.deb
-  dpkg -i libgrpc-csharp-ext0_0.11.0.0-1_amd64.deb
-  ```
-
 - Open MonoDevelop and start a new project/solution.
 
 - Add NuGet package `Grpc` as a dependency (Project -> Add NuGet packages).
+  That will also pull all the transitive dependencies (including the gRPC native library that
+  gRPC C# is using internally).
 
-- NOTE: Currently, there are no debian packages for the latest version Protocol Buffers compiler (_protoc_)
-  and the gRPC _protoc_ plugin. You can install them using [gRPC Linuxbrew instructions][].
+- NOTE: gRPC C# doesn't have a good story yet for shipping precompiled Linux version of Protocol Buffers compiler (_protoc_) and the gRPC _protoc_ plugin. You can install them using [gRPC Linuxbrew instructions][].
 
 **Mac OS X**
 
-- WARNING: As of now gRPC C# only works on 64bit version of Mono (because we don't compile
-  the native extension for C# in 32bit mode yet). That means your development experience
-  with Xamarin Studio on MacOS will not be great, as you won't be able to run your
-  code directly from Xamarin Studio (which requires 32bit version of Mono).
-
-- Install [homebrew][]. Run the following command to install gRPC C# native dependencies.
-
-  ```sh
-  $ curl -fsSL https://goo.gl/getgrpc | bash -
-  ```
-  This will download and run the [gRPC install script][], then install the latest version of gRPC C core and native C# extension.
-  It also installs Protocol Buffers compiler (_protoc_) and the gRPC _protoc_ plugin for C#.
-
-- Install 64-bit version of mono with command `brew install mono`.
-
 - Open Xamarin Studio and start a new project/solution.
 
 - Add NuGet package `Grpc` as a dependency (Project -> Add NuGet packages).
+  That will also pull all the transitive dependencies (including the gRPC native library that
+  gRPC C# is using internally).
 
-- *You will be able to build your project in Xamarin Studio, but to run or test it,
-  you will need to run it under 64-bit version of Mono.*
+- NOTE: gRPC C# doesn't have a good story yet for shipping precompiled Mac OS X version of Protocol Buffers compiler (_protoc_) and the gRPC _protoc_ plugin. You can install them using [gRPC Homebrew instructions][].
 
 BUILD FROM SOURCE
 -----------------
@@ -94,7 +56,7 @@ If you are a user of gRPC C#, go to Usage section above.
 **Windows**
 
 - The grpc_csharp_ext native library needs to be built so you can build the gRPC C# solution. You can 
-  either build the native solution in `vsprojects/grpc.sln` from Visual Studio manually, or you can use
+  either build the native solution in `vsprojects/grpc_csharp_ext.sln` from Visual Studio manually, or you can use
   a convenience batch script that builds everything for you.
 
   ```
@@ -102,30 +64,28 @@ If you are a user of gRPC C#, go to Usage section above.
   > buildall.bat
   ```
 
-- Open Grpc.sln using Visual Studio. NuGet dependencies will be restored
-  upon build (you need to have NuGet add-in installed).
+- Open Grpc.sln using Visual Studio.
 
 **Linux**
 
+- The grpc_csharp_ext native library needs to be built so you can build the gRPC C# solution:
   ```sh
-  $ sudo apt-get install mono-devel
-  $ sudo apt-get install nunit nunit-console
+  # from the gRPC repository root
+  $ make CONFIG=dbg grpc_csharp_ext
   ```
 
-You can use older versions of MonoDevelop, but then you might need to restore
-NuGet dependencies manually (by `nuget restore`), because older versions of MonoDevelop
-don't support NuGet add-in.
+- Use MonoDevelop to open the solution Grpc.sln
+
+**Mac OS X**
 
-- Compile and install the gRPC C# extension library (that will be used via
-  P/Invoke from C#).
+- The grpc_csharp_ext native library needs to be built so you can build the gRPC C# solution.
+  
   ```sh
-  $ make grpc_csharp_ext
-  $ sudo make install_grpc_csharp_ext
+  # from the gRPC repository root
+  $ tools/run_tests/run_tests.py -c dbg -l csharp --build_only
   ```
 
-- Use MonoDevelop to open the solution Grpc.sln
-
-- Build the solution & run all the tests from test view.
+- Use Xamarin Studio to open the solution Grpc.sln
 
 RUNNING TESTS
 -------------
@@ -135,17 +95,9 @@ gRPC C# is using NUnit as the testing framework.
 Under Visual Studio, make sure NUnit test adapter is installed (under "Extensions and Updates").
 Then you should be able to run all the tests using Test Explorer.
 
-Under Monodevelop, make sure you installed "NUnit support" in Add-in manager.
+Under Monodevelop or Xamarin Studio, make sure you installed "NUnit support" in Add-in manager.
 Then you should be able to run all the test from the Test View.
 
-After building the solution, you can also run the tests from command line 
-using nunit-console tool.
-
-```sh
-# from Grpc.Core.Test/bin/Debug directory
-$ nunit-console Grpc.Core.Tests.dll
-```
-
 gRPC team uses a Python script to simplify facilitate running tests for
 different languages.
 
@@ -176,27 +128,15 @@ CONTENTS
 - Grpc.IntegrationTesting:
   Cross-language gRPC implementation testing (interop testing).
 
-TROUBLESHOOTING
+THE NATIVE DEPENDENCY
 ---------------
 
-### Problem: Unable to load DLL 'grpc_csharp_ext.dll'
-
-Internally, gRPC C# uses a native library written in C (gRPC C core) and invokes its functionality via P/Invoke. `grpc_csharp_ext` library is a native extension library that facilitates this by wrapping some C core API into a form that's more digestible for P/Invoke. If you get the above error, it means that the native dependencies could not be located by the C# runtime (or they are incompatible with the current runtime, so they could not be loaded). The solution to this is environment specific.
-
-- If you are developing on Windows in Visual Studio, the `grpc_csharp_ext.dll` that is shipped by gRPC nuget packages should be automatically copied to your build destination folder once you build. By adjusting project properties in your VS project file, you can influence which exact configuration of `grpc_csharp_ext.dll` will be used (based on VS version, bitness, debug/release configuration).
-
-- If you are running your application that is using gRPC on Windows machine that doesn't have Visual Studio installed, you might need to install [Visual C++ 2013 redistributable](https://www.microsoft.com/en-us/download/details.aspx?id=40784) that contains some system .dll libraries that `grpc_csharp_ext.dll` depends on (see #905 for more details).
-
-- On Linux (or Docker), you need to first install gRPC C core and `libgrpc_csharp_ext.so` shared libraries.
-  See [How to Use](#how-to-use) section for details how to install it.
-  Installation on a machine where your application is going to be deployed is no different.
-
-- On Mac, you need to first install gRPC C core and `libgrpc_csharp_ext.dylib` shared libraries using Homebrew. See above for installation instruction.
-  Installation on a machine where your application is going to be deployed is no different.
+Internally, gRPC C# uses a native library written in C (gRPC C core) and invokes its functionality via P/Invoke. `grpc_csharp_ext` library is a native extension library that facilitates this by wrapping some C core API into a form that's more digestible for P/Invoke.
 
-- Possible cause for the problem is that the `grpc_csharp_ext` library is installed, but it has different bitness (32/64bit) than your C# runtime (in case you are using mono) or C# application.
+Prior to version 0.13, installing `grpc_csharp_ext` was required to make gRPC work on Linux and MacOS. Starting with version 0.13, we have improved the packaging story significantly and precompiled versions of the native library for all supported platforms are now shipped with the NuGet package. Just installing the `Grpc` NuGet package should be the only step needed to use gRPC C#, regardless of your platform (Windows, Linux or Mac) and the bitness (32 or 64bit).
 
 [gRPC Linuxbrew instructions]:https://github.com/grpc/homebrew-grpc#quick-install-linux
+[gRPC Homebrew instructions]:https://github.com/grpc/homebrew-grpc#quick-install-linux
 [homebrew]:http://brew.sh
 [gRPC install script]:https://raw.githubusercontent.com/grpc/homebrew-grpc/master/scripts/install
 [grpc.io]: http://www.grpc.io/docs/installation/csharp.html
diff --git a/src/csharp/generate_proto_csharp.sh b/src/csharp/generate_proto_csharp.sh
index 0261a458af730dd3996a21e9f10d3e346fa68791..23e0540253a3ec226619959dbc8000a3bba741a1 100755
--- a/src/csharp/generate_proto_csharp.sh
+++ b/src/csharp/generate_proto_csharp.sh
@@ -42,7 +42,7 @@ $PROTOC --plugin=$PLUGIN --csharp_out=$EXAMPLES_DIR --grpc_out=$EXAMPLES_DIR \
     -I src/proto/math src/proto/math/math.proto
 
 $PROTOC --plugin=$PLUGIN --csharp_out=$HEALTHCHECK_DIR --grpc_out=$HEALTHCHECK_DIR \
-    -I src/proto/grpc/health/v1alpha src/proto/grpc/health/v1alpha/health.proto
+    -I src/proto/grpc/health/v1 src/proto/grpc/health/v1/health.proto
 
 $PROTOC --plugin=$PLUGIN --csharp_out=$TESTING_DIR --grpc_out=$TESTING_DIR \
     -I . src/proto/grpc/testing/{control,empty,messages,payloads,services,stats,test}.proto 
diff --git a/src/node/health_check/health.js b/src/node/health_check/health.js
index 1a2c0366875701b6b57cf52e0bbfabaf9137f2a2..6ab41571831b803f372fd7f32fd78a972d1ec2a3 100644
--- a/src/node/health_check/health.js
+++ b/src/node/health_check/health.js
@@ -1,6 +1,6 @@
 /*
  *
- * Copyright 2015, Google Inc.
+ * Copyright 2015-2016, Google Inc.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -38,9 +38,9 @@ var grpc = require('../');
 var _ = require('lodash');
 
 var health_proto = grpc.load(__dirname +
-    '/../../proto/grpc/health/v1alpha/health.proto');
+    '/../../proto/grpc/health/v1/health.proto');
 
-var HealthClient = health_proto.grpc.health.v1alpha.Health;
+var HealthClient = health_proto.grpc.health.v1.Health;
 
 function HealthImplementation(statusMap) {
   this.statusMap = _.clone(statusMap);
diff --git a/src/proto/grpc/health/v1alpha/health.proto b/src/proto/grpc/health/v1/health.proto
similarity index 93%
rename from src/proto/grpc/health/v1alpha/health.proto
rename to src/proto/grpc/health/v1/health.proto
index 05f837dd9904ad7f9ea043abe59e1866dec7a99d..6e27606d1b6fdb4f3e658e0ff4b07d21f1bbc017 100644
--- a/src/proto/grpc/health/v1alpha/health.proto
+++ b/src/proto/grpc/health/v1/health.proto
@@ -29,12 +29,11 @@
 
 syntax = "proto3";
 
-package grpc.health.v1alpha;
-option csharp_namespace = "Grpc.Health.V1Alpha";
+package grpc.health.v1;
+option csharp_namespace = "Grpc.Health.V1";
 
 message HealthCheckRequest {
-  string host = 1;
-  string service = 2;
+  string service = 1;
 }
 
 message HealthCheckResponse {
diff --git a/src/python/grpcio/precompiled.py b/src/python/grpcio/precompiled.py
index 05c651b506f9b5785a9125a77420eb733a8cf9a3..ae2a0c835a0786867c14bb5c8974cf06642adb97 100644
--- a/src/python/grpcio/precompiled.py
+++ b/src/python/grpcio/precompiled.py
@@ -100,3 +100,5 @@ def update_setup_arguments(setup_arguments):
     sys.stderr.write(
         'could not write precompiled extension to directory: {} -> {}\n'
             .format(url, target_path))
+    return
+  setup_arguments['package_data']['grpc._cython'].append('cygrpc.so')
diff --git a/src/python/grpcio_health_checking/grpc/health/v1alpha/__init__.py b/src/python/grpcio_health_checking/grpc/health/v1/__init__.py
similarity index 97%
rename from src/python/grpcio_health_checking/grpc/health/v1alpha/__init__.py
rename to src/python/grpcio_health_checking/grpc/health/v1/__init__.py
index 708651910607ffb686d781713f6893567821b9fd..13aac79160b8db0fd6863590a4d044464b72dbcc 100644
--- a/src/python/grpcio_health_checking/grpc/health/v1alpha/__init__.py
+++ b/src/python/grpcio_health_checking/grpc/health/v1/__init__.py
@@ -1,4 +1,4 @@
-# Copyright 2015, Google Inc.
+# Copyright 2015-2016, Google Inc.
 # All rights reserved.
 #
 # Redistribution and use in source and binary forms, with or without
diff --git a/src/python/grpcio_health_checking/grpc/health/v1alpha/health.proto b/src/python/grpcio_health_checking/grpc/health/v1/health.proto
similarity index 96%
rename from src/python/grpcio_health_checking/grpc/health/v1alpha/health.proto
rename to src/python/grpcio_health_checking/grpc/health/v1/health.proto
index 57f4aaa9c08d9bbc81aa755cf6b0b3efb76d8adb..de10719b6ced765117e2a4c5672af8a010fa2bd3 100644
--- a/src/python/grpcio_health_checking/grpc/health/v1alpha/health.proto
+++ b/src/python/grpcio_health_checking/grpc/health/v1/health.proto
@@ -1,4 +1,4 @@
-// Copyright 2015, Google Inc.
+// Copyright 2015-2016, Google Inc.
 // All rights reserved.
 //
 // Redistribution and use in source and binary forms, with or without
@@ -29,7 +29,7 @@
 
 syntax = "proto3";
 
-package grpc.health.v1alpha;
+package grpc.health.v1;
 
 message HealthCheckRequest {
   string service = 1;
diff --git a/src/python/grpcio_health_checking/grpc/health/v1alpha/health.py b/src/python/grpcio_health_checking/grpc/health/v1/health.py
similarity index 96%
rename from src/python/grpcio_health_checking/grpc/health/v1alpha/health.py
rename to src/python/grpcio_health_checking/grpc/health/v1/health.py
index 9dfcd962f06142a6f6f85dee8dde2338635d4c58..60cbd644330b2ac48126fed40c58768de087c007 100644
--- a/src/python/grpcio_health_checking/grpc/health/v1alpha/health.py
+++ b/src/python/grpcio_health_checking/grpc/health/v1/health.py
@@ -1,4 +1,4 @@
-# Copyright 2015, Google Inc.
+# Copyright 2015-2016, Google Inc.
 # All rights reserved.
 #
 # Redistribution and use in source and binary forms, with or without
@@ -33,7 +33,7 @@ import abc
 import enum
 import threading
 
-from grpc.health.v1alpha import health_pb2
+from grpc.health.v1 import health_pb2
 
 
 @enum.unique
@@ -64,7 +64,7 @@ class _HealthServicer(health_pb2.EarlyAdopterHealthServicer):
 
   def set(service, status):
     if not isinstance(status, HealthStatus):
-      raise TypeError('expected grpc.health.v1alpha.health.HealthStatus '
+      raise TypeError('expected grpc.health.v1.health.HealthStatus '
                       'for argument `status` but got {}'.format(status))
     with self._server_status_lock:
       self._server_status[service] = status
diff --git a/src/ruby/.rubocop.yml b/src/ruby/.rubocop.yml
index dd57ab60828bc0bf6902ae6ef571992feb4f957d..ff5cf8db83190a6fab07d6c37cbf4f626a2fb29e 100644
--- a/src/ruby/.rubocop.yml
+++ b/src/ruby/.rubocop.yml
@@ -7,7 +7,7 @@ AllCops:
     - 'bin/apis/**/*'
     - 'bin/math.rb'
     - 'bin/math_services.rb'
-    - 'pb/grpc/health/v1alpha/*'
+    - 'pb/grpc/health/v1/*'
     - 'pb/test/**/*'
 
 Metrics/CyclomaticComplexity:
diff --git a/src/ruby/ext/grpc/rb_grpc.c b/src/ruby/ext/grpc/rb_grpc.c
index eefdb93d6734b7c30afdca549301f0e0cdce2822..0f9b18fa212a44278d80222f653bc59f483d44d1 100644
--- a/src/ruby/ext/grpc/rb_grpc.c
+++ b/src/ruby/ext/grpc/rb_grpc.c
@@ -269,20 +269,9 @@ static void Init_grpc_time_consts() {
   id_tv_nsec = rb_intern("tv_nsec");
 }
 
-/*
-   TODO: find an alternative to ruby_vm_at_exit that is ok in Ruby 2.0 where
-   RUBY_TYPED_FREE_IMMEDIATELY is not defined.
-
-   At the moment, registering a function using ruby_vm_at_exit segfaults in Ruby
-   2.0.  This is not an issue with the gRPC handler.  More likely, this was an
-   in issue with 2.0 that got resolved in 2.1 and has not been backported.
-*/
-#ifdef RUBY_TYPED_FREE_IMMEDIATELY
-static void grpc_rb_shutdown(ruby_vm_t *vm) {
-  (void)vm;
+static void grpc_rb_shutdown(void) {
   grpc_shutdown();
 }
-#endif
 
 /* Initialize the GRPC module structs */
 
@@ -300,18 +289,30 @@ VALUE sym_code = Qundef;
 VALUE sym_details = Qundef;
 VALUE sym_metadata = Qundef;
 
+static gpr_once g_once_init = GPR_ONCE_INIT;
+
+static void grpc_ruby_once_init() {
+  grpc_init();
+  atexit(grpc_rb_shutdown);
+}
+
 void Init_grpc_c() {
   if (!grpc_rb_load_core()) {
     rb_raise(rb_eLoadError, "Couldn't find or load gRPC's dynamic C core");
     return;
   }
 
-  grpc_init();
-
-/* TODO: find alternative to ruby_vm_at_exit that is ok in Ruby 2.0 */
-#ifdef RUBY_TYPED_FREE_IMMEDIATELY
-  ruby_vm_at_exit(grpc_rb_shutdown);
-#endif
+  /* ruby_vm_at_exit doesn't seem to be working. It would crash once every
+   * blue moon, and some users are getting it repeatedly. See the discussions
+   *  - https://github.com/grpc/grpc/pull/5337
+   *  - https://bugs.ruby-lang.org/issues/12095
+   *
+   * In order to still be able to handle the (unlikely) situation where the
+   * extension is loaded by a first Ruby VM that is subsequently destroyed,
+   * then loaded again by another VM within the same process, we need to
+   * schedule our initialization and destruction only once.
+   */
+  gpr_once_init(&g_once_init, grpc_ruby_once_init);
 
   grpc_rb_mGRPC = rb_define_module("GRPC");
   grpc_rb_mGrpcCore = rb_define_module_under(grpc_rb_mGRPC, "Core");
diff --git a/src/ruby/lib/grpc/core/time_consts.rb b/src/ruby/lib/grpc/core/time_consts.rb
index e6dae7b08a065c9999dec3bbbe3a33a4f3521d19..c8eae7806b349b78affbcb279cc46210740d4c44 100644
--- a/src/ruby/lib/grpc/core/time_consts.rb
+++ b/src/ruby/lib/grpc/core/time_consts.rb
@@ -1,4 +1,4 @@
-# Copyright 2015, Google Inc.
+# Copyright 2015-2016, Google Inc.
 # All rights reserved.
 #
 # Redistribution and use in source and binary forms, with or without
@@ -27,7 +27,7 @@
 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
 # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 
-require 'grpc'
+require 'grpc/grpc'
 
 # GRPC contains the General RPC module.
 module GRPC
diff --git a/src/ruby/lib/grpc/errors.rb b/src/ruby/lib/grpc/errors.rb
index f1201c17040737c350552aad505ea2fca455bd5f..2227ee1f12b503d3ee92b89e11ad042412cda5c4 100644
--- a/src/ruby/lib/grpc/errors.rb
+++ b/src/ruby/lib/grpc/errors.rb
@@ -1,4 +1,4 @@
-# Copyright 2015, Google Inc.
+# Copyright 2015-2016, Google Inc.
 # All rights reserved.
 #
 # Redistribution and use in source and binary forms, with or without
@@ -27,7 +27,7 @@
 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
 # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 
-require 'grpc'
+require 'grpc/grpc'
 
 # GRPC contains the General RPC module.
 module GRPC
diff --git a/src/ruby/pb/README.md b/src/ruby/pb/README.md
index e04aef185caaa51720922dbd73e02c82da147450..d9e30bbc854434947bb9560d4115d448170ef64a 100644
--- a/src/ruby/pb/README.md
+++ b/src/ruby/pb/README.md
@@ -11,7 +11,7 @@ The code is is generated using the protoc (> 3.0.0.alpha.1) and the
 grpc_ruby_plugin.  These must be installed to regenerate the IDL defined
 classes, but that's not necessary just to use them.
 
-health_check/v1alpha
+health_check/v1
 --------------------
 
 This package defines the surface of a simple health check service that gRPC
@@ -20,7 +20,7 @@ re-generate the surface.
 
 ```bash
 $ # (from this directory)
-$ protoc -I ../../proto ../../proto/grpc/health/v1alpha/health.proto \
+$ protoc -I ../../proto ../../proto/grpc/health/v1/health.proto \
     --grpc_out=. \
     --ruby_out=. \
     --plugin=protoc-gen-grpc=`which grpc_ruby_plugin`
diff --git a/src/ruby/pb/generate_proto_ruby.sh b/src/ruby/pb/generate_proto_ruby.sh
index 576b1c08d300f0a1bf97388a38ae71e18b91524f..86c082099d98304859e4ab55f5a6512b0116f8ab 100755
--- a/src/ruby/pb/generate_proto_ruby.sh
+++ b/src/ruby/pb/generate_proto_ruby.sh
@@ -1,5 +1,5 @@
 #!/bin/sh
-# Copyright 2015, Google Inc.
+# Copyright 2015-2016, Google Inc.
 # All rights reserved.
 #
 # Redistribution and use in source and binary forms, with or without
@@ -35,7 +35,7 @@ cd $(dirname $0)/../../..
 PROTOC=bins/opt/protobuf/protoc
 PLUGIN=protoc-gen-grpc=bins/opt/grpc_ruby_plugin
 
-$PROTOC -I src/proto src/proto/grpc/health/v1alpha/health.proto \
+$PROTOC -I src/proto src/proto/grpc/health/v1/health.proto \
     --grpc_out=src/ruby/pb \
     --ruby_out=src/ruby/pb \
     --plugin=$PLUGIN
diff --git a/src/ruby/pb/grpc/health/checker.rb b/src/ruby/pb/grpc/health/checker.rb
index 8c692e74f900bbc78b15685e4df41274f358a8ba..9f1ee65c41935164c322cde79e7412265010df0e 100644
--- a/src/ruby/pb/grpc/health/checker.rb
+++ b/src/ruby/pb/grpc/health/checker.rb
@@ -1,4 +1,4 @@
-# Copyright 2015, Google Inc.
+# Copyright 2015-2016, Google Inc.
 # All rights reserved.
 #
 # Redistribution and use in source and binary forms, with or without
@@ -28,7 +28,7 @@
 # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 
 require 'grpc'
-require 'grpc/health/v1alpha/health_services'
+require 'grpc/health/v1/health_services'
 require 'thread'
 
 module Grpc
@@ -36,9 +36,9 @@ module Grpc
   # service.
   module Health
     # Checker is implementation of the schema-specified health checking service.
-    class Checker < V1alpha::Health::Service
+    class Checker < V1::Health::Service
       StatusCodes = GRPC::Core::StatusCodes
-      HealthCheckResponse = V1alpha::HealthCheckResponse
+      HealthCheckResponse = V1::HealthCheckResponse
 
       # Initializes the statuses of participating services
       def initialize
@@ -50,20 +50,20 @@ module Grpc
       def check(req, _call)
         status = nil
         @status_mutex.synchronize do
-          status = @statuses["#{req.host}/#{req.service}"]
+          status = @statuses["#{req.service}"]
         end
         fail GRPC::BadStatus, StatusCodes::NOT_FOUND if status.nil?
         HealthCheckResponse.new(status: status)
       end
 
-      # Adds the health status for a given host and service.
-      def add_status(host, service, status)
-        @status_mutex.synchronize { @statuses["#{host}/#{service}"] = status }
+      # Adds the health status for a given service.
+      def add_status(service, status)
+        @status_mutex.synchronize { @statuses["#{service}"] = status }
       end
 
-      # Clears the status for the given host or service.
-      def clear_status(host, service)
-        @status_mutex.synchronize { @statuses.delete("#{host}/#{service}") }
+      # Clears the status for the given service.
+      def clear_status(service)
+        @status_mutex.synchronize { @statuses.delete("#{service}") }
       end
 
       # Clears alls the statuses.
diff --git a/src/ruby/pb/grpc/health/v1/health.rb b/src/ruby/pb/grpc/health/v1/health.rb
new file mode 100644
index 0000000000000000000000000000000000000000..aa87a93918b123f6af2f91f58fc7f004b91481b0
--- /dev/null
+++ b/src/ruby/pb/grpc/health/v1/health.rb
@@ -0,0 +1,28 @@
+# Generated by the protocol buffer compiler.  DO NOT EDIT!
+# source: grpc/health/v1/health.proto
+
+require 'google/protobuf'
+
+Google::Protobuf::DescriptorPool.generated_pool.build do
+  add_message "grpc.health.v1.HealthCheckRequest" do
+    optional :service, :string, 1
+  end
+  add_message "grpc.health.v1.HealthCheckResponse" do
+    optional :status, :enum, 1, "grpc.health.v1.HealthCheckResponse.ServingStatus"
+  end
+  add_enum "grpc.health.v1.HealthCheckResponse.ServingStatus" do
+    value :UNKNOWN, 0
+    value :SERVING, 1
+    value :NOT_SERVING, 2
+  end
+end
+
+module Grpc
+  module Health
+    module V1
+      HealthCheckRequest = Google::Protobuf::DescriptorPool.generated_pool.lookup("grpc.health.v1.HealthCheckRequest").msgclass
+      HealthCheckResponse = Google::Protobuf::DescriptorPool.generated_pool.lookup("grpc.health.v1.HealthCheckResponse").msgclass
+      HealthCheckResponse::ServingStatus = Google::Protobuf::DescriptorPool.generated_pool.lookup("grpc.health.v1.HealthCheckResponse.ServingStatus").enummodule
+    end
+  end
+end
diff --git a/src/ruby/pb/grpc/health/v1alpha/health_services.rb b/src/ruby/pb/grpc/health/v1/health_services.rb
similarity index 71%
rename from src/ruby/pb/grpc/health/v1alpha/health_services.rb
rename to src/ruby/pb/grpc/health/v1/health_services.rb
index d5cba2e9ec71c22555c3ebb7c4f739e6bb3c6ed8..cb79b20437f573b40f9c3f6265eec722db4e87c7 100644
--- a/src/ruby/pb/grpc/health/v1alpha/health_services.rb
+++ b/src/ruby/pb/grpc/health/v1/health_services.rb
@@ -1,12 +1,12 @@
 # Generated by the protocol buffer compiler.  DO NOT EDIT!
-# Source: grpc/health/v1alpha/health.proto for package 'grpc.health.v1alpha'
+# Source: grpc/health/v1/health.proto for package 'grpc.health.v1'
 
 require 'grpc'
-require 'grpc/health/v1alpha/health'
+require 'grpc/health/v1/health'
 
 module Grpc
   module Health
-    module V1alpha
+    module V1
       module Health
 
         # TODO: add proto service documentation here
@@ -16,7 +16,7 @@ module Grpc
 
           self.marshal_class_method = :encode
           self.unmarshal_class_method = :decode
-          self.service_name = 'grpc.health.v1alpha.Health'
+          self.service_name = 'grpc.health.v1.Health'
 
           rpc :Check, HealthCheckRequest, HealthCheckResponse
         end
diff --git a/src/ruby/pb/grpc/health/v1alpha/health.rb b/src/ruby/pb/grpc/health/v1alpha/health.rb
deleted file mode 100644
index 9c04298ea54394cda76b9953b15bfae08755f8ce..0000000000000000000000000000000000000000
--- a/src/ruby/pb/grpc/health/v1alpha/health.rb
+++ /dev/null
@@ -1,29 +0,0 @@
-# Generated by the protocol buffer compiler.  DO NOT EDIT!
-# source: grpc/health/v1alpha/health.proto
-
-require 'google/protobuf'
-
-Google::Protobuf::DescriptorPool.generated_pool.build do
-  add_message "grpc.health.v1alpha.HealthCheckRequest" do
-    optional :host, :string, 1
-    optional :service, :string, 2
-  end
-  add_message "grpc.health.v1alpha.HealthCheckResponse" do
-    optional :status, :enum, 1, "grpc.health.v1alpha.HealthCheckResponse.ServingStatus"
-  end
-  add_enum "grpc.health.v1alpha.HealthCheckResponse.ServingStatus" do
-    value :UNKNOWN, 0
-    value :SERVING, 1
-    value :NOT_SERVING, 2
-  end
-end
-
-module Grpc
-  module Health
-    module V1alpha
-      HealthCheckRequest = Google::Protobuf::DescriptorPool.generated_pool.lookup("grpc.health.v1alpha.HealthCheckRequest").msgclass
-      HealthCheckResponse = Google::Protobuf::DescriptorPool.generated_pool.lookup("grpc.health.v1alpha.HealthCheckResponse").msgclass
-      HealthCheckResponse::ServingStatus = Google::Protobuf::DescriptorPool.generated_pool.lookup("grpc.health.v1alpha.HealthCheckResponse.ServingStatus").enummodule
-    end
-  end
-end
diff --git a/src/ruby/spec/pb/health/checker_spec.rb b/src/ruby/spec/pb/health/checker_spec.rb
index c1decd822a76062a58ea9dda0e83a18ec7776590..9bb79bb4cae057c8a5ebab92467570d570076e2d 100644
--- a/src/ruby/spec/pb/health/checker_spec.rb
+++ b/src/ruby/spec/pb/health/checker_spec.rb
@@ -28,7 +28,7 @@
 # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 
 require 'grpc'
-require 'grpc/health/v1alpha/health'
+require 'grpc/health/v1/health'
 require 'grpc/health/checker'
 require 'open3'
 require 'tmpdir'
@@ -43,7 +43,7 @@ describe 'Health protobuf code generation' do
       skip 'protoc || grpc_ruby_plugin missing, cannot verify health code-gen'
     else
       it 'should already be loaded indirectly i.e, used by the other specs' do
-        expect(require('grpc/health/v1alpha/health_services')).to be(false)
+        expect(require('grpc/health/v1/health_services')).to be(false)
       end
 
       it 'should have the same content as created by code generation' do
@@ -52,7 +52,7 @@ describe 'Health protobuf code generation' do
 
         # Get the current content
         service_path = File.join(root_dir, 'ruby', 'pb', 'grpc',
-                                 'health', 'v1alpha', 'health_services.rb')
+                                 'health', 'v1', 'health_services.rb')
         want = nil
         File.open(service_path) { |f| want = f.read }
 
@@ -61,12 +61,12 @@ describe 'Health protobuf code generation' do
         plugin = plugin.strip
         got = nil
         Dir.mktmpdir do |tmp_dir|
-          gen_out = File.join(tmp_dir, 'grpc', 'health', 'v1alpha',
+          gen_out = File.join(tmp_dir, 'grpc', 'health', 'v1',
                               'health_services.rb')
           pid = spawn(
             'protoc',
             '-I.',
-            'grpc/health/v1alpha/health.proto',
+            'grpc/health/v1/health.proto',
             "--grpc_out=#{tmp_dir}",
             "--plugin=protoc-gen-grpc=#{plugin}",
             chdir: pb_dir)
@@ -81,27 +81,17 @@ end
 
 describe Grpc::Health::Checker do
   StatusCodes = GRPC::Core::StatusCodes
-  ServingStatus = Grpc::Health::V1alpha::HealthCheckResponse::ServingStatus
-  HCResp = Grpc::Health::V1alpha::HealthCheckResponse
-  HCReq = Grpc::Health::V1alpha::HealthCheckRequest
+  ServingStatus = Grpc::Health::V1::HealthCheckResponse::ServingStatus
+  HCResp = Grpc::Health::V1::HealthCheckResponse
+  HCReq = Grpc::Health::V1::HealthCheckRequest
   success_tests =
     [
       {
-        desc: 'neither host or service are specified',
-        host: '',
+        desc: 'the service is not specified',
         service: ''
       }, {
-        desc: 'only the host is specified',
-        host: 'test-fake-host',
-        service: ''
-      }, {
-        desc: 'the host and service are specified',
-        host: 'test-fake-host',
+        desc: 'the service is specified',
         service: 'fake-service-1'
-      }, {
-        desc: 'only the service is specified',
-        host: '',
-        service: 'fake-service-2'
       }
     ]
 
@@ -114,9 +104,8 @@ describe Grpc::Health::Checker do
   context 'method `add_status` and `check`' do
     success_tests.each do |t|
       it "should succeed when #{t[:desc]}" do
-        subject.add_status(t[:host], t[:service], ServingStatus::NOT_SERVING)
-        got = subject.check(HCReq.new(host: t[:host], service: t[:service]),
-                            nil)
+        subject.add_status(t[:service], ServingStatus::NOT_SERVING)
+        got = subject.check(HCReq.new(service: t[:service]), nil)
         want = HCResp.new(status: ServingStatus::NOT_SERVING)
         expect(got).to eq(want)
       end
@@ -127,7 +116,7 @@ describe Grpc::Health::Checker do
     success_tests.each do |t|
       it "should fail with NOT_FOUND when #{t[:desc]}" do
         blk = proc do
-          subject.check(HCReq.new(host: t[:host], service: t[:service]), nil)
+          subject.check(HCReq.new(service: t[:service]), nil)
         end
         expected_msg = /#{StatusCodes::NOT_FOUND}/
         expect(&blk).to raise_error GRPC::BadStatus, expected_msg
@@ -138,16 +127,14 @@ describe Grpc::Health::Checker do
   context 'method `clear_status`' do
     success_tests.each do |t|
       it "should fail after clearing status when #{t[:desc]}" do
-        subject.add_status(t[:host], t[:service], ServingStatus::NOT_SERVING)
-        got = subject.check(HCReq.new(host: t[:host], service: t[:service]),
-                            nil)
+        subject.add_status(t[:service], ServingStatus::NOT_SERVING)
+        got = subject.check(HCReq.new(service: t[:service]), nil)
         want = HCResp.new(status: ServingStatus::NOT_SERVING)
         expect(got).to eq(want)
 
-        subject.clear_status(t[:host], t[:service])
+        subject.clear_status(t[:service])
         blk = proc do
-          subject.check(HCReq.new(host: t[:host], service: t[:service]),
-                        nil)
+          subject.check(HCReq.new(service: t[:service]), nil)
         end
         expected_msg = /#{StatusCodes::NOT_FOUND}/
         expect(&blk).to raise_error GRPC::BadStatus, expected_msg
@@ -158,9 +145,8 @@ describe Grpc::Health::Checker do
   context 'method `clear_all`' do
     it 'should return NOT_FOUND after being invoked' do
       success_tests.each do |t|
-        subject.add_status(t[:host], t[:service], ServingStatus::NOT_SERVING)
-        got = subject.check(HCReq.new(host: t[:host], service: t[:service]),
-                            nil)
+        subject.add_status(t[:service], ServingStatus::NOT_SERVING)
+        got = subject.check(HCReq.new(service: t[:service]), nil)
         want = HCResp.new(status: ServingStatus::NOT_SERVING)
         expect(got).to eq(want)
       end
@@ -169,7 +155,7 @@ describe Grpc::Health::Checker do
 
       success_tests.each do |t|
         blk = proc do
-          subject.check(HCReq.new(host: t[:host], service: t[:service]), nil)
+          subject.check(HCReq.new(service: t[:service]), nil)
         end
         expected_msg = /#{StatusCodes::NOT_FOUND}/
         expect(&blk).to raise_error GRPC::BadStatus, expected_msg
@@ -203,7 +189,7 @@ describe Grpc::Health::Checker do
 
     it 'should receive the correct status', server: true do
       @srv.handle(subject)
-      subject.add_status('', '', ServingStatus::NOT_SERVING)
+      subject.add_status('', ServingStatus::NOT_SERVING)
       t = Thread.new { @srv.run }
       @srv.wait_till_running
 
@@ -221,7 +207,7 @@ describe Grpc::Health::Checker do
       @srv.wait_till_running
       blk = proc do
         stub = CheckerStub.new(@host, :this_channel_is_insecure, **@client_opts)
-        stub.check(HCReq.new(host: 'unknown', service: 'unknown'))
+        stub.check(HCReq.new(service: 'unknown'))
       end
       expected_msg = /#{StatusCodes::NOT_FOUND}/
       expect(&blk).to raise_error GRPC::BadStatus, expected_msg
diff --git a/templates/config.m4.template b/templates/config.m4.template
index dbc12188dc00cd65525f429f566848b920deb6b8..5847d456f51c89c941065e04344f86ce0a2f4469 100644
--- a/templates/config.m4.template
+++ b/templates/config.m4.template
@@ -38,7 +38,22 @@
       % endfor
       % endif
       % endfor
-      , $ext_shared, , -Wall -Werror -std=c11 ${"\\"}
+      , $ext_shared, , -Wall -Werror ${"\\"}
+      -Wno-parentheses-equality -Wno-unused-value -std=c11 ${"\\"}
       -fvisibility=hidden -DOPENSSL_NO_ASM -D_GNU_SOURCE -DWIN32_LEAN_AND_MEAN ${"\\"}
       -D_HAS_EXCEPTIONS=0 -DNOMINMAX)
+
+    PHP_ADD_BUILD_DIR($ext_builddir/src/php/ext/grpc)
+  <%
+    dirs = {}
+    for lib in libs:
+      if lib.name in php_config_m4.get('deps', []):
+        for source in lib.src:
+          dirs[source[:source.rfind('/')]] = 1
+    dirs = dirs.keys()
+    dirs.sort()
+  %>
+    % for dir in dirs:
+    PHP_ADD_BUILD_DIR($ext_builddir/${dir})
+    % endfor
   fi
diff --git a/templates/package.xml.template b/templates/package.xml.template
index 455b002e64a0a4788943c13667391b02696172c9..067c8839d5a849f20c14a0919f53ab00217b3793 100644
--- a/templates/package.xml.template
+++ b/templates/package.xml.template
@@ -12,7 +12,7 @@
     <email>grpc-packages@google.com</email>
     <active>yes</active>
    </lead>
-   <%! from time import strftime %><date>${"%Y-%m-%d" | strftime}</date>
+   <date>2016-02-24</date>
    <time>16:06:07</time>
    <version>
     <release>0.8.0</release>
@@ -149,7 +149,7 @@
       <release>beta</release>
       <api>beta</api>
      </stability>
-     <date>${"%Y-%m-%d" | strftime}</date>
+     <date>2016-02-24</date>
      <license>BSD</license>
      <notes>
   - Simplify gRPC PHP installation #4517
diff --git a/templates/tools/run_tests/tests.json.template b/templates/tools/run_tests/tests.json.template
index 9a84783467ac3abe4b70e5ee301e98214234a4ab..5690874415a585fa70fbc557e7fc2e5070082cf2 100644
--- a/templates/tools/run_tests/tests.json.template
+++ b/templates/tools/run_tests/tests.json.template
@@ -3,11 +3,12 @@
   <%!
   import json
   %>
-  
+
   ${json.dumps([{"name": tgt.name,
                  "language": tgt.language,
                  "platforms": tgt.platforms,
                  "ci_platforms": tgt.ci_platforms,
+                 "gtest": tgt.gtest,
                  "exclude_configs": tgt.get("exclude_configs", []),
                  "args": [],
                  "flaky": tgt.flaky,
diff --git a/test/core/end2end/fixtures/h2_uchannel.c b/test/core/end2end/fixtures/h2_uchannel.c
index ec1e5f428072d6857130f5d44f47008464e67131..87bbd64d09a937b66ab8637647e4b1445a2f16a8 100644
--- a/test/core/end2end/fixtures/h2_uchannel.c
+++ b/test/core/end2end/fixtures/h2_uchannel.c
@@ -253,8 +253,7 @@ static void destroy_pollset(grpc_exec_ctx *exec_ctx, void *arg, bool success) {
 }
 
 static grpc_connected_subchannel *connect_subchannel(grpc_subchannel *c) {
-  gpr_mu mu;
-  gpr_mu_init(&mu);
+  gpr_mu *mu;
   grpc_pollset *pollset = gpr_malloc(grpc_pollset_size());
   grpc_exec_ctx exec_ctx = GRPC_EXEC_CTX_INIT;
   grpc_pollset_init(pollset, &mu);
@@ -264,22 +263,21 @@ static grpc_connected_subchannel *connect_subchannel(grpc_subchannel *c) {
                                          &g_state,
                                          grpc_closure_create(state_changed, c));
   grpc_exec_ctx_flush(&exec_ctx);
-  gpr_mu_lock(&mu);
+  gpr_mu_lock(mu);
   while (g_state != GRPC_CHANNEL_READY) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, pollset, &worker, gpr_now(GPR_CLOCK_MONOTONIC),
                       GRPC_TIMEOUT_SECONDS_TO_DEADLINE(1));
-    gpr_mu_unlock(&mu);
+    gpr_mu_unlock(mu);
     grpc_exec_ctx_flush(&exec_ctx);
-    gpr_mu_lock(&mu);
+    gpr_mu_lock(mu);
   }
   grpc_pollset_shutdown(&exec_ctx, pollset,
                         grpc_closure_create(destroy_pollset, pollset));
   grpc_pollset_set_destroy(g_interested_parties);
-  gpr_mu_unlock(&mu);
+  gpr_mu_unlock(mu);
   grpc_exec_ctx_finish(&exec_ctx);
   gpr_free(pollset);
-  gpr_mu_destroy(&mu);
   return grpc_subchannel_get_connected_subchannel(c);
 }
 
diff --git a/test/core/httpcli/httpcli_test.c b/test/core/httpcli/httpcli_test.c
index cfa1829214941a1c347d4a8ceb0358a98514bd42..da1463329d4c731495a64351a4d19e860f2467b4 100644
--- a/test/core/httpcli/httpcli_test.c
+++ b/test/core/httpcli/httpcli_test.c
@@ -47,7 +47,7 @@
 
 static int g_done = 0;
 static grpc_httpcli_context g_context;
-static gpr_mu g_mu;
+static gpr_mu *g_mu;
 static grpc_pollset *g_pollset;
 
 static gpr_timespec n_seconds_time(int seconds) {
@@ -64,10 +64,10 @@ static void on_finish(grpc_exec_ctx *exec_ctx, void *arg,
   GPR_ASSERT(response->status == 200);
   GPR_ASSERT(response->body_length == strlen(expect));
   GPR_ASSERT(0 == memcmp(expect, response->body, response->body_length));
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   g_done = 1;
   grpc_pollset_kick(g_pollset, NULL);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 static void test_get(int port) {
@@ -88,16 +88,16 @@ static void test_get(int port) {
 
   grpc_httpcli_get(&exec_ctx, &g_context, g_pollset, &req, n_seconds_time(15),
                    on_finish, (void *)42);
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (!g_done) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC), n_seconds_time(20));
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
   gpr_free(host);
 }
 
@@ -119,16 +119,16 @@ static void test_post(int port) {
 
   grpc_httpcli_post(&exec_ctx, &g_context, g_pollset, &req, "hello", 5,
                     n_seconds_time(15), on_finish, (void *)42);
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (!g_done) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC), n_seconds_time(20));
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
   gpr_free(host);
 }
 
@@ -177,7 +177,6 @@ int main(int argc, char **argv) {
   grpc_init();
   grpc_httpcli_context_init(&g_context);
   g_pollset = gpr_malloc(grpc_pollset_size());
-  gpr_mu_init(&g_mu);
   grpc_pollset_init(g_pollset, &g_mu);
 
   test_get(port);
@@ -189,7 +188,6 @@ int main(int argc, char **argv) {
   grpc_exec_ctx_finish(&exec_ctx);
   grpc_shutdown();
 
-  gpr_mu_destroy(&g_mu);
   gpr_free(g_pollset);
 
   gpr_subprocess_destroy(server);
diff --git a/test/core/httpcli/httpscli_test.c b/test/core/httpcli/httpscli_test.c
index b12f9472b152a3bfeae66e69d31421c203a6088a..7f765bc614f2682c876acd03d83841b76eb19938 100644
--- a/test/core/httpcli/httpscli_test.c
+++ b/test/core/httpcli/httpscli_test.c
@@ -47,7 +47,7 @@
 
 static int g_done = 0;
 static grpc_httpcli_context g_context;
-static gpr_mu g_mu;
+static gpr_mu *g_mu;
 static grpc_pollset *g_pollset;
 
 static gpr_timespec n_seconds_time(int seconds) {
@@ -64,10 +64,10 @@ static void on_finish(grpc_exec_ctx *exec_ctx, void *arg,
   GPR_ASSERT(response->status == 200);
   GPR_ASSERT(response->body_length == strlen(expect));
   GPR_ASSERT(0 == memcmp(expect, response->body, response->body_length));
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   g_done = 1;
   grpc_pollset_kick(g_pollset, NULL);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 static void test_get(int port) {
@@ -89,16 +89,16 @@ static void test_get(int port) {
 
   grpc_httpcli_get(&exec_ctx, &g_context, g_pollset, &req, n_seconds_time(15),
                    on_finish, (void *)42);
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (!g_done) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC), n_seconds_time(20));
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
   gpr_free(host);
 }
 
@@ -121,16 +121,16 @@ static void test_post(int port) {
 
   grpc_httpcli_post(&exec_ctx, &g_context, g_pollset, &req, "hello", 5,
                     n_seconds_time(15), on_finish, (void *)42);
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (!g_done) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC), n_seconds_time(20));
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
   gpr_free(host);
 }
 
@@ -192,7 +192,6 @@ int main(int argc, char **argv) {
   grpc_shutdown();
 
   gpr_free(g_pollset);
-  gpr_mu_destroy(&g_mu);
 
   gpr_subprocess_destroy(server);
 
diff --git a/test/core/iomgr/endpoint_pair_test.c b/test/core/iomgr/endpoint_pair_test.c
index c02e41493591de4faf81734a08f5b2bc1df426c3..c3a91088a5737e0ab239841afd1fc9321c35a9cc 100644
--- a/test/core/iomgr/endpoint_pair_test.c
+++ b/test/core/iomgr/endpoint_pair_test.c
@@ -42,7 +42,7 @@
 #include "test/core/iomgr/endpoint_tests.h"
 #include "test/core/util/test_config.h"
 
-static gpr_mu g_mu;
+static gpr_mu *g_mu;
 static grpc_pollset *g_pollset;
 
 static void clean_up(void) {}
@@ -73,17 +73,15 @@ static void destroy_pollset(grpc_exec_ctx *exec_ctx, void *p, bool success) {
 int main(int argc, char **argv) {
   grpc_closure destroyed;
   grpc_exec_ctx exec_ctx = GRPC_EXEC_CTX_INIT;
-  gpr_mu_init(&g_mu);
   grpc_test_init(argc, argv);
   grpc_init();
   g_pollset = gpr_malloc(grpc_pollset_size());
   grpc_pollset_init(g_pollset, &g_mu);
-  grpc_endpoint_tests(configs[0], g_pollset, &g_mu);
+  grpc_endpoint_tests(configs[0], g_pollset, g_mu);
   grpc_closure_init(&destroyed, destroy_pollset, g_pollset);
   grpc_pollset_shutdown(&exec_ctx, g_pollset, &destroyed);
   grpc_exec_ctx_finish(&exec_ctx);
   grpc_shutdown();
-  gpr_mu_destroy(&g_mu);
   gpr_free(g_pollset);
 
   return 0;
diff --git a/test/core/iomgr/fd_posix_test.c b/test/core/iomgr/fd_posix_test.c
index 9e00f8a43ef03bfd2258cdb9c905fc0788861358..8c64a2e787b68e251efe9121dfb684c073be4873 100644
--- a/test/core/iomgr/fd_posix_test.c
+++ b/test/core/iomgr/fd_posix_test.c
@@ -53,7 +53,7 @@
 #include "src/core/iomgr/iomgr.h"
 #include "test/core/util/test_config.h"
 
-static gpr_mu g_mu;
+static gpr_mu *g_mu;
 static grpc_pollset *g_pollset;
 
 /* buffer size used to send and receive data.
@@ -182,10 +182,10 @@ static void listen_shutdown_cb(grpc_exec_ctx *exec_ctx, void *arg /*server */,
 
   grpc_fd_orphan(exec_ctx, sv->em_fd, NULL, NULL, "b");
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   sv->done = 1;
   grpc_pollset_kick(g_pollset, NULL);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 /* Called when a new TCP connection request arrives in the listening port. */
@@ -252,18 +252,18 @@ static int server_start(grpc_exec_ctx *exec_ctx, server *sv) {
 
 /* Wait and shutdown a sever. */
 static void server_wait_and_shutdown(server *sv) {
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (!sv->done) {
     grpc_exec_ctx exec_ctx = GRPC_EXEC_CTX_INIT;
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       gpr_inf_future(GPR_CLOCK_MONOTONIC));
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 /* ===An upload client to test notify_on_write=== */
@@ -310,9 +310,9 @@ static void client_session_write(grpc_exec_ctx *exec_ctx, void *arg, /*client */
   ssize_t write_once = 0;
 
   if (!success) {
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
     client_session_shutdown_cb(exec_ctx, arg, 1);
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     return;
   }
 
@@ -322,7 +322,7 @@ static void client_session_write(grpc_exec_ctx *exec_ctx, void *arg, /*client */
   } while (write_once > 0);
 
   if (errno == EAGAIN) {
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
     if (cl->client_write_cnt < CLIENT_TOTAL_WRITE_CNT) {
       cl->write_closure.cb = client_session_write;
       cl->write_closure.cb_arg = cl;
@@ -331,7 +331,7 @@ static void client_session_write(grpc_exec_ctx *exec_ctx, void *arg, /*client */
     } else {
       client_session_shutdown_cb(exec_ctx, arg, 1);
     }
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
   } else {
     gpr_log(GPR_ERROR, "unknown errno %s", strerror(errno));
     abort();
@@ -367,18 +367,18 @@ static void client_start(grpc_exec_ctx *exec_ctx, client *cl, int port) {
 
 /* Wait for the signal to shutdown a client. */
 static void client_wait_and_shutdown(client *cl) {
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (!cl->done) {
     grpc_pollset_worker *worker = NULL;
     grpc_exec_ctx exec_ctx = GRPC_EXEC_CTX_INIT;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       gpr_inf_future(GPR_CLOCK_MONOTONIC));
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 /* Test grpc_fd. Start an upload server and client, upload a stream of
@@ -413,20 +413,20 @@ static void first_read_callback(grpc_exec_ctx *exec_ctx,
                                 void *arg /* fd_change_data */, bool success) {
   fd_change_data *fdc = arg;
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   fdc->cb_that_ran = first_read_callback;
   grpc_pollset_kick(g_pollset, NULL);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 static void second_read_callback(grpc_exec_ctx *exec_ctx,
                                  void *arg /* fd_change_data */, bool success) {
   fd_change_data *fdc = arg;
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   fdc->cb_that_ran = second_read_callback;
   grpc_pollset_kick(g_pollset, NULL);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 /* Test that changing the callback we use for notify_on_read actually works.
@@ -468,18 +468,18 @@ static void test_grpc_fd_change(void) {
   GPR_ASSERT(result == 1);
 
   /* And now wait for it to run. */
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (a.cb_that_ran == NULL) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       gpr_inf_future(GPR_CLOCK_MONOTONIC));
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
   GPR_ASSERT(a.cb_that_ran == first_read_callback);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 
   /* And drain the socket so we can generate a new read edge */
   result = read(sv[0], &data, 1);
@@ -492,19 +492,19 @@ static void test_grpc_fd_change(void) {
   result = write(sv[1], &data, 1);
   GPR_ASSERT(result == 1);
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (b.cb_that_ran == NULL) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       gpr_inf_future(GPR_CLOCK_MONOTONIC));
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
   /* Except now we verify that second_read_callback ran instead */
   GPR_ASSERT(b.cb_that_ran == second_read_callback);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 
   grpc_fd_orphan(&exec_ctx, em_fd, NULL, NULL, "d");
   grpc_exec_ctx_finish(&exec_ctx);
@@ -522,7 +522,6 @@ int main(int argc, char **argv) {
   grpc_exec_ctx exec_ctx = GRPC_EXEC_CTX_INIT;
   grpc_test_init(argc, argv);
   grpc_iomgr_init();
-  gpr_mu_init(&g_mu);
   g_pollset = gpr_malloc(grpc_pollset_size());
   grpc_pollset_init(g_pollset, &g_mu);
   test_grpc_fd();
@@ -531,7 +530,6 @@ int main(int argc, char **argv) {
   grpc_pollset_shutdown(&exec_ctx, g_pollset, &destroyed);
   grpc_exec_ctx_finish(&exec_ctx);
   gpr_free(g_pollset);
-  gpr_mu_destroy(&g_mu);
   grpc_iomgr_shutdown();
   return 0;
 }
diff --git a/test/core/iomgr/tcp_client_posix_test.c b/test/core/iomgr/tcp_client_posix_test.c
index 51581a8cb0451170a0dd67de09701e438f166898..ac666080fe9a60c45c61dd3a7b07356fff7fc2ad 100644
--- a/test/core/iomgr/tcp_client_posix_test.c
+++ b/test/core/iomgr/tcp_client_posix_test.c
@@ -51,7 +51,7 @@
 #include "test/core/util/test_config.h"
 
 static grpc_pollset_set *g_pollset_set;
-static gpr_mu g_mu;
+static gpr_mu *g_mu;
 static grpc_pollset *g_pollset;
 static int g_connections_complete = 0;
 static grpc_endpoint *g_connecting = NULL;
@@ -61,10 +61,10 @@ static gpr_timespec test_deadline(void) {
 }
 
 static void finish_connection() {
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   g_connections_complete++;
   grpc_pollset_kick(g_pollset, NULL);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 static void must_succeed(grpc_exec_ctx *exec_ctx, void *arg, bool success) {
@@ -102,9 +102,9 @@ void test_succeeds(void) {
   GPR_ASSERT(0 == bind(svr_fd, (struct sockaddr *)&addr, addr_len));
   GPR_ASSERT(0 == listen(svr_fd, 1));
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   connections_complete_before = g_connections_complete;
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 
   /* connect to it */
   GPR_ASSERT(getsockname(svr_fd, (struct sockaddr *)&addr, &addr_len) == 0);
@@ -121,19 +121,19 @@ void test_succeeds(void) {
   GPR_ASSERT(r >= 0);
   close(r);
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
 
   while (g_connections_complete == connections_complete_before) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5));
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_flush(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
 
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 
   grpc_exec_ctx_finish(&exec_ctx);
 }
@@ -150,9 +150,9 @@ void test_fails(void) {
   memset(&addr, 0, sizeof(addr));
   addr.sin_family = AF_INET;
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   connections_complete_before = g_connections_complete;
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 
   /* connect to a broken address */
   grpc_closure_init(&done, must_fail, NULL);
@@ -160,7 +160,7 @@ void test_fails(void) {
                           (struct sockaddr *)&addr, addr_len,
                           gpr_inf_future(GPR_CLOCK_REALTIME));
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
 
   /* wait for the connection callback to finish */
   while (g_connections_complete == connections_complete_before) {
@@ -170,12 +170,12 @@ void test_fails(void) {
     if (!grpc_timer_check(&exec_ctx, now, &polling_deadline)) {
       grpc_pollset_work(&exec_ctx, g_pollset, &worker, now, polling_deadline);
     }
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_flush(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
 
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
   grpc_exec_ctx_finish(&exec_ctx);
 }
 
@@ -220,16 +220,16 @@ void test_times_out(void) {
 
   connect_deadline = GRPC_TIMEOUT_SECONDS_TO_DEADLINE(1);
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   connections_complete_before = g_connections_complete;
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 
   grpc_closure_init(&done, must_fail, NULL);
   grpc_tcp_client_connect(&exec_ctx, &done, &g_connecting, g_pollset_set,
                           (struct sockaddr *)&addr, addr_len, connect_deadline);
 
   /* Make sure the event doesn't trigger early */
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   for (;;) {
     grpc_pollset_worker *worker = NULL;
     gpr_timespec now = gpr_now(connect_deadline.clock_type);
@@ -257,11 +257,11 @@ void test_times_out(void) {
     if (!grpc_timer_check(&exec_ctx, now, &polling_deadline)) {
       grpc_pollset_work(&exec_ctx, g_pollset, &worker, now, polling_deadline);
     }
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_flush(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 
   grpc_exec_ctx_finish(&exec_ctx);
 
@@ -282,7 +282,6 @@ int main(int argc, char **argv) {
   grpc_init();
   g_pollset_set = grpc_pollset_set_create();
   g_pollset = gpr_malloc(grpc_pollset_size());
-  gpr_mu_init(&g_mu);
   grpc_pollset_init(g_pollset, &g_mu);
   grpc_pollset_set_add_pollset(&exec_ctx, g_pollset_set, g_pollset);
   grpc_exec_ctx_finish(&exec_ctx);
@@ -296,6 +295,5 @@ int main(int argc, char **argv) {
   grpc_exec_ctx_finish(&exec_ctx);
   grpc_shutdown();
   gpr_free(g_pollset);
-  gpr_mu_destroy(&g_mu);
   return 0;
 }
diff --git a/test/core/iomgr/tcp_posix_test.c b/test/core/iomgr/tcp_posix_test.c
index d6758f8fe1b79788841f65b8bfe404d1980e6486..4351642ab6e3fb16593fa3c48093538e84446470 100644
--- a/test/core/iomgr/tcp_posix_test.c
+++ b/test/core/iomgr/tcp_posix_test.c
@@ -48,7 +48,7 @@
 #include "test/core/iomgr/endpoint_tests.h"
 #include "test/core/util/test_config.h"
 
-static gpr_mu g_mu;
+static gpr_mu *g_mu;
 static grpc_pollset *g_pollset;
 
 /*
@@ -146,7 +146,7 @@ static void read_cb(grpc_exec_ctx *exec_ctx, void *user_data, bool success) {
 
   GPR_ASSERT(success);
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   current_data = state->read_bytes % 256;
   read_bytes = count_slices(state->incoming.slices, state->incoming.count,
                             &current_data);
@@ -154,10 +154,10 @@ static void read_cb(grpc_exec_ctx *exec_ctx, void *user_data, bool success) {
   gpr_log(GPR_INFO, "Read %d bytes of %d", read_bytes,
           state->target_read_bytes);
   if (state->read_bytes >= state->target_read_bytes) {
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
   } else {
     grpc_endpoint_read(exec_ctx, state->ep, &state->incoming, &state->read_cb);
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
   }
 }
 
@@ -189,17 +189,17 @@ static void read_test(size_t num_bytes, size_t slice_size) {
 
   grpc_endpoint_read(&exec_ctx, ep, &state.incoming, &state.read_cb);
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (state.read_bytes < state.target_read_bytes) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC), deadline);
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
   GPR_ASSERT(state.read_bytes == state.target_read_bytes);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 
   gpr_slice_buffer_destroy(&state.incoming);
   grpc_endpoint_destroy(&exec_ctx, ep);
@@ -235,17 +235,17 @@ static void large_read_test(size_t slice_size) {
 
   grpc_endpoint_read(&exec_ctx, ep, &state.incoming, &state.read_cb);
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (state.read_bytes < state.target_read_bytes) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC), deadline);
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
   GPR_ASSERT(state.read_bytes == state.target_read_bytes);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 
   gpr_slice_buffer_destroy(&state.incoming);
   grpc_endpoint_destroy(&exec_ctx, ep);
@@ -284,11 +284,11 @@ static void write_done(grpc_exec_ctx *exec_ctx,
                        void *user_data /* write_socket_state */, bool success) {
   struct write_socket_state *state = (struct write_socket_state *)user_data;
   gpr_log(GPR_INFO, "Write done callback called");
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   gpr_log(GPR_INFO, "Signalling write done");
   state->write_done = 1;
   grpc_pollset_kick(g_pollset, NULL);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 void drain_socket_blocking(int fd, size_t num_bytes, size_t read_size) {
@@ -305,11 +305,11 @@ void drain_socket_blocking(int fd, size_t num_bytes, size_t read_size) {
 
   for (;;) {
     grpc_pollset_worker *worker = NULL;
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       GRPC_TIMEOUT_MILLIS_TO_DEADLINE(10));
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
     do {
       bytes_read =
@@ -364,7 +364,7 @@ static void write_test(size_t num_bytes, size_t slice_size) {
 
   grpc_endpoint_write(&exec_ctx, ep, &outgoing, &write_done_closure);
   drain_socket_blocking(sv[0], num_bytes, num_bytes);
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   for (;;) {
     grpc_pollset_worker *worker = NULL;
     if (state.write_done) {
@@ -372,11 +372,11 @@ static void write_test(size_t num_bytes, size_t slice_size) {
     }
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC), deadline);
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 
   gpr_slice_buffer_destroy(&outgoing);
   grpc_endpoint_destroy(&exec_ctx, ep);
@@ -424,27 +424,27 @@ static void release_fd_test(size_t num_bytes, size_t slice_size) {
 
   grpc_endpoint_read(&exec_ctx, ep, &state.incoming, &state.read_cb);
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (state.read_bytes < state.target_read_bytes) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC), deadline);
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
   GPR_ASSERT(state.read_bytes == state.target_read_bytes);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 
   gpr_slice_buffer_destroy(&state.incoming);
   grpc_tcp_destroy_and_release_fd(&exec_ctx, ep, &fd, &fd_released_cb);
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   while (!fd_released_done) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC), deadline);
   }
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
   GPR_ASSERT(fd_released_done == 1);
   GPR_ASSERT(fd == sv[1]);
   grpc_exec_ctx_finish(&exec_ctx);
@@ -514,16 +514,14 @@ int main(int argc, char **argv) {
   grpc_test_init(argc, argv);
   grpc_init();
   g_pollset = gpr_malloc(grpc_pollset_size());
-  gpr_mu_init(&g_mu);
   grpc_pollset_init(g_pollset, &g_mu);
   run_tests();
-  grpc_endpoint_tests(configs[0], g_pollset, &g_mu);
+  grpc_endpoint_tests(configs[0], g_pollset, g_mu);
   grpc_closure_init(&destroyed, destroy_pollset, g_pollset);
   grpc_pollset_shutdown(&exec_ctx, g_pollset, &destroyed);
   grpc_exec_ctx_finish(&exec_ctx);
   grpc_shutdown();
   gpr_free(g_pollset);
-  gpr_mu_destroy(&g_mu);
 
   return 0;
 }
diff --git a/test/core/iomgr/tcp_server_posix_test.c b/test/core/iomgr/tcp_server_posix_test.c
index ed627734bfadcd3bbb3190c1a3c08a431b7c39d9..7933468355a77e06f778979a99052e26b139539d 100644
--- a/test/core/iomgr/tcp_server_posix_test.c
+++ b/test/core/iomgr/tcp_server_posix_test.c
@@ -52,7 +52,7 @@
 
 #define LOG_TEST(x) gpr_log(GPR_INFO, "%s", #x)
 
-static gpr_mu g_mu;
+static gpr_mu *g_mu;
 static grpc_pollset *g_pollset;
 static int g_nconnects = 0;
 
@@ -117,11 +117,11 @@ static void on_connect(grpc_exec_ctx *exec_ctx, void *arg, grpc_endpoint *tcp,
   grpc_endpoint_shutdown(exec_ctx, tcp);
   grpc_endpoint_destroy(exec_ctx, tcp);
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   on_connect_result_set(&g_result, acceptor);
   g_nconnects++;
   grpc_pollset_kick(g_pollset, NULL);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 static void test_no_op(void) {
@@ -178,7 +178,7 @@ static void tcp_connect(grpc_exec_ctx *exec_ctx, const struct sockaddr *remote,
   int clifd = socket(remote->sa_family, SOCK_STREAM, 0);
   int nconnects_before;
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   nconnects_before = g_nconnects;
   on_connect_result_init(&g_result);
   GPR_ASSERT(clifd >= 0);
@@ -190,16 +190,16 @@ static void tcp_connect(grpc_exec_ctx *exec_ctx, const struct sockaddr *remote,
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(exec_ctx, g_pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC), deadline);
-    gpr_mu_unlock(&g_mu);
+    gpr_mu_unlock(g_mu);
     grpc_exec_ctx_finish(exec_ctx);
-    gpr_mu_lock(&g_mu);
+    gpr_mu_lock(g_mu);
   }
   gpr_log(GPR_DEBUG, "wait done");
   GPR_ASSERT(g_nconnects == nconnects_before + 1);
   close(clifd);
   *result = g_result;
 
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 /* Tests a tcp server with multiple ports. TODO(daniel-j-born): Multiple fds for
@@ -315,7 +315,6 @@ int main(int argc, char **argv) {
   grpc_test_init(argc, argv);
   grpc_init();
   g_pollset = gpr_malloc(grpc_pollset_size());
-  gpr_mu_init(&g_mu);
   grpc_pollset_init(g_pollset, &g_mu);
 
   test_no_op();
@@ -330,6 +329,5 @@ int main(int argc, char **argv) {
   grpc_exec_ctx_finish(&exec_ctx);
   grpc_shutdown();
   gpr_free(g_pollset);
-  gpr_mu_destroy(&g_mu);
   return 0;
 }
diff --git a/test/core/iomgr/workqueue_test.c b/test/core/iomgr/workqueue_test.c
index f557042e39b4dcf575785d24c4205113b89ac947..8a1faf6303ef626d89b76bbf98a9db587279d284 100644
--- a/test/core/iomgr/workqueue_test.c
+++ b/test/core/iomgr/workqueue_test.c
@@ -39,15 +39,15 @@
 
 #include "test/core/util/test_config.h"
 
-static gpr_mu g_mu;
+static gpr_mu *g_mu;
 static grpc_pollset *g_pollset;
 
 static void must_succeed(grpc_exec_ctx *exec_ctx, void *p, bool success) {
   GPR_ASSERT(success == 1);
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   *(int *)p = 1;
   grpc_pollset_kick(g_pollset, NULL);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
 }
 
 static void test_ref_unref(void) {
@@ -71,11 +71,11 @@ static void test_add_closure(void) {
   grpc_workqueue_push(wq, &c, 1);
   grpc_workqueue_add_to_pollset(&exec_ctx, wq, g_pollset);
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   GPR_ASSERT(!done);
   grpc_pollset_work(&exec_ctx, g_pollset, &worker, gpr_now(deadline.clock_type),
                     deadline);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
   grpc_exec_ctx_finish(&exec_ctx);
   GPR_ASSERT(done);
 
@@ -96,11 +96,11 @@ static void test_flush(void) {
   grpc_workqueue_flush(&exec_ctx, wq);
   grpc_workqueue_add_to_pollset(&exec_ctx, wq, g_pollset);
 
-  gpr_mu_lock(&g_mu);
+  gpr_mu_lock(g_mu);
   GPR_ASSERT(!done);
   grpc_pollset_work(&exec_ctx, g_pollset, &worker, gpr_now(deadline.clock_type),
                     deadline);
-  gpr_mu_unlock(&g_mu);
+  gpr_mu_unlock(g_mu);
   grpc_exec_ctx_finish(&exec_ctx);
   GPR_ASSERT(done);
 
@@ -117,7 +117,6 @@ int main(int argc, char **argv) {
   grpc_exec_ctx exec_ctx = GRPC_EXEC_CTX_INIT;
   grpc_test_init(argc, argv);
   grpc_init();
-  gpr_mu_init(&g_mu);
   g_pollset = gpr_malloc(grpc_pollset_size());
   grpc_pollset_init(g_pollset, &g_mu);
 
@@ -131,6 +130,5 @@ int main(int argc, char **argv) {
   grpc_shutdown();
 
   gpr_free(g_pollset);
-  gpr_mu_destroy(&g_mu);
   return 0;
 }
diff --git a/test/core/security/oauth2_utils.c b/test/core/security/oauth2_utils.c
index 3280eac801cc8b1de0883bc7222673b40fafb373..9b70afffe1eebd4a20db36ed76d151f8b70e1a40 100644
--- a/test/core/security/oauth2_utils.c
+++ b/test/core/security/oauth2_utils.c
@@ -45,7 +45,7 @@
 #include "src/core/security/credentials.h"
 
 typedef struct {
-  gpr_mu mu;
+  gpr_mu *mu;
   grpc_pollset *pollset;
   int is_done;
   char *token;
@@ -67,11 +67,11 @@ static void on_oauth2_response(grpc_exec_ctx *exec_ctx, void *user_data,
            GPR_SLICE_LENGTH(token_slice));
     token[GPR_SLICE_LENGTH(token_slice)] = '\0';
   }
-  gpr_mu_lock(&request->mu);
+  gpr_mu_lock(request->mu);
   request->is_done = 1;
   request->token = token;
   grpc_pollset_kick(request->pollset, NULL);
-  gpr_mu_unlock(&request->mu);
+  gpr_mu_unlock(request->mu);
 }
 
 static void do_nothing(grpc_exec_ctx *exec_ctx, void *unused, bool success) {}
@@ -95,14 +95,14 @@ char *grpc_test_fetch_oauth2_token_with_credentials(
 
   grpc_exec_ctx_finish(&exec_ctx);
 
-  gpr_mu_lock(&request.mu);
+  gpr_mu_lock(request.mu);
   while (!request.is_done) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, request.pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       gpr_inf_future(GPR_CLOCK_MONOTONIC));
   }
-  gpr_mu_unlock(&request.mu);
+  gpr_mu_unlock(request.mu);
 
   grpc_pollset_shutdown(&exec_ctx, request.pollset, &do_nothing_closure);
   grpc_exec_ctx_finish(&exec_ctx);
diff --git a/test/core/security/print_google_default_creds_token.c b/test/core/security/print_google_default_creds_token.c
index 2145a79ff97bd61d5bd3a238c1c9f26326c8262d..09673f362cfcc87bfba608688ae052c7517af734 100644
--- a/test/core/security/print_google_default_creds_token.c
+++ b/test/core/security/print_google_default_creds_token.c
@@ -46,7 +46,7 @@
 #include "src/core/support/string.h"
 
 typedef struct {
-  gpr_mu mu;
+  gpr_mu *mu;
   grpc_pollset *pollset;
   int is_done;
 } synchronizer;
@@ -64,10 +64,10 @@ static void on_metadata_response(grpc_exec_ctx *exec_ctx, void *user_data,
     printf("\nGot token: %s\n\n", token);
     gpr_free(token);
   }
-  gpr_mu_lock(&sync->mu);
+  gpr_mu_lock(sync->mu);
   sync->is_done = 1;
   grpc_pollset_kick(sync->pollset, NULL);
-  gpr_mu_unlock(&sync->mu);
+  gpr_mu_unlock(sync->mu);
 }
 
 int main(int argc, char **argv) {
@@ -94,7 +94,6 @@ int main(int argc, char **argv) {
   }
 
   sync.pollset = gpr_malloc(grpc_pollset_size());
-  gpr_mu_init(&sync.mu);
   grpc_pollset_init(sync.pollset, &sync.mu);
   sync.is_done = 0;
 
@@ -102,21 +101,22 @@ int main(int argc, char **argv) {
       &exec_ctx, ((grpc_composite_channel_credentials *)creds)->call_creds,
       sync.pollset, context, on_metadata_response, &sync);
 
-  gpr_mu_lock(&sync.mu);
+  gpr_mu_lock(sync.mu);
   while (!sync.is_done) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, sync.pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       gpr_inf_future(GPR_CLOCK_MONOTONIC));
-    gpr_mu_unlock(&sync.mu);
-    grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&sync.mu);
+    gpr_mu_unlock(sync.mu);
+    grpc_exec_ctx_flush(&exec_ctx);
+    gpr_mu_lock(sync.mu);
   }
-  gpr_mu_unlock(&sync.mu);
+  gpr_mu_unlock(sync.mu);
+
+  grpc_exec_ctx_finish(&exec_ctx);
 
   grpc_channel_credentials_release(creds);
   gpr_free(sync.pollset);
-  gpr_mu_destroy(&sync.mu);
 
 end:
   gpr_cmdline_destroy(cl);
diff --git a/test/core/security/secure_endpoint_test.c b/test/core/security/secure_endpoint_test.c
index 61543ada43e16eb5040f0bb7bb598a0e4f8b3eaf..0e8c38a53ec3cf8795cf9029626ca969c12e55c5 100644
--- a/test/core/security/secure_endpoint_test.c
+++ b/test/core/security/secure_endpoint_test.c
@@ -45,7 +45,7 @@
 #include "src/core/tsi/fake_transport_security.h"
 #include "test/core/util/test_config.h"
 
-static gpr_mu g_mu;
+static gpr_mu *g_mu;
 static grpc_pollset *g_pollset;
 
 static grpc_endpoint_test_fixture secure_endpoint_create_fixture_tcp_socketpair(
@@ -183,9 +183,8 @@ int main(int argc, char **argv) {
 
   grpc_init();
   g_pollset = gpr_malloc(grpc_pollset_size());
-  gpr_mu_init(&g_mu);
   grpc_pollset_init(g_pollset, &g_mu);
-  grpc_endpoint_tests(configs[0], g_pollset, &g_mu);
+  grpc_endpoint_tests(configs[0], g_pollset, g_mu);
   test_leftover(configs[1], 1);
   grpc_closure_init(&destroyed, destroy_pollset, g_pollset);
   grpc_pollset_shutdown(&exec_ctx, g_pollset, &destroyed);
@@ -193,7 +192,6 @@ int main(int argc, char **argv) {
   grpc_shutdown();
 
   gpr_free(g_pollset);
-  gpr_mu_destroy(&g_mu);
 
   return 0;
 }
diff --git a/test/core/security/verify_jwt.c b/test/core/security/verify_jwt.c
index c3cf6bb739934d0d5429d33f3e1c1e67be626c9c..eb86589681d12644dffa7c3a09f2fcbfd948cb1b 100644
--- a/test/core/security/verify_jwt.c
+++ b/test/core/security/verify_jwt.c
@@ -46,7 +46,7 @@
 
 typedef struct {
   grpc_pollset *pollset;
-  gpr_mu mu;
+  gpr_mu *mu;
   int is_done;
   int success;
 } synchronizer;
@@ -79,10 +79,10 @@ static void on_jwt_verification_done(void *user_data,
             grpc_jwt_verifier_status_to_string(status));
   }
 
-  gpr_mu_lock(&sync->mu);
+  gpr_mu_lock(sync->mu);
   sync->is_done = 1;
   grpc_pollset_kick(sync->pollset, NULL);
-  gpr_mu_unlock(&sync->mu);
+  gpr_mu_unlock(sync->mu);
 }
 
 int main(int argc, char **argv) {
@@ -106,26 +106,24 @@ int main(int argc, char **argv) {
   grpc_init();
 
   sync.pollset = gpr_malloc(grpc_pollset_size());
-  gpr_mu_init(&sync.mu);
   grpc_pollset_init(sync.pollset, &sync.mu);
   sync.is_done = 0;
 
   grpc_jwt_verifier_verify(&exec_ctx, verifier, sync.pollset, jwt, aud,
                            on_jwt_verification_done, &sync);
 
-  gpr_mu_lock(&sync.mu);
+  gpr_mu_lock(sync.mu);
   while (!sync.is_done) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, sync.pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       gpr_inf_future(GPR_CLOCK_MONOTONIC));
-    gpr_mu_unlock(&sync.mu);
+    gpr_mu_unlock(sync.mu);
     grpc_exec_ctx_finish(&exec_ctx);
-    gpr_mu_lock(&sync.mu);
+    gpr_mu_lock(sync.mu);
   }
-  gpr_mu_unlock(&sync.mu);
+  gpr_mu_unlock(sync.mu);
 
-  gpr_mu_destroy(&sync.mu);
   gpr_free(sync.pollset);
 
   grpc_jwt_verifier_destroy(verifier);
diff --git a/test/core/util/port_posix.c b/test/core/util/port_posix.c
index a04471706eeffbe8805d2263331dc230518e70c6..ba382d242a36878448ce799611e204421eeb2920 100644
--- a/test/core/util/port_posix.c
+++ b/test/core/util/port_posix.c
@@ -69,7 +69,7 @@ static int has_port_been_chosen(int port) {
 }
 
 typedef struct freereq {
-  gpr_mu mu;
+  gpr_mu *mu;
   grpc_pollset *pollset;
   int done;
 } freereq;
@@ -83,10 +83,10 @@ static void destroy_pollset_and_shutdown(grpc_exec_ctx *exec_ctx, void *p,
 static void freed_port_from_server(grpc_exec_ctx *exec_ctx, void *arg,
                                    const grpc_httpcli_response *response) {
   freereq *pr = arg;
-  gpr_mu_lock(&pr->mu);
+  gpr_mu_lock(pr->mu);
   pr->done = 1;
   grpc_pollset_kick(pr->pollset, NULL);
-  gpr_mu_unlock(&pr->mu);
+  gpr_mu_unlock(pr->mu);
 }
 
 static void free_port_using_server(char *server, int port) {
@@ -103,7 +103,6 @@ static void free_port_using_server(char *server, int port) {
   memset(&req, 0, sizeof(req));
 
   pr.pollset = gpr_malloc(grpc_pollset_size());
-  gpr_mu_init(&pr.mu);
   grpc_pollset_init(pr.pollset, &pr.mu);
   grpc_closure_init(&shutdown_closure, destroy_pollset_and_shutdown,
                     pr.pollset);
@@ -116,21 +115,20 @@ static void free_port_using_server(char *server, int port) {
   grpc_httpcli_get(&exec_ctx, &context, pr.pollset, &req,
                    GRPC_TIMEOUT_SECONDS_TO_DEADLINE(10), freed_port_from_server,
                    &pr);
-  gpr_mu_lock(&pr.mu);
+  gpr_mu_lock(pr.mu);
   while (!pr.done) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, pr.pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       GRPC_TIMEOUT_SECONDS_TO_DEADLINE(1));
   }
-  gpr_mu_unlock(&pr.mu);
+  gpr_mu_unlock(pr.mu);
 
   grpc_httpcli_context_destroy(&context);
   grpc_exec_ctx_finish(&exec_ctx);
   grpc_pollset_shutdown(&exec_ctx, pr.pollset, &shutdown_closure);
   grpc_exec_ctx_finish(&exec_ctx);
   gpr_free(pr.pollset);
-  gpr_mu_destroy(&pr.mu);
   gpr_free(path);
 }
 
@@ -208,7 +206,7 @@ static int is_port_available(int *port, int is_tcp) {
 }
 
 typedef struct portreq {
-  gpr_mu mu;
+  gpr_mu *mu;
   grpc_pollset *pollset;
   int port;
   int retries;
@@ -253,10 +251,10 @@ static void got_port_from_server(grpc_exec_ctx *exec_ctx, void *arg,
     port = port * 10 + response->body[i] - '0';
   }
   GPR_ASSERT(port > 1024);
-  gpr_mu_lock(&pr->mu);
+  gpr_mu_lock(pr->mu);
   pr->port = port;
   grpc_pollset_kick(pr->pollset, NULL);
-  gpr_mu_unlock(&pr->mu);
+  gpr_mu_unlock(pr->mu);
 }
 
 static int pick_port_using_server(char *server) {
@@ -271,7 +269,6 @@ static int pick_port_using_server(char *server) {
   memset(&pr, 0, sizeof(pr));
   memset(&req, 0, sizeof(req));
   pr.pollset = gpr_malloc(grpc_pollset_size());
-  gpr_mu_init(&pr.mu);
   grpc_pollset_init(pr.pollset, &pr.mu);
   grpc_closure_init(&shutdown_closure, destroy_pollset_and_shutdown,
                     pr.pollset);
@@ -287,20 +284,19 @@ static int pick_port_using_server(char *server) {
                    GRPC_TIMEOUT_SECONDS_TO_DEADLINE(10), got_port_from_server,
                    &pr);
   grpc_exec_ctx_finish(&exec_ctx);
-  gpr_mu_lock(&pr.mu);
+  gpr_mu_lock(pr.mu);
   while (pr.port == -1) {
     grpc_pollset_worker *worker = NULL;
     grpc_pollset_work(&exec_ctx, pr.pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       GRPC_TIMEOUT_SECONDS_TO_DEADLINE(1));
   }
-  gpr_mu_unlock(&pr.mu);
+  gpr_mu_unlock(pr.mu);
 
   grpc_httpcli_context_destroy(&context);
   grpc_pollset_shutdown(&exec_ctx, pr.pollset, &shutdown_closure);
   grpc_exec_ctx_finish(&exec_ctx);
   gpr_free(pr.pollset);
-  gpr_mu_destroy(&pr.mu);
 
   return pr.port;
 }
diff --git a/test/core/util/port_windows.c b/test/core/util/port_windows.c
index b5bd0168ad2808581257dae898ce988875826090..3b20aeb71827906aac51d470fdad3964076766a6 100644
--- a/test/core/util/port_windows.c
+++ b/test/core/util/port_windows.c
@@ -129,7 +129,8 @@ static int is_port_available(int *port, int is_tcp) {
 }
 
 typedef struct portreq {
-  grpc_pollset pollset;
+  grpc_pollset *pollset;
+  gpr_mu *mu;
   int port;
 } portreq;
 
@@ -145,10 +146,10 @@ static void got_port_from_server(grpc_exec_ctx *exec_ctx, void *arg,
     port = port * 10 + response->body[i] - '0';
   }
   GPR_ASSERT(port > 1024);
-  gpr_mu_lock(GRPC_POLLSET_MU(&pr->pollset));
+  gpr_mu_lock(pr->mu);
   pr->port = port;
-  grpc_pollset_kick(&pr->pollset, NULL);
-  gpr_mu_unlock(GRPC_POLLSET_MU(&pr->pollset));
+  grpc_pollset_kick(pr->pollset, NULL);
+  gpr_mu_unlock(pr->mu);
 }
 
 static void destroy_pollset_and_shutdown(grpc_exec_ctx *exec_ctx, void *p,
@@ -168,32 +169,34 @@ static int pick_port_using_server(char *server) {
 
   memset(&pr, 0, sizeof(pr));
   memset(&req, 0, sizeof(req));
-  grpc_pollset_init(&pr.pollset);
+  pr.pollset = gpr_malloc(grpc_pollset_size());
+  grpc_pollset_init(pr.pollset, &pr.mu);
   pr.port = -1;
 
   req.host = server;
   req.path = "/get";
 
   grpc_httpcli_context_init(&context);
-  grpc_httpcli_get(&exec_ctx, &context, &pr.pollset, &req,
+  grpc_httpcli_get(&exec_ctx, &context, pr.pollset, &req,
                    GRPC_TIMEOUT_SECONDS_TO_DEADLINE(10), got_port_from_server,
                    &pr);
-  gpr_mu_lock(GRPC_POLLSET_MU(&pr.pollset));
+  gpr_mu_lock(pr.mu);
   while (pr.port == -1) {
     grpc_pollset_worker *worker = NULL;
-    grpc_pollset_work(&exec_ctx, &pr.pollset, &worker,
+    grpc_pollset_work(&exec_ctx, pr.pollset, &worker,
                       gpr_now(GPR_CLOCK_MONOTONIC),
                       GRPC_TIMEOUT_SECONDS_TO_DEADLINE(1));
-    gpr_mu_unlock(GRPC_POLLSET_MU(&pr.pollset));
+    gpr_mu_unlock(pr.mu);
     grpc_exec_ctx_flush(&exec_ctx);
-    gpr_mu_lock(GRPC_POLLSET_MU(&pr.pollset));
+    gpr_mu_lock(pr.mu);
   }
-  gpr_mu_unlock(GRPC_POLLSET_MU(&pr.pollset));
+  gpr_mu_unlock(pr.mu);
 
   grpc_httpcli_context_destroy(&context);
   grpc_closure_init(&destroy_pollset_closure, destroy_pollset_and_shutdown,
                     &pr.pollset);
-  grpc_pollset_shutdown(&exec_ctx, &pr.pollset, &destroy_pollset_closure);
+  grpc_pollset_shutdown(&exec_ctx, pr.pollset, &destroy_pollset_closure);
+  gpr_free(pr.pollset);
 
   grpc_exec_ctx_finish(&exec_ctx);
   return pr.port;
diff --git a/test/core/util/test_tcp_server.c b/test/core/util/test_tcp_server.c
index 8f1db4e50152108ac2e6dfc6286e16e272d272e2..ab379441d8c6c57f8437566db7278225ac6a7f4f 100644
--- a/test/core/util/test_tcp_server.c
+++ b/test/core/util/test_tcp_server.c
@@ -58,7 +58,6 @@ void test_tcp_server_init(test_tcp_server *server,
   grpc_closure_init(&server->shutdown_complete, on_server_destroyed, server);
   server->shutdown = 0;
   server->pollset = gpr_malloc(grpc_pollset_size());
-  gpr_mu_init(&server->mu);
   grpc_pollset_init(server->pollset, &server->mu);
   server->on_connect = on_connect;
   server->cb_data = user_data;
@@ -91,10 +90,10 @@ void test_tcp_server_poll(test_tcp_server *server, int seconds) {
       gpr_time_add(gpr_now(GPR_CLOCK_MONOTONIC),
                    gpr_time_from_seconds(seconds, GPR_TIMESPAN));
   grpc_exec_ctx exec_ctx = GRPC_EXEC_CTX_INIT;
-  gpr_mu_lock(&server->mu);
+  gpr_mu_lock(server->mu);
   grpc_pollset_work(&exec_ctx, server->pollset, &worker,
                     gpr_now(GPR_CLOCK_MONOTONIC), deadline);
-  gpr_mu_unlock(&server->mu);
+  gpr_mu_unlock(server->mu);
   grpc_exec_ctx_finish(&exec_ctx);
 }
 
@@ -116,6 +115,5 @@ void test_tcp_server_destroy(test_tcp_server *server) {
   grpc_exec_ctx_finish(&exec_ctx);
   grpc_pollset_destroy(server->pollset);
   gpr_free(server->pollset);
-  gpr_mu_destroy(&server->mu);
   grpc_shutdown();
 }
diff --git a/test/core/util/test_tcp_server.h b/test/core/util/test_tcp_server.h
index ef9dd007c77f2de5c9b7eac70cefe485113a824f..15fcb4fb873ab3ccf1be390966d8bf19f86ff79b 100644
--- a/test/core/util/test_tcp_server.h
+++ b/test/core/util/test_tcp_server.h
@@ -41,7 +41,7 @@ typedef struct test_tcp_server {
   grpc_tcp_server *tcp_server;
   grpc_closure shutdown_complete;
   int shutdown;
-  gpr_mu mu;
+  gpr_mu *mu;
   grpc_pollset *pollset;
   grpc_tcp_server_cb on_connect;
   void *cb_data;
diff --git a/test/cpp/common/alarm_cpp_test.cc b/test/cpp/common/alarm_cpp_test.cc
index 5d7344046ce564df72fd0c323ac181fb21796ca3..d4381c051589cd1477d9e05bd7922daadbc76412 100644
--- a/test/cpp/common/alarm_cpp_test.cc
+++ b/test/cpp/common/alarm_cpp_test.cc
@@ -55,6 +55,23 @@ TEST(AlarmTest, RegularExpiry) {
   EXPECT_EQ(junk, output_tag);
 }
 
+TEST(AlarmTest, RegularExpiryChrono) {
+  CompletionQueue cq;
+  void* junk = reinterpret_cast<void*>(1618033);
+  std::chrono::system_clock::time_point one_sec_deadline =
+      std::chrono::system_clock::now() + std::chrono::seconds(1);
+  Alarm alarm(&cq, one_sec_deadline, junk);
+
+  void* output_tag;
+  bool ok;
+  const CompletionQueue::NextStatus status = cq.AsyncNext(
+      (void**)&output_tag, &ok, GRPC_TIMEOUT_SECONDS_TO_DEADLINE(2));
+
+  EXPECT_EQ(status, CompletionQueue::GOT_EVENT);
+  EXPECT_TRUE(ok);
+  EXPECT_EQ(junk, output_tag);
+}
+
 TEST(AlarmTest, ZeroExpiry) {
   CompletionQueue cq;
   void* junk = reinterpret_cast<void*>(1618033);
diff --git a/test/cpp/end2end/async_end2end_test.cc b/test/cpp/end2end/async_end2end_test.cc
index 9ca3bf98f85c470abda4ef0482c0e16acac6922c..e7b16f0d27ad0525d70a8ce9f2d2389302dd3474 100644
--- a/test/cpp/end2end/async_end2end_test.cc
+++ b/test/cpp/end2end/async_end2end_test.cc
@@ -53,7 +53,7 @@
 #include "test/cpp/util/string_ref_helper.h"
 
 #ifdef GPR_POSIX_SOCKET
-#include "src/core/iomgr/pollset_posix.h"
+#include "src/core/iomgr/ev_posix.h"
 #endif
 
 using grpc::testing::EchoRequest;
diff --git a/test/cpp/end2end/end2end_test.cc b/test/cpp/end2end/end2end_test.cc
index ce8e4d2a109762ac28c70135bfdd4200debda87f..42757974b22e97a0c627d3942c8f6b4e6527a3d6 100644
--- a/test/cpp/end2end/end2end_test.cc
+++ b/test/cpp/end2end/end2end_test.cc
@@ -904,9 +904,9 @@ TEST_P(End2endTest, SimultaneousReadWritesDone) {
   std::thread reader_thread(ReaderThreadFunc, stream.get(), &ev);
   gpr_event_wait(&ev, gpr_inf_future(GPR_CLOCK_REALTIME));
   stream->WritesDone();
+  reader_thread.join();
   Status s = stream->Finish();
   EXPECT_TRUE(s.ok());
-  reader_thread.join();
 }
 
 TEST_P(End2endTest, ChannelState) {
diff --git a/third_party/nanopb b/third_party/nanopb
index 5497a1dfc91a86965383cdd1652e348345400435..f8ac463766281625ad710900479130c7fcb4d63b 160000
--- a/third_party/nanopb
+++ b/third_party/nanopb
@@ -1 +1 @@
-Subproject commit 5497a1dfc91a86965383cdd1652e348345400435
+Subproject commit f8ac463766281625ad710900479130c7fcb4d63b
diff --git a/tools/buildgen/build-cleaner.py b/tools/buildgen/build-cleaner.py
index 49a364412350c0aa6bb02e61c1b426ce9bc8fc29..12054da238eeb992ad5b67a9b23a4d3f1ac39387 100755
--- a/tools/buildgen/build-cleaner.py
+++ b/tools/buildgen/build-cleaner.py
@@ -40,6 +40,7 @@ TEST = (os.environ.get('TEST', 'false') == 'true')
 _TOP_LEVEL_KEYS = ['settings', 'proto_deps', 'filegroups', 'libs', 'targets', 'vspackages']
 _ELEM_KEYS = [
     'name',
+    'gtest',
     'cpu_cost',
     'flaky',
     'build',
@@ -98,4 +99,3 @@ for filename in sys.argv[1:]:
   else:
     with open(filename, 'w') as f:
       f.write(output)
-
diff --git a/tools/buildgen/plugins/expand_bin_attrs.py b/tools/buildgen/plugins/expand_bin_attrs.py
index 735c60ea9959a573c6192595567f5d237f2f8b3f..c30df2ad892753959bca62af17ef1710be903aa3 100755
--- a/tools/buildgen/plugins/expand_bin_attrs.py
+++ b/tools/buildgen/plugins/expand_bin_attrs.py
@@ -52,6 +52,7 @@ def mako_plugin(dictionary):
     tgt['ci_platforms'] = sorted(tgt.get('ci_platforms', tgt['platforms']))
     tgt['boringssl'] = tgt.get('boringssl', False)
     tgt['zlib'] = tgt.get('zlib', False)
+    tgt['gtest'] = tgt.get('gtest', False)
 
   libs = dictionary.get('libs')
   for lib in libs:
diff --git a/tools/doxygen/Doxyfile.c++.internal b/tools/doxygen/Doxyfile.c++.internal
index d5e5df86f64e920dd271c11ebe2058381b7f8edb..a2853108476f1c1b0cbf18fc62f679e9205f56a9 100644
--- a/tools/doxygen/Doxyfile.c++.internal
+++ b/tools/doxygen/Doxyfile.c++.internal
@@ -854,7 +854,6 @@ src/cpp/client/create_channel_internal.cc \
 src/cpp/client/credentials.cc \
 src/cpp/client/generic_stub.cc \
 src/cpp/client/insecure_credentials.cc \
-src/cpp/common/alarm.cc \
 src/cpp/common/call.cc \
 src/cpp/common/channel_arguments.cc \
 src/cpp/common/completion_queue.cc \
diff --git a/tools/run_tests/artifact_targets.py b/tools/run_tests/artifact_targets.py
index 803d3d106b21532521712c393b76854c49466c45..288a3f01542304b467ef94f69ef6242ea93cfcc1 100644
--- a/tools/run_tests/artifact_targets.py
+++ b/tools/run_tests/artifact_targets.py
@@ -254,10 +254,14 @@ class PHPArtifact:
     return []
 
   def build_jobspec(self):
-    return create_docker_jobspec(
-        self.name,
-        'tools/dockerfile/grpc_artifact_linux_{}'.format(self.arch),
-        'tools/run_tests/build_artifact_php.sh')
+    if self.platform == 'linux':
+      return create_docker_jobspec(
+          self.name,
+          'tools/dockerfile/grpc_artifact_linux_{}'.format(self.arch),
+          'tools/run_tests/build_artifact_php.sh')
+    else:
+      return create_jobspec(self.name,
+                            ['tools/run_tests/build_artifact_php.sh'])
 
 class ProtocArtifact:
   """Builds protoc and protoc-plugin artifacts"""
diff --git a/tools/run_tests/build_artifact_python.sh b/tools/run_tests/build_artifact_python.sh
index 6e7ab911d5bb5215fe0eccc9ebfd0a23a18bf774..7ba04d75463f3ef0dc26da70e759bf0bec60fcf2 100755
--- a/tools/run_tests/build_artifact_python.sh
+++ b/tools/run_tests/build_artifact_python.sh
@@ -39,6 +39,14 @@ then
   pip install -rrequirements.txt
 fi
 
+# Build the source distribution first because MANIFEST.in cannot override
+# exclusion of built shared objects among package resources (for some
+# inexplicable reason).
+GRPC_PYTHON_USE_CUSTOM_BDIST=0  \
+GRPC_PYTHON_BUILD_WITH_CYTHON=1 \
+${SETARCH_CMD} python setup.py  \
+    sdist
+
 # The bdist_wheel_grpc_custom command is finicky about command output ordering
 # and thus ought to be run in a shell command separate of others. Further, it
 # trashes the actual bdist_wheel output, so it should be run first so that
@@ -48,11 +56,12 @@ GRPC_PYTHON_BUILD_WITH_CYTHON=1 \
 ${SETARCH_CMD} python setup.py  \
     build_tagged_ext
 
+# Wheel has a bug where directories don't get excluded.
+# https://bitbucket.org/pypa/wheel/issues/99/cannot-exclude-directory
 GRPC_PYTHON_USE_CUSTOM_BDIST=0  \
 GRPC_PYTHON_BUILD_WITH_CYTHON=1 \
 ${SETARCH_CMD} python setup.py  \
-    bdist_wheel                 \
-    sdist
+    bdist_wheel
 
 mkdir -p artifacts
 
diff --git a/tools/run_tests/distribtest_targets.py b/tools/run_tests/distribtest_targets.py
index 0c02344d90d6e038bbaa404394f21209f98b9a09..933103f0a0598ba63e99004aaa537c0b12b5f8eb 100644
--- a/tools/run_tests/distribtest_targets.py
+++ b/tools/run_tests/distribtest_targets.py
@@ -201,7 +201,7 @@ class RubyDistribTest(object):
 class PHPDistribTest(object):
   """Tests PHP package"""
 
-  def __init__(self, platform, arch, docker_suffix):
+  def __init__(self, platform, arch, docker_suffix=None):
     self.name = 'php_%s_%s_%s' % (platform, arch, docker_suffix)
     self.platform = platform
     self.arch = arch
@@ -212,15 +212,19 @@ class PHPDistribTest(object):
     return []
 
   def build_jobspec(self):
-    if not self.platform == 'linux':
+    if self.platform == 'linux':
+      return create_docker_jobspec(self.name,
+                                   'tools/dockerfile/distribtest/php_%s_%s' % (
+                                       self.docker_suffix,
+                                       self.arch),
+                                   'test/distrib/php/run_distrib_test.sh')
+    elif self.platform == 'macos':
+      return create_jobspec(self.name,
+          ['test/distrib/php/run_distrib_test.sh'],
+          environ={'EXTERNAL_GIT_ROOT': '../../..'})
+    else:
       raise Exception("Not supported yet.")
 
-    return create_docker_jobspec(self.name,
-          'tools/dockerfile/distribtest/php_%s_%s' % (
-              self.docker_suffix,
-              self.arch),
-          'test/distrib/php/run_distrib_test.sh')
-
   def __str__(self):
     return self.name
 
@@ -271,6 +275,7 @@ def targets():
           NodeDistribTest('macos', 'x64', None, '5'),
           NodeDistribTest('linux', 'x86', 'jessie', '4'),
           PHPDistribTest('linux', 'x64', 'jessie'),
+          PHPDistribTest('macos', 'x64'),
           ] + [
             NodeDistribTest('linux', 'x64', os, version)
             for os in ('wheezy', 'jessie', 'ubuntu1204', 'ubuntu1404',
diff --git a/tools/run_tests/run_tests.py b/tools/run_tests/run_tests.py
index b6810e83a20ade921248f9904288057c2b4e7ba3..30a398e3fcdd40660c49c2eaea27d90c4451f21a 100755
--- a/tools/run_tests/run_tests.py
+++ b/tools/run_tests/run_tests.py
@@ -160,20 +160,45 @@ class CLanguage(object):
       else:
         binary = 'bins/%s/%s' % (self.config.build_config, target['name'])
       env = {}
-      shortname = ' '.join(cmdline)
+      shortname_ext = ''
       if 'env' in target:
         tenv = target['env']
         env.update(tenv)
-        shortname += ' '
-        shortname += ' '.join('%s=%s' % (key, tenv[key]) for key in sorted(tenv.keys()))
+        shortname_ext += ' '
+        shortname_ext += ' '.join('%s=%s' % (key, tenv[key]) for key in sorted(tenv.keys()))
       env['GRPC_DEFAULT_SSL_ROOTS_FILE_PATH'] = (
           _ROOT + '/src/core/tsi/test_creds/ca.pem')
       if os.path.isfile(binary):
-        cmdline = [binary] + target['args']
-        out.append(self.config.job_spec(cmdline, [binary],
-                                        shortname=' '.join(cmdline),
-                                        cpu_cost=target['cpu_cost'],
-                                        environ=env))
+        if 'gtest' in target and target['gtest']:
+          # here we parse the output of --gtest_list_tests to build up a
+          # complete list of the tests contained in a binary
+          # for each test, we then add a job to run, filtering for just that
+          # test
+          with open(os.devnull, 'w') as fnull:
+            tests = subprocess.check_output([binary, '--gtest_list_tests'],
+                                            stderr=fnull)
+          base = None
+          for line in tests.split('\n'):
+            i = line.find('#')
+            if i >= 0: line = line[:i]
+            if not line: continue
+            if line[0] != ' ':
+              base = line.strip()
+            else:
+              assert base is not None
+              assert line[1] == ' '
+              test = base + line.strip()
+              cmdline = [binary] + ['--gtest_filter=%s' % test]
+              out.append(self.config.job_spec(cmdline, [binary],
+                                              shortname='%s:%s %s' % (binary, test, shortname_ext),
+                                              cpu_cost=target['cpu_cost'],
+                                              environ=env))
+        else:
+          cmdline = [binary] + target['args']
+          out.append(self.config.job_spec(cmdline, [binary],
+                                          shortname=' '.join(cmdline) + shortname_ext,
+                                          cpu_cost=target['cpu_cost'],
+                                          environ=env))
       elif self.args.regex == '.*' or self.platform == 'windows':
         print '\nWARNING: binary not found, skipping', binary
     return sorted(out)
diff --git a/tools/run_tests/sources_and_headers.json b/tools/run_tests/sources_and_headers.json
index 0d3d97a8294c8e1c9c362a7c631239b01dfb69bb..d075bd364c35eb247ce6a2f5456f8c06f19d421b 100644
--- a/tools/run_tests/sources_and_headers.json
+++ b/tools/run_tests/sources_and_headers.json
@@ -4914,7 +4914,6 @@
       "src/cpp/client/secure_credentials.cc", 
       "src/cpp/client/secure_credentials.h", 
       "src/cpp/codegen/grpc_library.cc", 
-      "src/cpp/common/alarm.cc", 
       "src/cpp/common/auth_property_iterator.cc", 
       "src/cpp/common/call.cc", 
       "src/cpp/common/channel_arguments.cc", 
@@ -5173,7 +5172,6 @@
       "src/cpp/client/generic_stub.cc", 
       "src/cpp/client/insecure_credentials.cc", 
       "src/cpp/codegen/grpc_library.cc", 
-      "src/cpp/common/alarm.cc", 
       "src/cpp/common/call.cc", 
       "src/cpp/common/channel_arguments.cc", 
       "src/cpp/common/completion_queue.cc", 
diff --git a/tools/run_tests/tests.json b/tools/run_tests/tests.json
index a3195277b67c0b9db6b2532d76c83c6920abae27..dbc24462b67b5d07083c7b92e0dfa81cbdc94ec8 100644
--- a/tools/run_tests/tests.json
+++ b/tools/run_tests/tests.json
@@ -12,6 +12,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "alarm_test", 
     "platforms": [
@@ -32,6 +33,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "algorithm_test", 
     "platforms": [
@@ -52,6 +54,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "alloc_test", 
     "platforms": [
@@ -72,6 +75,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "alpn_test", 
     "platforms": [
@@ -92,6 +96,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "bin_encoder_test", 
     "platforms": [
@@ -112,6 +117,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "census_context_test", 
     "platforms": [
@@ -132,6 +138,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "channel_create_test", 
     "platforms": [
@@ -152,6 +159,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "chttp2_hpack_encoder_test", 
     "platforms": [
@@ -172,6 +180,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "chttp2_status_conversion_test", 
     "platforms": [
@@ -192,6 +201,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "chttp2_stream_map_test", 
     "platforms": [
@@ -212,6 +222,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "chttp2_varint_test", 
     "platforms": [
@@ -232,6 +243,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "compression_test", 
     "platforms": [
@@ -252,6 +264,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "dns_resolver_test", 
     "platforms": [
@@ -271,6 +284,7 @@
     "cpu_cost": 0.1, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "dualstack_socket_test", 
     "platforms": [
@@ -290,6 +304,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "endpoint_pair_test", 
     "platforms": [
@@ -309,6 +324,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "fd_conservation_posix_test", 
     "platforms": [
@@ -327,6 +343,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "fd_posix_test", 
     "platforms": [
@@ -345,6 +362,7 @@
     "cpu_cost": 2, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "fling_stream_test", 
     "platforms": [
@@ -363,6 +381,7 @@
     "cpu_cost": 2, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "fling_test", 
     "platforms": [
@@ -382,6 +401,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_avl_test", 
     "platforms": [
@@ -402,6 +422,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_cmdline_test", 
     "platforms": [
@@ -422,6 +443,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_cpu_test", 
     "platforms": [
@@ -442,6 +464,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_env_test", 
     "platforms": [
@@ -462,6 +485,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_histogram_test", 
     "platforms": [
@@ -482,6 +506,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_host_port_test", 
     "platforms": [
@@ -502,6 +527,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_load_file_test", 
     "platforms": [
@@ -522,6 +548,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_log_test", 
     "platforms": [
@@ -542,6 +569,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_slice_buffer_test", 
     "platforms": [
@@ -562,6 +590,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_slice_test", 
     "platforms": [
@@ -582,6 +611,7 @@
     "cpu_cost": 10, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_stack_lockfree_test", 
     "platforms": [
@@ -602,6 +632,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_string_test", 
     "platforms": [
@@ -622,6 +653,7 @@
     "cpu_cost": 10, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_sync_test", 
     "platforms": [
@@ -642,6 +674,7 @@
     "cpu_cost": 10, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_thd_test", 
     "platforms": [
@@ -662,6 +695,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_time_test", 
     "platforms": [
@@ -682,6 +716,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_tls_test", 
     "platforms": [
@@ -702,6 +737,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "gpr_useful_test", 
     "platforms": [
@@ -722,6 +758,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "grpc_auth_context_test", 
     "platforms": [
@@ -742,6 +779,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "grpc_b64_test", 
     "platforms": [
@@ -762,6 +800,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "grpc_byte_buffer_reader_test", 
     "platforms": [
@@ -782,6 +821,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "grpc_channel_args_test", 
     "platforms": [
@@ -802,6 +842,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "grpc_channel_stack_test", 
     "platforms": [
@@ -822,6 +863,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "grpc_completion_queue_test", 
     "platforms": [
@@ -842,6 +884,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "grpc_credentials_test", 
     "platforms": [
@@ -862,6 +905,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "grpc_invalid_channel_args_test", 
     "platforms": [
@@ -881,6 +925,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "grpc_json_token_test", 
     "platforms": [
@@ -900,6 +945,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "grpc_jwt_verifier_test", 
     "platforms": [
@@ -920,6 +966,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "grpc_security_connector_test", 
     "platforms": [
@@ -940,6 +987,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "hpack_parser_test", 
     "platforms": [
@@ -960,6 +1008,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "hpack_table_test", 
     "platforms": [
@@ -980,6 +1029,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "httpcli_format_request_test", 
     "platforms": [
@@ -1000,6 +1050,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "httpcli_parser_test", 
     "platforms": [
@@ -1019,6 +1070,7 @@
     "cpu_cost": 0.5, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "httpcli_test", 
     "platforms": [
@@ -1035,6 +1087,7 @@
     "cpu_cost": 0.5, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "httpscli_test", 
     "platforms": [
@@ -1052,6 +1105,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "init_test", 
     "platforms": [
@@ -1072,6 +1126,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "invalid_call_argument_test", 
     "platforms": [
@@ -1092,6 +1147,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "json_rewrite_test", 
     "platforms": [
@@ -1112,6 +1168,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "json_stream_error_test", 
     "platforms": [
@@ -1132,6 +1189,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "json_test", 
     "platforms": [
@@ -1152,6 +1210,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "lame_client_test", 
     "platforms": [
@@ -1172,6 +1231,7 @@
     "cpu_cost": 0.1, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "lb_policies_test", 
     "platforms": [
@@ -1192,6 +1252,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "message_compress_test", 
     "platforms": [
@@ -1212,6 +1273,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "mlog_test", 
     "platforms": [
@@ -1232,6 +1294,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "multiple_server_queues_test", 
     "platforms": [
@@ -1252,6 +1315,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "murmur_hash_test", 
     "platforms": [
@@ -1272,6 +1336,7 @@
     "cpu_cost": 0.1, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "no_server_test", 
     "platforms": [
@@ -1292,6 +1357,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "resolve_address_test", 
     "platforms": [
@@ -1312,6 +1378,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "secure_channel_create_test", 
     "platforms": [
@@ -1332,6 +1399,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "secure_endpoint_test", 
     "platforms": [
@@ -1352,6 +1420,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "server_chttp2_test", 
     "platforms": [
@@ -1372,6 +1441,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "server_test", 
     "platforms": [
@@ -1392,6 +1462,7 @@
     "cpu_cost": 0.1, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "set_initial_connect_string_test", 
     "platforms": [
@@ -1412,6 +1483,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "sockaddr_resolver_test", 
     "platforms": [
@@ -1432,6 +1504,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "sockaddr_utils_test", 
     "platforms": [
@@ -1451,6 +1524,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "socket_utils_test", 
     "platforms": [
@@ -1469,6 +1543,7 @@
     "cpu_cost": 0.5, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "tcp_client_posix_test", 
     "platforms": [
@@ -1487,6 +1562,7 @@
     "cpu_cost": 0.5, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "tcp_posix_test", 
     "platforms": [
@@ -1505,6 +1581,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "tcp_server_posix_test", 
     "platforms": [
@@ -1524,6 +1601,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "time_averaged_stats_test", 
     "platforms": [
@@ -1544,6 +1622,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "timeout_encoding_test", 
     "platforms": [
@@ -1564,6 +1643,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "timer_heap_test", 
     "platforms": [
@@ -1584,6 +1664,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "timer_list_test", 
     "platforms": [
@@ -1604,6 +1685,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "timers_test", 
     "platforms": [
@@ -1624,6 +1706,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "transport_connectivity_state_test", 
     "platforms": [
@@ -1644,6 +1727,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "transport_metadata_test", 
     "platforms": [
@@ -1663,6 +1747,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "transport_security_test", 
     "platforms": [
@@ -1681,6 +1766,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "udp_server_test", 
     "platforms": [
@@ -1700,6 +1786,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "uri_parser_test", 
     "platforms": [
@@ -1719,6 +1806,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "workqueue_test", 
     "platforms": [
@@ -1738,6 +1826,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "alarm_cpp_test", 
     "platforms": [
@@ -1758,6 +1847,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "async_end2end_test", 
     "platforms": [
@@ -1777,6 +1867,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c++", 
     "name": "async_streaming_ping_pong_test", 
     "platforms": [
@@ -1795,6 +1886,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c++", 
     "name": "async_unary_ping_pong_test", 
     "platforms": [
@@ -1814,6 +1906,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "auth_property_iterator_test", 
     "platforms": [
@@ -1834,6 +1927,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "channel_arguments_test", 
     "platforms": [
@@ -1854,6 +1948,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "cli_call_test", 
     "platforms": [
@@ -1873,6 +1968,7 @@
     "cpu_cost": 0.1, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "client_crash_test", 
     "platforms": [
@@ -1892,6 +1988,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "credentials_test", 
     "platforms": [
@@ -1912,6 +2009,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "cxx_byte_buffer_test", 
     "platforms": [
@@ -1932,6 +2030,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "cxx_slice_test", 
     "platforms": [
@@ -1952,6 +2051,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "cxx_string_ref_test", 
     "platforms": [
@@ -1972,6 +2072,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "cxx_time_test", 
     "platforms": [
@@ -1992,6 +2093,7 @@
     "cpu_cost": 0.5, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "end2end_test", 
     "platforms": [
@@ -2011,6 +2113,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c++", 
     "name": "generic_async_streaming_ping_pong_test", 
     "platforms": [
@@ -2030,6 +2133,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "generic_end2end_test", 
     "platforms": [
@@ -2050,6 +2154,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "grpclb_api_test", 
     "platforms": [
@@ -2070,6 +2175,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "hybrid_end2end_test", 
     "platforms": [
@@ -2089,6 +2195,7 @@
     "cpu_cost": 0.1, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c++", 
     "name": "interop_test", 
     "platforms": [
@@ -2108,6 +2215,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "mock_test", 
     "platforms": [
@@ -2127,6 +2235,7 @@
     "cpu_cost": 10, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c++", 
     "name": "qps_openloop_test", 
     "platforms": [
@@ -2145,6 +2254,7 @@
     "cpu_cost": 10, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c++", 
     "name": "qps_test", 
     "platforms": [
@@ -2164,6 +2274,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "secure_auth_context_test", 
     "platforms": [
@@ -2183,6 +2294,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c++", 
     "name": "secure_sync_unary_ping_pong_test", 
     "platforms": [
@@ -2201,6 +2313,7 @@
     "cpu_cost": 0.1, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "server_crash_test", 
     "platforms": [
@@ -2220,6 +2333,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "shutdown_test", 
     "platforms": [
@@ -2240,6 +2354,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c++", 
     "name": "status_test", 
     "platforms": [
@@ -2259,6 +2374,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "streaming_throughput_test", 
     "platforms": [
@@ -2277,6 +2393,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c++", 
     "name": "sync_streaming_ping_pong_test", 
     "platforms": [
@@ -2295,6 +2412,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c++", 
     "name": "sync_unary_ping_pong_test", 
     "platforms": [
@@ -2314,6 +2432,7 @@
     "cpu_cost": 100, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": true, 
     "language": "c++", 
     "name": "thread_stress_test", 
     "platforms": [
@@ -2334,6 +2453,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c89", 
     "name": "public_headers_must_be_c89", 
     "platforms": [
@@ -2354,6 +2474,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "badreq_bad_client_test", 
     "platforms": [
@@ -2374,6 +2495,7 @@
     "cpu_cost": 0.2, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "connection_prefix_bad_client_test", 
     "platforms": [
@@ -2394,6 +2516,7 @@
     "cpu_cost": 0.2, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "headers_bad_client_test", 
     "platforms": [
@@ -2414,6 +2537,7 @@
     "cpu_cost": 0.2, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "initial_settings_frame_bad_client_test", 
     "platforms": [
@@ -2434,6 +2558,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "server_registered_method_bad_client_test", 
     "platforms": [
@@ -2454,6 +2579,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "simple_request_bad_client_test", 
     "platforms": [
@@ -2474,6 +2600,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "unknown_frame_bad_client_test", 
     "platforms": [
@@ -2494,6 +2621,7 @@
     "cpu_cost": 1.0, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "window_overflow_bad_client_test", 
     "platforms": [
@@ -2513,6 +2641,7 @@
     "cpu_cost": 0.1, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "bad_ssl_alpn_test", 
     "platforms": [
@@ -2531,6 +2660,7 @@
     "cpu_cost": 0.1, 
     "exclude_configs": [], 
     "flaky": false, 
+    "gtest": false, 
     "language": "c", 
     "name": "bad_ssl_cert_test", 
     "platforms": [
diff --git a/vsprojects/vcxproj/grpc++/grpc++.vcxproj b/vsprojects/vcxproj/grpc++/grpc++.vcxproj
index c62faf33e6fc8e7098d19c42e6ed342f77edf91d..0b8c345196913fbfef1cb03f287699ddf37b7f7e 100644
--- a/vsprojects/vcxproj/grpc++/grpc++.vcxproj
+++ b/vsprojects/vcxproj/grpc++/grpc++.vcxproj
@@ -369,8 +369,6 @@
     </ClCompile>
     <ClCompile Include="$(SolutionDir)\..\src\cpp\client\insecure_credentials.cc">
     </ClCompile>
-    <ClCompile Include="$(SolutionDir)\..\src\cpp\common\alarm.cc">
-    </ClCompile>
     <ClCompile Include="$(SolutionDir)\..\src\cpp\common\call.cc">
     </ClCompile>
     <ClCompile Include="$(SolutionDir)\..\src\cpp\common\channel_arguments.cc">
diff --git a/vsprojects/vcxproj/grpc++/grpc++.vcxproj.filters b/vsprojects/vcxproj/grpc++/grpc++.vcxproj.filters
index 5f9350e76a00a708caa25bb92aab62e1d5b9a06f..0f3dccf17c5dce96580269ebaaf2dbc7656254ba 100644
--- a/vsprojects/vcxproj/grpc++/grpc++.vcxproj.filters
+++ b/vsprojects/vcxproj/grpc++/grpc++.vcxproj.filters
@@ -40,9 +40,6 @@
     <ClCompile Include="$(SolutionDir)\..\src\cpp\client\insecure_credentials.cc">
       <Filter>src\cpp\client</Filter>
     </ClCompile>
-    <ClCompile Include="$(SolutionDir)\..\src\cpp\common\alarm.cc">
-      <Filter>src\cpp\common</Filter>
-    </ClCompile>
     <ClCompile Include="$(SolutionDir)\..\src\cpp\common\call.cc">
       <Filter>src\cpp\common</Filter>
     </ClCompile>
diff --git a/vsprojects/vcxproj/grpc++_unsecure/grpc++_unsecure.vcxproj b/vsprojects/vcxproj/grpc++_unsecure/grpc++_unsecure.vcxproj
index fb4246580fd57a136610c45e3eca81dac7f563e4..2dcadbaec0c56d3e99aae6635740277300b3a673 100644
--- a/vsprojects/vcxproj/grpc++_unsecure/grpc++_unsecure.vcxproj
+++ b/vsprojects/vcxproj/grpc++_unsecure/grpc++_unsecure.vcxproj
@@ -356,8 +356,6 @@
     </ClCompile>
     <ClCompile Include="$(SolutionDir)\..\src\cpp\client\insecure_credentials.cc">
     </ClCompile>
-    <ClCompile Include="$(SolutionDir)\..\src\cpp\common\alarm.cc">
-    </ClCompile>
     <ClCompile Include="$(SolutionDir)\..\src\cpp\common\call.cc">
     </ClCompile>
     <ClCompile Include="$(SolutionDir)\..\src\cpp\common\channel_arguments.cc">
diff --git a/vsprojects/vcxproj/grpc++_unsecure/grpc++_unsecure.vcxproj.filters b/vsprojects/vcxproj/grpc++_unsecure/grpc++_unsecure.vcxproj.filters
index eeff7d3697c49bc168147e3ea53cde47f2ff0fc0..3572c651b6d117446fb032c194787c398d6d0b50 100644
--- a/vsprojects/vcxproj/grpc++_unsecure/grpc++_unsecure.vcxproj.filters
+++ b/vsprojects/vcxproj/grpc++_unsecure/grpc++_unsecure.vcxproj.filters
@@ -25,9 +25,6 @@
     <ClCompile Include="$(SolutionDir)\..\src\cpp\client\insecure_credentials.cc">
       <Filter>src\cpp\client</Filter>
     </ClCompile>
-    <ClCompile Include="$(SolutionDir)\..\src\cpp\common\alarm.cc">
-      <Filter>src\cpp\common</Filter>
-    </ClCompile>
     <ClCompile Include="$(SolutionDir)\..\src\cpp\common\call.cc">
       <Filter>src\cpp\common</Filter>
     </ClCompile>