diff --git a/src/third_party/starboard/rdk/shared/application_rdk.cc b/src/third_party/starboard/rdk/shared/application_rdk.cc
index cbfa0f7..daebcb9 100644
--- a/src/third_party/starboard/rdk/shared/application_rdk.cc
+++ b/src/third_party/starboard/rdk/shared/application_rdk.cc
@@ -433,6 +433,18 @@
   return kSbTimeSecond;
 }
 
+void Application::InjectAccessibilitySettingsChanged() {
+  Inject(new Event(kSbEventTypeAccessibilitySettingsChanged, NULL, NULL));
+}
+
+void Application::InjectAccessibilityCaptionSettingsChanged() {
+  Inject(new Event(kSbEventTypeAccessibilityCaptionSettingsChanged, NULL, NULL));
+}
+
+void Application::InjectAccessibilityTextToSpeechSettingsChanged() {
+  Inject(new Event(kSbEventTypeAccessibilityTextToSpeechSettingsChanged, NULL, NULL));
+}
+
 }  // namespace shared
 }  // namespace rdk
 }  // namespace starboard
diff --git a/src/third_party/starboard/rdk/shared/application_rdk.h b/src/third_party/starboard/rdk/shared/application_rdk.h
index 1bd3dda..b61c8c8 100644
--- a/src/third_party/starboard/rdk/shared/application_rdk.h
+++ b/src/third_party/starboard/rdk/shared/application_rdk.h
@@ -78,6 +78,10 @@
   bool IsStartImmediate() override { return !HasPreloadSwitch(); }
   bool IsPreloadImmediate() override { return HasPreloadSwitch(); }
 
+  void InjectAccessibilitySettingsChanged();
+  void InjectAccessibilityCaptionSettingsChanged();
+  void InjectAccessibilityTextToSpeechSettingsChanged();
+
  protected:
   // --- Application overrides ---
   void Initialize() override;
diff --git a/src/third_party/starboard/rdk/shared/rdkservices.cc b/src/third_party/starboard/rdk/shared/rdkservices.cc
index 215ef9f..8d86260 100644
--- a/src/third_party/starboard/rdk/shared/rdkservices.cc
+++ b/src/third_party/starboard/rdk/shared/rdkservices.cc
@@ -72,7 +72,7 @@
 const char kNetworkCallsign[] = "org.rdk.Network.1";
 const char kTTSCallsign[] = "org.rdk.TextToSpeech.1";
 const char kAuthServiceCallsign[] = "org.rdk.AuthService.1";
-
+const char kUserSetingsCallsign[] = "org.rdk.UserSettings.1";
 const char kDeviceInfoCallsign[] = "DeviceInfo.1";
 const char kBluetoothCallsign[] = "org.rdk.Bluetooth.1";
 
@@ -241,191 +241,12 @@
 
 SB_ONCE_INITIALIZE_FUNCTION(DeviceIdImpl, GetDeviceIdImpl);
 
