diff --git a/indra/llrender/llshadermgr.cpp b/indra/llrender/llshadermgr.cpp
index b53ab6502efc3cc76176341b9fee8eed0c3944ce..18f796b3816122394a2b994fc17d8805c477c94e 100644
--- a/indra/llrender/llshadermgr.cpp
+++ b/indra/llrender/llshadermgr.cpp
@@ -604,11 +604,6 @@ GLuint LLShaderMgr::loadShaderFile(const std::string& filename, S32 & shader_lev
         extra_code_text[extra_code_count++] = strdup("#define VERTEX_SHADER 1\n");
     }
 
-    if (sMirrorsEnabled)
-    {
-        extra_code_text[extra_code_count++] = strdup("#define HERO_PROBES 1\n");
-    }
-
     // Use alpha float to store bit flags
     // See: C++: addDeferredAttachment(), shader: frag_data[2]
     extra_code_text[extra_code_count++] = strdup("#define GBUFFER_FLAG_SKIP_ATMOS   0.0 \n"); // atmo kill
@@ -617,6 +612,12 @@ GLuint LLShaderMgr::loadShaderFile(const std::string& filename, S32 & shader_lev
     extra_code_text[extra_code_count++] = strdup("#define GBUFFER_FLAG_HAS_HDRI      1.0\n");  // bit 2
     extra_code_text[extra_code_count++] = strdup("#define GET_GBUFFER_FLAG(flag)    (abs(norm.w-flag)< 0.1)\n");
 
+    for (auto iter = LLGLSLShader::sGlobalDefines.begin(); iter != LLGLSLShader::sGlobalDefines.end(); ++iter)
+    {
+        std::string define = "#define " + iter->first + " " + iter->second + "\n";
+        extra_code_text[extra_code_count++] = (GLchar*)strdup(define.c_str());
+    }
+
     if (defines)
     {
         for (auto iter = defines->begin(); iter != defines->end(); ++iter)
diff --git a/indra/newview/llfeaturemanager.cpp b/indra/newview/llfeaturemanager.cpp
index 6494e1551c6b00230f681e0c3833c267e8b17033..a1012b5db00a3ebc648eddfa3ff66bb39004f196 100644
--- a/indra/newview/llfeaturemanager.cpp
+++ b/indra/newview/llfeaturemanager.cpp
@@ -602,8 +602,9 @@ void LLFeatureManager::setGraphicsLevel(U32 level, bool skipFeatures)
     applyFeatures(skipFeatures);
 
     LLViewerShaderMgr::sSkipReload = false;
-    LLViewerShaderMgr::instance()->setShaders();
     gPipeline.refreshCachedSettings();
+    gPipeline.releaseGLBuffers();
+    LLViewerShaderMgr::instance()->setShaders();
 }
 
 void LLFeatureManager::applyBaseMasks()
diff --git a/indra/newview/llviewercontrol.cpp b/indra/newview/llviewercontrol.cpp
index 9043f960b3392e2de93cf7cf5a50f600b10b2e33..d4e1be0b0b067161fd7f4bb8e6981fb45301126c 100644
--- a/indra/newview/llviewercontrol.cpp
+++ b/indra/newview/llviewercontrol.cpp
@@ -177,6 +177,7 @@ static bool handleSetShaderChanged(const LLSD& newvalue)
     }
 
     // else, leave terrain detail as is
+    gPipeline.releaseGLBuffers();
     LLViewerShaderMgr::instance()->setShaders();
     return true;
 }
@@ -222,7 +223,6 @@ bool handleRenderTransparentWaterChanged(const LLSD& newvalue)
     {
         gPipeline.updateRenderTransparentWater();
         gPipeline.releaseGLBuffers();
-        gPipeline.createGLBuffers();
         LLViewerShaderMgr::instance()->setShaders();
     }
     LLWorld::getInstance()->updateWaterObjects();
