diff --git a/src/Servers/IIS/AspNetCoreModuleV2/AspNetCore/applicationinfo.cpp b/src/Servers/IIS/AspNetCoreModuleV2/AspNetCore/applicationinfo.cpp
index 6c9f5d848269049fbb24a3acf759feaf9f69d6ab..28a5dde1c8c908adba5e06e7d8e17b6a861e6449 100644
--- a/src/Servers/IIS/AspNetCoreModuleV2/AspNetCore/applicationinfo.cpp
+++ b/src/Servers/IIS/AspNetCoreModuleV2/AspNetCore/applicationinfo.cpp
@@ -133,6 +133,30 @@ APPLICATION_INFO::CreateApplication(IHttpContext& pHttpContext)
 HRESULT
 APPLICATION_INFO::TryCreateApplication(IHttpContext& pHttpContext, const ShimOptions& options)
 {
+    const auto startupEvent = Environment::GetEnvironmentVariableValue(L"ASPNETCORE_STARTUP_SUSPEND_EVENT");
+    if (startupEvent.has_value())
+    {
+        LOG_INFOF(L"Startup suspend event %ls", startupEvent.value().c_str());
+
+        HandleWrapper<NullHandleTraits> eventHandle = OpenEvent(SYNCHRONIZE, false, startupEvent.value().c_str());
+
+        if (eventHandle == nullptr)
+        {
+            LOG_INFOF(L"Unable to open startup suspend event");
+        }
+        else
+        {
+            auto const suspendedEventName = startupEvent.value() + L"_suspended";
+
+            HandleWrapper<NullHandleTraits> suspendedEventHandle = OpenEvent(EVENT_MODIFY_STATE, false, suspendedEventName.c_str());
+            if (suspendedEventHandle != nullptr)
+            {
+                LOG_LAST_ERROR_IF(!SetEvent(suspendedEventHandle));
+            }
+            LOG_LAST_ERROR_IF(WaitForSingleObject(eventHandle, INFINITE) != WAIT_OBJECT_0);
+        }
+
+    }
     RETURN_IF_FAILED(m_handlerResolver.GetApplicationFactory(*pHttpContext.GetApplication(), m_pApplicationFactory, options));
     LOG_INFO(L"Creating handler application");
 
diff --git a/src/Servers/IIS/IIS/test/Common.FunctionalTests/Inprocess/StartupTests.cs b/src/Servers/IIS/IIS/test/Common.FunctionalTests/Inprocess/StartupTests.cs
index 0390b5b3df2f127432f41e278dc577b4621676cb..55d4cfc170ddc351127bf7566b6e38a126bd40de 100644
--- a/src/Servers/IIS/IIS/test/Common.FunctionalTests/Inprocess/StartupTests.cs
+++ b/src/Servers/IIS/IIS/test/Common.FunctionalTests/Inprocess/StartupTests.cs
@@ -7,6 +7,7 @@ using System.IO;
 using System.Linq;
 using System.Net;
 using System.Text.RegularExpressions;
+using System.Threading;
 using System.Threading.Tasks;
 using System.Xml.Linq;
 using Microsoft.AspNetCore.Server.IIS.FunctionalTests.Utilities;
@@ -520,6 +521,41 @@ namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
             Assert.Equal(deploymentResult.ContentRoot + "\\", await deploymentResult.HttpClient.GetStringAsync("/ASPNETCORE_IIS_PHYSICAL_PATH"));
         }
 
+        [ConditionalFact]
+        [RequiresNewShim]
+        [RequiresIIS(IISCapability.PoolEnvironmentVariables)]
+        public async Task StartupIsSuspendedWhenEventIsUsed()
+        {
+            var deploymentParameters = _fixture.GetBaseDeploymentParameters();
+            deploymentParameters.ApplicationType = ApplicationType.Standalone;
+            deploymentParameters.EnvironmentVariables["ASPNETCORE_STARTUP_SUSPEND_EVENT"] = "ANCM_TestEvent";
+
+            var eventPrefix = deploymentParameters.ServerType == ServerType.IISExpress ? "" : "Global\\";
+
+            var startWaitHandle = new EventWaitHandle(false, EventResetMode.ManualReset, eventPrefix + "ANCM_TestEvent");
+            var suspendedWaitHandle = new EventWaitHandle(false, EventResetMode.ManualReset, eventPrefix + "ANCM_TestEvent_suspended");
+
+            var deploymentResult = await DeployAsync(deploymentParameters);
+
+            var request = deploymentResult.AssertStarts();
+
+            Assert.True(suspendedWaitHandle.WaitOne(TimeoutExtensions.DefaultTimeoutValue));
+
+            // didn't figure out a better way to check that ANCM is waiting to start
+            var applicationDll = Path.Combine(deploymentResult.ContentRoot, "InProcessWebSite.dll");
+            var handlerDll = Path.Combine(deploymentResult.ContentRoot, "aspnetcorev2_inprocess.dll");
+            // Make sure application dll is not locked
+            File.WriteAllBytes(applicationDll, File.ReadAllBytes(applicationDll));
+            // Make sure handler dll is not locked
+            File.WriteAllBytes(handlerDll, File.ReadAllBytes(handlerDll));
+            // Make sure request is not completed
+            Assert.False(request.IsCompleted);
+
+            startWaitHandle.Set();
+
+            await request;
+        }
+
         private static void MoveApplication(
             IISDeploymentParameters parameters,
             string subdirectory)