-struct TextToSpeechImpl {
-private:
-  ::starboard::atomic_bool is_enabled_ { false };
-  ::starboard::atomic_bool needs_refresh_ { true };
-  ::starboard::atomic_bool did_subscribe_ { false };
-  int64_t speech_id_ { -1 };
-  int32_t speech_request_num_ { 0 };
-  ServiceLink tts_link_ { kTTSCallsign };
-  ::starboard::Mutex mutex_;
-  ::starboard::ConditionVariable condition_ { mutex_ };
-
-  std::string client_id_;
-  struct IsTTSEnabledInfo : public Core::JSON::Container {
-    IsTTSEnabledInfo()
-      : Core::JSON::Container() {
-      Add(_T("isenabled"), &IsEnabled);
-    }
-    IsTTSEnabledInfo(const IsTTSEnabledInfo&) = delete;
-    IsTTSEnabledInfo& operator=(const IsTTSEnabledInfo&) = delete;
-
-    Core::JSON::Boolean IsEnabled;
-  };
-
-  struct SpeakResult : public Core::JSON::Container {
-    SpeakResult()
-      : Core::JSON::Container()
-      , SpeechId(-1) {
-      Add(_T("speechid"), &SpeechId);
-    }
-    SpeakResult(const SpeakResult&) = delete;
-    SpeakResult& operator=(const SpeakResult&) = delete;
-
-    Core::JSON::DecSInt64 SpeechId;
-  };
-
-  struct StateInfo : public Core::JSON::Container {
-    StateInfo()
-      : Core::JSON::Container()
-      , State(false) {
-      Add(_T("state"), &State);
-    }
-    StateInfo(const StateInfo& other)
-      : Core::JSON::Container()
-      , State(other.State) {
-      Add(_T("state"), &State);
-    }
-    StateInfo& operator=(const StateInfo&) = delete;
-
-    Core::JSON::Boolean State;
-  };
-
-  void OnCancelResult(const Core::JSON::String&, const Core::JSONRPC::Error*) {
-  }
-
-  void OnStateChanged(const StateInfo& info) {
-    is_enabled_.store( info.State.Value() );
-  }
-
-  void OnSpeakResult(const SpeakResult& result, const Core::JSONRPC::Error* err) {
-    ::starboard::ScopedLock lock(mutex_);
-    if (err) {
-      SB_LOG(ERROR)
-          << "TTS speak request failed. Error code: "
-          << err->Code.Value()
-          << " message: "
-          << err->Text.Value();
-      speech_id_ = -1;
-    }
-    else {
-      speech_id_ = result.SpeechId;
-    }
-    --speech_request_num_;
-    condition_.Broadcast();
-  }
-
-public:
-  TextToSpeechImpl() = default;
-
-  void Speak(const std::string &text) {
-    Refresh();
-    if (!is_enabled_.load())
-      return;
-
-    JsonObject params;
-    params.Set(_T("text"), text);
-    params.Set(_T("callsign"), client_id_ );
-
-    uint64_t rc = tts_link_.Dispatch(kDefaultTimeoutMs, "speak", params, &TextToSpeechImpl::OnSpeakResult, this);
-    if (Core::ERROR_NONE == rc) {
-      ::starboard::ScopedLock lock(mutex_);
-      ++speech_request_num_;
-    }
-  }
-
-  void Cancel() {
-    Refresh();
-    if (!is_enabled_.load())
-      return;
-
-    int64_t speechId = -1;
-
-    {
-      ::starboard::ScopedLock lock(mutex_);
-      if (speech_request_num_ != 0) {
-        if (!condition_.WaitTimed(kSbTimeMillisecond) || speech_request_num_ != 0)
-          return;
-      }
-      speechId = speech_id_;
-    }
-
-    if (speechId < 0)
-      return;
-
-    JsonObject params;
-    params.Set(_T("speechid"), speechId);
-
-    tts_link_.Dispatch(kDefaultTimeoutMs, "cancel", params, &TextToSpeechImpl::OnCancelResult, this);
-  }
-
-  bool IsEnabled() {
-    Refresh();
-    return is_enabled_.load();
-  }
-
-  void Refresh() {
-    if (!needs_refresh_.load())
-      return;
-
-    uint32_t rc;
-    if (!did_subscribe_.load()) {
-      bool old_val = did_subscribe_.exchange(true);
-      if (old_val == false) {
-        rc = tts_link_.Subscribe<StateInfo>(kDefaultTimeoutMs, "onttsstatechanged", &TextToSpeechImpl::OnStateChanged, this);
-        if (Core::ERROR_UNAVAILABLE == rc || kPriviligedRequestErrorCode == rc) {
-          needs_refresh_.store(false);
-          SB_LOG(ERROR) << "Failed to subscribe to '" << kTTSCallsign
-                        << ".onstatechanged' event, rc=" << rc
-                        << " ( " << Core::ErrorToString(rc) << " )";
-          return;
-        }
-        if (Core::ERROR_NONE != rc && Core::ERROR_DUPLICATE_KEY != rc) {
-          did_subscribe_.store(false);
-          SB_LOG(ERROR) << "Failed to subscribe to '" << kTTSCallsign
-                        << ".onstatechanged' event, rc=" << rc
-                        << " ( " << Core::ErrorToString(rc) << " )."
-                        << " Going to try again next time.";
-          return;
-        }
-      }
-    }
-
-    IsTTSEnabledInfo info;
-    rc = tts_link_.Get(kDefaultTimeoutMs, "isttsenabled", info);
-    if (Core::ERROR_NONE == rc) {
-      is_enabled_.store( info.IsEnabled.Value() );
-    }
-    if (Core::SystemInfo::GetEnvironment(_T("CLIENT_IDENTIFIER"), client_id_) == true) {
-      std::string::size_type pos = client_id_.find(',');
-      if (pos != std::string::npos)
-        client_id_.erase(pos, std::string::npos);
-    } else {
-        client_id_ = "Cobalt";
-    }
-
-    needs_refresh_.store(false);
-  }
-
-  void Teardown() {
-    if (did_subscribe_.load()) {
-      tts_link_.Unsubscribe(kDefaultTimeoutMs, "onttsstatechanged");
-      did_subscribe_.store(false);
-    }
-    tts_link_.Teardown();
-    needs_refresh_.store(true);
-    is_enabled_.store(false);
-  }
-};
-
-SB_ONCE_INITIALIZE_FUNCTION(TextToSpeechImpl, GetTextToSpeech);
-
 struct AccessibilityImpl {
 private:
   ::starboard::Mutex mutex_;
   SbAccessibilityDisplaySettings display_settings_ { };
   SbAccessibilityCaptionSettings caption_settings_ { };
+  bool is_voice_guidance_enabled_ { false };
 
 public:
   AccessibilityImpl() {
@@ -448,7 +269,6 @@
   }
 
   void SetSettings(const std::string& json) {
-
     SB_LOG(INFO) << "Updating accessibility settings: " << json;
 
     JsonData::Accessibility::AccessibilityData settings;
@@ -461,6 +281,9 @@
 
     ::starboard::ScopedLock lock(mutex_);
 
+    bool was_cc_enabled = caption_settings_.is_enabled;
+    bool was_highcontrast_enabled = display_settings_.is_high_contrast_text_enabled;
+
     memset(&display_settings_, 0, sizeof(display_settings_));
     memset(&caption_settings_, 0, sizeof(caption_settings_));
 
@@ -512,6 +335,14 @@
       display_settings_.is_high_contrast_text_enabled =
         settings.TextDisplay.IsHighContrastTextEnabled.Value();
     }
+
+    if (auto* app = Application::Get(); app != nullptr) {
+      if (was_cc_enabled != caption_settings_.is_enabled)
+        app->InjectAccessibilityCaptionSettingsChanged();
+
+      if (was_highcontrast_enabled != display_settings_.is_high_contrast_text_enabled)
+        app->InjectAccessibilitySettingsChanged();
+    }
   }
 
   bool GetSettings(std::string& out_json) {
@@ -567,10 +398,226 @@
     return false;
   }
 