@@ -448,7 +448,6 @@ static bool handleReflectionProbeDetailChanged(const LLSD& newvalue)
     {
         LLPipeline::refreshCachedSettings();
         gPipeline.releaseGLBuffers();
-        gPipeline.createGLBuffers();
         LLViewerShaderMgr::instance()->setShaders();
         gPipeline.mReflectionMapManager.reset();
         gPipeline.mHeroProbeManager.reset();
@@ -819,6 +818,7 @@ void settings_setup_listeners()
     setting_setup_signal_listener(gSavedSettings, "RenderReflectionProbeDetail", handleReflectionProbeDetailChanged);
     setting_setup_signal_listener(gSavedSettings, "RenderReflectionsEnabled", handleReflectionProbeDetailChanged);
     setting_setup_signal_listener(gSavedSettings, "RenderScreenSpaceReflections", handleReflectionProbeDetailChanged);
+    setting_setup_signal_listener(gSavedSettings, "RenderMirrors", handleHeroProbeResolutionChanged);
     setting_setup_signal_listener(gSavedSettings, "RenderHeroProbeResolution", handleHeroProbeResolutionChanged);
     setting_setup_signal_listener(gSavedSettings, "RenderShaderCacheEnabled", handleSetShaderChanged);
     setting_setup_signal_listener(gSavedSettings, "RenderShadowDetail", handleSetShaderChanged);
diff --git a/indra/newview/llviewershadermgr.cpp b/indra/newview/llviewershadermgr.cpp
index 470db5218512555b11d32e831c835d380f71190d..a886ae6ea88e0272f156f1a72fe15e676ece4d10 100644
--- a/indra/newview/llviewershadermgr.cpp
+++ b/indra/newview/llviewershadermgr.cpp
@@ -411,8 +411,6 @@ void LLViewerShaderMgr::setShaders()
 
     mShaderList.clear();
 
-    LLShaderMgr::sMirrorsEnabled = LLPipeline::RenderMirrors;
-
     if (!gGLManager.mHasRequirements)
     {
         // Viewer will show 'hardware requirements' warning later
@@ -665,6 +663,8 @@ std::string LLViewerShaderMgr::loadBasicShaders()
 
     bool has_reflection_probes = gSavedSettings.getBOOL("RenderReflectionsEnabled") && gGLManager.mGLVersion > 3.99f;
 
+    bool has_mirrors = gSavedSettings.getBOOL("RenderMirrors") && gGLManager.mGLVersion > 3.99f;
+
     S32 probe_level = llclamp(gSavedSettings.getS32("RenderReflectionProbeLevel"), 0, 3);
 
     S32 shadow_detail            = gSavedSettings.getS32("RenderShadowDetail");
@@ -690,6 +690,11 @@ std::string LLViewerShaderMgr::loadBasicShaders()
         attribs["REF_SAMPLE_COUNT"] = "32";
     }
 
+    if (has_mirrors)
+    {
+        attribs["HERO_PROBES"] = "1";
+    }
+
     { // PBR terrain
         const S32 mapping = clamp_terrain_mapping(gSavedSettings.getS32("RenderTerrainPBRPlanarSampleCount"));
         attribs["TERRAIN_PLANAR_TEXTURE_SAMPLE_COUNT"] = llformat("%d", mapping);
diff --git a/indra/newview/pipeline.cpp b/indra/newview/pipeline.cpp
index 48a2310b25b4f6af036d2e8f28dd03c0d044b8c8..3620e82271edce2e3a5c1ba646aefb71f373d0ac 100644
--- a/indra/newview/pipeline.cpp
+++ b/indra/newview/pipeline.cpp
@@ -1132,12 +1132,7 @@ void LLPipeline::refreshCachedSettings()
     RenderScreenSpaceReflectionAdaptiveStepMultiplier = gSavedSettings.getF32("RenderScreenSpaceReflectionAdaptiveStepMultiplier");
     RenderScreenSpaceReflectionGlossySamples = gSavedSettings.getS32("RenderScreenSpaceReflectionGlossySamples");
     RenderBufferVisualization = gSavedSettings.getS32("RenderBufferVisualization");
-    if (gSavedSettings.getBOOL("RenderMirrors") != (BOOL)RenderMirrors)
-    {
-        RenderMirrors = gSavedSettings.getBOOL("RenderMirrors");
-        LLViewerShaderMgr::instance()->clearShaderCache();
-        LLViewerShaderMgr::instance()->setShaders();
-    }
+    RenderMirrors = gSavedSettings.getBOOL("RenderMirrors");
     RenderHeroProbeUpdateRate = gSavedSettings.getS32("RenderHeroProbeUpdateRate");
     RenderHeroProbeConservativeUpdateMultiplier = gSavedSettings.getS32("RenderHeroProbeConservativeUpdateMultiplier");