chromium/third_party/abseil-cpp/absl/time/internal/cctz/src/time_zone_lookup.cc

// Copyright 2016 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//   https://www.apache.org/licenses/LICENSE-2.0
//
//   Unless required by applicable law or agreed to in writing, software
//   distributed under the License is distributed on an "AS IS" BASIS,
//   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//   See the License for the specific language governing permissions and
//   limitations under the License.

#include "absl/base/config.h"
#include "absl/time/internal/cctz/include/cctz/time_zone.h"

#if defined(__ANDROID__)
#include <sys/system_properties.h>
#endif

#if defined(__APPLE__)
#include <CoreFoundation/CFTimeZone.h>

#include <vector>
#endif

#if defined(__Fuchsia__)
#include <fuchsia/intl/cpp/fidl.h>
#include <lib/async-loop/cpp/loop.h>
#include <lib/fdio/directory.h>
#include <zircon/types.h>
#endif

#if defined(_WIN32)
#include <sdkddkver.h>
// Include only when the SDK is for Windows 10 (and later), and the binary is
// targeted for Windows XP and later.
// Note: The Windows SDK added windows.globalization.h file for Windows 10, but
// MinGW did not add it until NTDDI_WIN10_NI (SDK version 10.0.22621.0).
#if ((defined(_WIN32_WINNT_WIN10) && !defined(__MINGW32__)) ||        \
     (defined(NTDDI_WIN10_NI) && NTDDI_VERSION >= NTDDI_WIN10_NI)) && \
    (_WIN32_WINNT >= _WIN32_WINNT_WINXP)
#define USE_WIN32_LOCAL_TIME_ZONE
#include <roapi.h>
#include <tchar.h>
#include <wchar.h>
#include <windows.globalization.h>
#include <windows.h>
#endif
#endif

#include <cstdlib>
#include <cstring>
#include <string>

#include "time_zone_fixed.h"
#include "time_zone_impl.h"

namespace absl {
ABSL_NAMESPACE_BEGIN
namespace time_internal {
namespace cctz {

namespace {
#if defined(USE_WIN32_LOCAL_TIME_ZONE)
// Calls the WinRT Calendar.GetTimeZone method to obtain the IANA ID of the
// local time zone. Returns an empty vector in case of an error.
std::string win32_local_time_zone(const HMODULE combase) {
  std::string result;
  const auto ro_activate_instance =
      reinterpret_cast<decltype(&RoActivateInstance)>(
          GetProcAddress(combase, "RoActivateInstance"));
  if (!ro_activate_instance) {
    return result;
  }
  const auto windows_create_string_reference =
      reinterpret_cast<decltype(&WindowsCreateStringReference)>(
          GetProcAddress(combase, "WindowsCreateStringReference"));
  if (!windows_create_string_reference) {
    return result;
  }
  const auto windows_delete_string =
      reinterpret_cast<decltype(&WindowsDeleteString)>(
          GetProcAddress(combase, "WindowsDeleteString"));
  if (!windows_delete_string) {
    return result;
  }
  const auto windows_get_string_raw_buffer =
      reinterpret_cast<decltype(&WindowsGetStringRawBuffer)>(
          GetProcAddress(combase, "WindowsGetStringRawBuffer"));
  if (!windows_get_string_raw_buffer) {
    return result;
  }

  // The string returned by WindowsCreateStringReference doesn't need to be
  // deleted.
  HSTRING calendar_class_id;
  HSTRING_HEADER calendar_class_id_header;
  HRESULT hr = windows_create_string_reference(
      RuntimeClass_Windows_Globalization_Calendar,
      sizeof(RuntimeClass_Windows_Globalization_Calendar) / sizeof(wchar_t) - 1,
      &calendar_class_id_header, &calendar_class_id);
  if (FAILED(hr)) {
    return result;
  }

  IInspectable* calendar;
  hr = ro_activate_instance(calendar_class_id, &calendar);
  if (FAILED(hr)) {
    return result;
  }

  ABI::Windows::Globalization::ITimeZoneOnCalendar* time_zone;
  hr = calendar->QueryInterface(IID_PPV_ARGS(&time_zone));
  if (FAILED(hr)) {
    calendar->Release();
    return result;
  }

  HSTRING tz_hstr;
  hr = time_zone->GetTimeZone(&tz_hstr);
  if (SUCCEEDED(hr)) {
    UINT32 wlen;
    const PCWSTR tz_wstr = windows_get_string_raw_buffer(tz_hstr, &wlen);
    if (tz_wstr) {
      const int size =
          WideCharToMultiByte(CP_UTF8, 0, tz_wstr, static_cast<int>(wlen),
                              nullptr, 0, nullptr, nullptr);
      result.resize(static_cast<size_t>(size));
      WideCharToMultiByte(CP_UTF8, 0, tz_wstr, static_cast<int>(wlen),
                          &result[0], size, nullptr, nullptr);
    }
    windows_delete_string(tz_hstr);
  }
  time_zone->Release();
  calendar->Release();
  return result;
}
#endif
}  // namespace

std::string time_zone::name() const {}

time_zone::absolute_lookup time_zone::lookup(
    const time_point<seconds>& tp) const {}

time_zone::civil_lookup time_zone::lookup(const civil_second& cs) const {}

bool time_zone::next_transition(const time_point<seconds>& tp,
                                civil_transition* trans) const {}

bool time_zone::prev_transition(const time_point<seconds>& tp,
                                civil_transition* trans) const {}

std::string time_zone::version() const {}

std::string time_zone::description() const {}

const time_zone::Impl& time_zone::effective_impl() const {}

bool load_time_zone(const std::string& name, time_zone* tz) {}

time_zone utc_time_zone() {}

time_zone fixed_time_zone(const seconds& offset) {}

time_zone local_time_zone() {}

}  // namespace cctz
}  // namespace time_internal
ABSL_NAMESPACE_END
}  // namespace absl