+  void SetCaptionEnabled(bool enabled, bool notify_on_change = true) {
+    {
+      ::starboard::ScopedLock lock(mutex_);
+       notify_on_change &= (caption_settings_.is_enabled != enabled);
+       caption_settings_.is_enabled = enabled;
+    }
+    if (notify_on_change && Application::Get()) {
+      SB_LOG(INFO) << "Accessibility closed caption setting changed, enabled = " << enabled;
+      Application::Get()->InjectAccessibilityCaptionSettingsChanged();
+    }
+  }
+
+  void SetHighContrastEnabled(bool enabled, bool notify_on_change = true) {
+    {
+      ::starboard::ScopedLock lock(mutex_);
+      notify_on_change &= (display_settings_.is_high_contrast_text_enabled != enabled);
+      display_settings_.is_high_contrast_text_enabled = enabled;
+    }
+    if (notify_on_change && Application::Get()) {
+      SB_LOG(INFO) << "Accessibility high contrast text setting changed, enabled = " << enabled;
+      Application::Get()->InjectAccessibilitySettingsChanged();
+    }
+  }
+
+  void SetVoiceGuidanceEnabled(bool enabled, bool notify_on_change = true) {
+    {
+      ::starboard::ScopedLock lock(mutex_);
+      notify_on_change &= (is_voice_guidance_enabled_ != enabled);
+      is_voice_guidance_enabled_ = enabled;
+    }
+    if (notify_on_change && Application::Get()) {
+      SB_LOG(INFO) << "Accessibility voice guidance setting changed, enabled = " << enabled;
+      Application::Get()->InjectAccessibilityTextToSpeechSettingsChanged();
+    }
+  }
+
+  bool GetVoiceGuidanceEnabled() const {
+    ::starboard::ScopedLock lock(mutex_);
+    return is_voice_guidance_enabled_;
+  }
 };
 
 SB_ONCE_INITIALIZE_FUNCTION(AccessibilityImpl, GetAccessibility);
 
+struct TextToSpeechImpl {
+private:
+  ::starboard::atomic_bool is_enabled_ { false };
+  ::starboard::atomic_bool needs_refresh_ { true };
+  ::starboard::atomic_bool did_subscribe_ { false };
+  int64_t speech_id_ { -1 };
+  int32_t speech_request_num_ { 0 };
+  ServiceLink tts_link_ { kTTSCallsign };
+  ::starboard::Mutex mutex_;
+  ::starboard::ConditionVariable condition_ { mutex_ };
+  std::string client_id_;
+
+  struct IsTTSEnabledInfo : public Core::JSON::Container {
+    IsTTSEnabledInfo()
+      : Core::JSON::Container() {
+      Add(_T("isenabled"), &IsEnabled);
+    }
+    IsTTSEnabledInfo(const IsTTSEnabledInfo&) = delete;
+    IsTTSEnabledInfo& operator=(const IsTTSEnabledInfo&) = delete;
+
+    Core::JSON::Boolean IsEnabled;
+  };
+
+  struct SpeakResult : public Core::JSON::Container {
+    SpeakResult()
+      : Core::JSON::Container()
+      , SpeechId(-1) {
+      Add(_T("speechid"), &SpeechId);
+    }
+    SpeakResult(const SpeakResult&) = delete;
+    SpeakResult& operator=(const SpeakResult&) = delete;
+
+    Core::JSON::DecSInt64 SpeechId;
+  };
+
+  struct StateInfo : public Core::JSON::Container {
+    StateInfo()
+      : Core::JSON::Container()
+      , State(false) {
+      Add(_T("state"), &State);
+    }
+    StateInfo(const StateInfo& other)
+      : Core::JSON::Container()
+      , State(other.State) {
+      Add(_T("state"), &State);
+    }
+    StateInfo& operator=(const StateInfo&) = delete;
+
+    Core::JSON::Boolean State;
+  };
+
+  void OnCancelResult(const Core::JSON::String&, const Core::JSONRPC::Error*) {
+  }
+
+  void OnStateChanged(const StateInfo& info) {
+    is_enabled_.store( info.State.Value() );
+    GetAccessibility()->SetVoiceGuidanceEnabled( info.State.Value() );
+  }
+
+  void OnSpeakResult(const SpeakResult& result, const Core::JSONRPC::Error* err) {
+    ::starboard::ScopedLock lock(mutex_);
+    if (err) {
+      SB_LOG(ERROR)
+          << "TTS speak request failed. Error code: "
+          << err->Code.Value()
+          << " message: "
+          << err->Text.Value();
+      speech_id_ = -1;
+    }
+    else {
+      speech_id_ = result.SpeechId;
+    }
+    --speech_request_num_;
+    condition_.Broadcast();
+  }
+
+public:
+  TextToSpeechImpl() = default;
+
+  void Speak(const std::string &text) {
+    if (!IsEnabled())
+      return;
+
+    JsonObject params;
+    params.Set(_T("text"), text);
+    params.Set(_T("callsign"), client_id_ );
+
+    uint64_t rc = tts_link_.Dispatch(kDefaultTimeoutMs, "speak", params, &TextToSpeechImpl::OnSpeakResult, this);
+    if (Core::ERROR_NONE == rc) {
+      ::starboard::ScopedLock lock(mutex_);
+      ++speech_request_num_;
+    }
+  }
+
+  void Cancel() {
+    int64_t speechId = -1;
+
+    {
+      ::starboard::ScopedLock lock(mutex_);
+      if (speech_request_num_ != 0) {
+        if (!condition_.WaitTimed(kSbTimeMillisecond) || speech_request_num_ != 0)
+          return;
+      }
+      speechId = std::exchange(speech_id_, -1);
+    }
+
+    if (speechId < 0)
+      return;
+
+    JsonObject params;
+    params.Set(_T("speechid"), speechId);
+
+    tts_link_.Dispatch(kDefaultTimeoutMs, "cancel", params, &TextToSpeechImpl::OnCancelResult, this);
+  }
+
+  bool IsEnabled() {
+    Refresh();
+    return is_enabled_.load() || GetAccessibility()->GetVoiceGuidanceEnabled();
+  }
+
+  void Refresh() {
+    if (!needs_refresh_.load())
+      return;
+
+    uint32_t rc;
+    if (!did_subscribe_.load()) {
+      bool old_val = did_subscribe_.exchange(true);
+      if (old_val == false) {
+        rc = tts_link_.Subscribe<StateInfo>(kDefaultTimeoutMs, "onttsstatechanged", &TextToSpeechImpl::OnStateChanged, this);
+        if (Core::ERROR_UNAVAILABLE == rc || kPriviligedRequestErrorCode == rc) {
+          needs_refresh_.store(false);
+          SB_LOG(ERROR) << "Failed to subscribe to '" << kTTSCallsign
+                        << ".onstatechanged' event, rc=" << rc
+                        << " ( " << Core::ErrorToString(rc) << " )";
+          return;
+        }
+        if (Core::ERROR_NONE != rc && Core::ERROR_DUPLICATE_KEY != rc) {
+          did_subscribe_.store(false);
+          SB_LOG(ERROR) << "Failed to subscribe to '" << kTTSCallsign
+                        << ".onstatechanged' event, rc=" << rc
+                        << " ( " << Core::ErrorToString(rc) << " )."
+                        << " Going to try again next time.";
+          return;
+        }
+      }
+    }
+
+    IsTTSEnabledInfo info;
+    rc = tts_link_.Get(kDefaultTimeoutMs, "isttsenabled", info);
+    if (Core::ERROR_NONE == rc) {
+      is_enabled_.store( info.IsEnabled.Value() );
+    }
+    if (Core::SystemInfo::GetEnvironment(_T("CLIENT_IDENTIFIER"), client_id_) == true) {
+      std::string::size_type pos = client_id_.find(',');
+      if (pos != std::string::npos)
+        client_id_.erase(pos, std::string::npos);
+    } else {
+      client_id_ = "Cobalt";
+    }
+
+    needs_refresh_.store(false);
+  }
+
+  void Teardown() {
+    if (did_subscribe_.load()) {
+      tts_link_.Unsubscribe(kDefaultTimeoutMs, "onttsstatechanged");
+      did_subscribe_.store(false);
+    }
+    tts_link_.Teardown();
+    needs_refresh_.store(true);
+    is_enabled_.store(false);
+  }
+};
+
+SB_ONCE_INITIALIZE_FUNCTION(TextToSpeechImpl, GetTextToSpeech);
+
 struct SystemPropertiesImpl {
   struct SystemPropertiesData : public Core::JSON::Container {
     SystemPropertiesData()
@@ -1462,6 +1509,148 @@
   return !out.empty();
 }
 
+struct UserSettingsImpl {
+private:
+  ::starboard::Mutex mutex_;
+  std::vector<std::string> subscriptions_ { };
+  bool needs_refresh_ { true };
+  ServiceLink link_ { kUserSetingsCallsign };
+
+  struct StateChangedInfo : public Core::JSON::Container {
+    StateChangedInfo()
+      : Core::JSON::Container()
+      , Enabled(false) {
+      Add(_T("enabled"), &Enabled);
+    }
+    StateChangedInfo(const StateChangedInfo& other)
+      : Core::JSON::Container()
+      , Enabled(other.Enabled) {
+      Add(_T("enabled"), &Enabled);
+    }
+    StateChangedInfo& operator=(const StateChangedInfo&) = delete;
+
+    Core::JSON::Boolean Enabled;
+  };
+
+  void OnVoiceGuidanceChanged(const StateChangedInfo& info) {
+    bool is_voice_guidance_enabled = info.Enabled.Value();
+    SB_LOG(INFO) << "User setting changed. voice guidance enabled = " << is_voice_guidance_enabled;
+    GetAccessibility()->SetVoiceGuidanceEnabled(is_voice_guidance_enabled);
+  };
+
+  void OnHighContrastChanged(const StateChangedInfo& info) {
+    bool is_highcontrast_enabled = info.Enabled.Value();
+    SB_LOG(INFO) << "User setting changed. highcontrast enabled = " << is_highcontrast_enabled;
+    GetAccessibility()->SetHighContrastEnabled(is_highcontrast_enabled);
+  };
+
+  void OnCaptionsChanged(const StateChangedInfo& info) {
+    bool is_cc_enabled = info.Enabled.Value();
+    SB_LOG(INFO) << "User setting changed. cc enabled = " << is_cc_enabled;
+    GetAccessibility()->SetCaptionEnabled(is_cc_enabled);
+  };
+
+  bool RefreshSubscriptions() {
+    using NotificationHandlerCb = void(UserSettingsImpl::*)(const StateChangedInfo&);
+
+    const std::map<std::string, NotificationHandlerCb> kNotificationHandlers = {
+      {"onVoiceGuidanceChanged", &UserSettingsImpl::OnVoiceGuidanceChanged },
+      {"onHighContrastChanged", &UserSettingsImpl::OnHighContrastChanged },
+      {"onCaptionsChanged", &UserSettingsImpl::OnCaptionsChanged },
+    };
+
+    uint32_t rc;
+
+    mutex_.DCheckAcquired();
+
+    for (const auto& kv : kNotificationHandlers) {
+      const auto& name = kv.first;
+      const auto& callback = kv.second;
+
+      if (std::find(subscriptions_.begin(), subscriptions_.end(), name)
+          != subscriptions_.end())
+        continue;
+
+      rc = link_.Subscribe<StateChangedInfo>(
+        kDefaultTimeoutMs, name, callback, this);
+
+      if (Core::ERROR_UNAVAILABLE == rc || kPriviligedRequestErrorCode == rc) {
+        needs_refresh_ = false;
+        SB_LOG(ERROR) << "Failed to subscribe to '" << kUserSetingsCallsign
+                      << "." << name << "' event, rc = " << rc
+                      << " ( " << Core::ErrorToString(rc) << " )";
+        return false;
+      }
+
+      if (Core::ERROR_NONE != rc && Core::ERROR_DUPLICATE_KEY != rc) {
+        SB_LOG(ERROR) << "Failed to subscribe to '" << kUserSetingsCallsign
+                      << "." << name << "' event, rc = " << rc
+                      << " ( " << Core::ErrorToString(rc) << " ).";
+        continue;
+      }
+
+      subscriptions_.push_back(name);
+    }
+
+    return true;
+  }
+
+public:
+  UserSettingsImpl() = default;
+
+  void Refresh() {
+    ::starboard::ScopedLock lock(mutex_);
+    if (!needs_refresh_)
+      return;
+
+    if (!RefreshSubscriptions())
+      return;
+
+    bool is_voice_guidance_enabled = false;
+    bool is_cc_enabled = false;
+    bool is_highcontrast_enabled = false;
+
+    const std::map<std::string, bool*> kSettings = {
+      {"getVoiceGuidance", &is_voice_guidance_enabled},
+      {"getHighContrast", &is_highcontrast_enabled},
+      {"getCaptions", &is_cc_enabled},
+    };
+
+    for (const auto& kv: kSettings) {
+      uint32_t rc;
+      Core::JSON::Boolean result;
+
+      rc = link_.Get(kDefaultTimeoutMs, kv.first, result);
+
+      if (Core::ERROR_NONE == rc) {
+        SB_LOG(INFO) << "User setting: " << kv.first << " = " << result.Value();
+        (*kv.second) = result.Value();
+      } else {
+        SB_LOG(ERROR) << "Failed to get user setting '" << kv.first<< ", rc=" << rc
+                      << " ( " << Core::ErrorToString(rc) << " ).";
+      }
+    }
+
+    needs_refresh_ = false;
+
+    auto *accessibility = GetAccessibility();
+    accessibility->SetVoiceGuidanceEnabled(is_voice_guidance_enabled, false);
+    accessibility->SetCaptionEnabled(is_cc_enabled, false);
+    accessibility->SetHighContrastEnabled(is_highcontrast_enabled, false);
+  }
+
+  void Teardown() {
+    ::starboard::ScopedLock lock(mutex_);
+    for (const auto& subscription : subscriptions_)
+      link_.Unsubscribe(kDefaultTimeoutMs, subscription.c_str());
+    link_.Teardown();
+    needs_refresh_ = true;
+    subscriptions_.clear();
+  }
+};
+
+SB_ONCE_INITIALIZE_FUNCTION(UserSettingsImpl, GetUserSettings);
+
 }  // namespace
 
 ResolutionInfo DisplayInfo::GetResolution() {
@@ -1497,6 +1686,7 @@
 }
 
 bool TextToSpeech::IsEnabled() {
+  GetUserSettings()->Refresh();
   return GetTextToSpeech()->IsEnabled();
 }
 
@@ -1505,10 +1695,12 @@
 }
 
 bool Accessibility::GetCaptionSettings(SbAccessibilityCaptionSettings* out) {
+  GetUserSettings()->Refresh();
   return GetAccessibility()->GetCaptionSettings(out);
 }
 
 bool Accessibility::GetDisplaySettings(SbAccessibilityDisplaySettings* out) {
+  GetUserSettings()->Refresh();
   return GetAccessibility()->GetDisplaySettings(out);
 }
 
@@ -1601,6 +1793,7 @@
   GetTextToSpeech()->Teardown();
   GetNetworkInfo()->Teardown();
   GetDeviceInfo()->Teardown();
+  GetUserSettings()->Teardown();
 }
 
 }  // namespace shared
