diff options
Diffstat (limited to 'src/core/hle/service/glue/time/time_zone.cpp')
-rw-r--r-- | src/core/hle/service/glue/time/time_zone.cpp | 352 |
1 files changed, 99 insertions, 253 deletions
diff --git a/src/core/hle/service/glue/time/time_zone.cpp b/src/core/hle/service/glue/time/time_zone.cpp index 503c327dd..98d928697 100644 --- a/src/core/hle/service/glue/time/time_zone.cpp +++ b/src/core/hle/service/glue/time/time_zone.cpp @@ -3,8 +3,10 @@ #include <chrono> +#include "common/scope_exit.h" #include "core/core.h" #include "core/hle/kernel/svc.h" +#include "core/hle/service/cmif_serialization.h" #include "core/hle/service/glue/time/file_timestamp_worker.h" #include "core/hle/service/glue/time/time_zone.h" #include "core/hle/service/glue/time/time_zone_binary.h" @@ -28,20 +30,20 @@ TimeZoneService::TimeZoneService( m_wrapped_service{std::move(time_zone_service)}, m_operation_event{m_system} { // clang-format off static const FunctionInfo functions[] = { - {0, &TimeZoneService::Handle_GetDeviceLocationName, "GetDeviceLocationName"}, - {1, &TimeZoneService::Handle_SetDeviceLocationName, "SetDeviceLocationName"}, - {2, &TimeZoneService::Handle_GetTotalLocationNameCount, "GetTotalLocationNameCount"}, - {3, &TimeZoneService::Handle_LoadLocationNameList, "LoadLocationNameList"}, - {4, &TimeZoneService::Handle_LoadTimeZoneRule, "LoadTimeZoneRule"}, - {5, &TimeZoneService::Handle_GetTimeZoneRuleVersion, "GetTimeZoneRuleVersion"}, - {6, &TimeZoneService::Handle_GetDeviceLocationNameAndUpdatedTime, "GetDeviceLocationNameAndUpdatedTime"}, - {7, &TimeZoneService::Handle_SetDeviceLocationNameWithTimeZoneRule, "SetDeviceLocationNameWithTimeZoneRule"}, - {8, &TimeZoneService::Handle_ParseTimeZoneBinary, "ParseTimeZoneBinary"}, - {20, &TimeZoneService::Handle_GetDeviceLocationNameOperationEventReadableHandle, "GetDeviceLocationNameOperationEventReadableHandle"}, - {100, &TimeZoneService::Handle_ToCalendarTime, "ToCalendarTime"}, - {101, &TimeZoneService::Handle_ToCalendarTimeWithMyRule, "ToCalendarTimeWithMyRule"}, - {201, &TimeZoneService::Handle_ToPosixTime, "ToPosixTime"}, - {202, &TimeZoneService::Handle_ToPosixTimeWithMyRule, "ToPosixTimeWithMyRule"}, + {0, D<&TimeZoneService::GetDeviceLocationName>, "GetDeviceLocationName"}, + {1, D<&TimeZoneService::SetDeviceLocationName>, "SetDeviceLocationName"}, + {2, D<&TimeZoneService::GetTotalLocationNameCount>, "GetTotalLocationNameCount"}, + {3, D<&TimeZoneService::LoadLocationNameList>, "LoadLocationNameList"}, + {4, D<&TimeZoneService::LoadTimeZoneRule>, "LoadTimeZoneRule"}, + {5, D<&TimeZoneService::GetTimeZoneRuleVersion>, "GetTimeZoneRuleVersion"}, + {6, D<&TimeZoneService::GetDeviceLocationNameAndUpdatedTime>, "GetDeviceLocationNameAndUpdatedTime"}, + {7, D<&TimeZoneService::SetDeviceLocationNameWithTimeZoneRule>, "SetDeviceLocationNameWithTimeZoneRule"}, + {8, D<&TimeZoneService::ParseTimeZoneBinary>, "ParseTimeZoneBinary"}, + {20, D<&TimeZoneService::GetDeviceLocationNameOperationEventReadableHandle>, "GetDeviceLocationNameOperationEventReadableHandle"}, + {100, D<&TimeZoneService::ToCalendarTime>, "ToCalendarTime"}, + {101, D<&TimeZoneService::ToCalendarTimeWithMyRule>, "ToCalendarTimeWithMyRule"}, + {201, D<&TimeZoneService::ToPosixTime>, "ToPosixTime"}, + {202, D<&TimeZoneService::ToPosixTimeWithMyRule>, "ToPosixTimeWithMyRule"}, }; // clang-format on RegisterHandlers(functions); @@ -53,220 +55,16 @@ TimeZoneService::TimeZoneService( TimeZoneService::~TimeZoneService() = default; -void TimeZoneService::Handle_GetDeviceLocationName(HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); - - Service::PSC::Time::LocationName name{}; - auto res = GetDeviceLocationName(name); - - IPC::ResponseBuilder rb{ctx, 2 + sizeof(Service::PSC::Time::LocationName) / sizeof(u32)}; - rb.Push(res); - rb.PushRaw<Service::PSC::Time::LocationName>(name); -} - -void TimeZoneService::Handle_SetDeviceLocationName(HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); - - IPC::RequestParser rp{ctx}; - auto name{rp.PopRaw<Service::PSC::Time::LocationName>()}; - - auto res = SetDeviceLocation(name); - - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(res); -} - -void TimeZoneService::Handle_GetTotalLocationNameCount(HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); - - u32 count{}; - auto res = GetTotalLocationNameCount(count); - - IPC::ResponseBuilder rb{ctx, 3}; - rb.Push(res); - rb.Push(count); -} - -void TimeZoneService::Handle_LoadLocationNameList(HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); - - IPC::RequestParser rp{ctx}; - auto index{rp.Pop<u32>()}; - - auto max_names{ctx.GetWriteBufferSize() / sizeof(Service::PSC::Time::LocationName)}; - - std::vector<Service::PSC::Time::LocationName> names{}; - u32 count{}; - auto res = LoadLocationNameList(count, names, max_names, index); - - ctx.WriteBuffer(names); - - IPC::ResponseBuilder rb{ctx, 3}; - rb.Push(res); - rb.Push(count); -} - -void TimeZoneService::Handle_LoadTimeZoneRule(HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); - - IPC::RequestParser rp{ctx}; - auto name{rp.PopRaw<Service::PSC::Time::LocationName>()}; - - Tz::Rule rule{}; - auto res = LoadTimeZoneRule(rule, name); - - ctx.WriteBuffer(rule); - - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(res); -} - -void TimeZoneService::Handle_GetTimeZoneRuleVersion(HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); - - Service::PSC::Time::RuleVersion rule_version{}; - auto res = GetTimeZoneRuleVersion(rule_version); - - IPC::ResponseBuilder rb{ctx, 2 + sizeof(Service::PSC::Time::RuleVersion) / sizeof(u32)}; - rb.Push(res); - rb.PushRaw<Service::PSC::Time::RuleVersion>(rule_version); -} - -void TimeZoneService::Handle_GetDeviceLocationNameAndUpdatedTime(HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); - - Service::PSC::Time::LocationName name{}; - Service::PSC::Time::SteadyClockTimePoint time_point{}; - auto res = GetDeviceLocationNameAndUpdatedTime(time_point, name); - - IPC::ResponseBuilder rb{ctx, - 2 + (sizeof(Service::PSC::Time::LocationName) / sizeof(u32)) + - (sizeof(Service::PSC::Time::SteadyClockTimePoint) / sizeof(u32))}; - rb.Push(res); - rb.PushRaw<Service::PSC::Time::LocationName>(name); - rb.PushRaw<Service::PSC::Time::SteadyClockTimePoint>(time_point); -} - -void TimeZoneService::Handle_SetDeviceLocationNameWithTimeZoneRule(HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); - - auto res = SetDeviceLocationNameWithTimeZoneRule(); - - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(res); -} - -void TimeZoneService::Handle_ParseTimeZoneBinary(HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); - - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(Service::PSC::Time::ResultNotImplemented); -} - -void TimeZoneService::Handle_GetDeviceLocationNameOperationEventReadableHandle( - HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); +Result TimeZoneService::GetDeviceLocationName( + Out<Service::PSC::Time::LocationName> out_location_name) { + SCOPE_EXIT({ LOG_DEBUG(Service_Time, "called. out_location_name={}", *out_location_name); }); - Kernel::KEvent* event{}; - auto res = GetDeviceLocationNameOperationEventReadableHandle(&event); - - IPC::ResponseBuilder rb{ctx, 2, 1}; - rb.Push(res); - rb.PushCopyObjects(event->GetReadableEvent()); -} - -void TimeZoneService::Handle_ToCalendarTime(HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); - - IPC::RequestParser rp{ctx}; - auto time{rp.Pop<s64>()}; - - auto rule_buffer{ctx.ReadBuffer()}; - Tz::Rule rule{}; - std::memcpy(&rule, rule_buffer.data(), sizeof(Tz::Rule)); - - Service::PSC::Time::CalendarTime calendar_time{}; - Service::PSC::Time::CalendarAdditionalInfo additional_info{}; - auto res = ToCalendarTime(calendar_time, additional_info, time, rule); - - IPC::ResponseBuilder rb{ctx, - 2 + (sizeof(Service::PSC::Time::CalendarTime) / sizeof(u32)) + - (sizeof(Service::PSC::Time::CalendarAdditionalInfo) / sizeof(u32))}; - rb.Push(res); - rb.PushRaw<Service::PSC::Time::CalendarTime>(calendar_time); - rb.PushRaw<Service::PSC::Time::CalendarAdditionalInfo>(additional_info); -} - -void TimeZoneService::Handle_ToCalendarTimeWithMyRule(HLERequestContext& ctx) { - IPC::RequestParser rp{ctx}; - auto time{rp.Pop<s64>()}; - - LOG_DEBUG(Service_Time, "called. time={}", time); - - Service::PSC::Time::CalendarTime calendar_time{}; - Service::PSC::Time::CalendarAdditionalInfo additional_info{}; - auto res = ToCalendarTimeWithMyRule(calendar_time, additional_info, time); - - IPC::ResponseBuilder rb{ctx, - 2 + (sizeof(Service::PSC::Time::CalendarTime) / sizeof(u32)) + - (sizeof(Service::PSC::Time::CalendarAdditionalInfo) / sizeof(u32))}; - rb.Push(res); - rb.PushRaw<Service::PSC::Time::CalendarTime>(calendar_time); - rb.PushRaw<Service::PSC::Time::CalendarAdditionalInfo>(additional_info); -} - -void TimeZoneService::Handle_ToPosixTime(HLERequestContext& ctx) { - IPC::RequestParser rp{ctx}; - auto calendar{rp.PopRaw<Service::PSC::Time::CalendarTime>()}; - - LOG_DEBUG(Service_Time, "called. calendar year {} month {} day {} hour {} minute {} second {}", - calendar.year, calendar.month, calendar.day, calendar.hour, calendar.minute, - calendar.second); - - auto binary{ctx.ReadBuffer()}; - - Tz::Rule rule{}; - std::memcpy(&rule, binary.data(), sizeof(Tz::Rule)); - - u32 count{}; - std::array<s64, 2> times{}; - u32 times_count{static_cast<u32>(ctx.GetWriteBufferSize() / sizeof(s64))}; - - auto res = ToPosixTime(count, times, times_count, calendar, rule); - - ctx.WriteBuffer(times); - - IPC::ResponseBuilder rb{ctx, 3}; - rb.Push(res); - rb.Push(count); -} - -void TimeZoneService::Handle_ToPosixTimeWithMyRule(HLERequestContext& ctx) { - LOG_DEBUG(Service_Time, "called."); - - IPC::RequestParser rp{ctx}; - auto calendar{rp.PopRaw<Service::PSC::Time::CalendarTime>()}; - - u32 count{}; - std::array<s64, 2> times{}; - u32 times_count{static_cast<u32>(ctx.GetWriteBufferSize() / sizeof(s64))}; - - auto res = ToPosixTimeWithMyRule(count, times, times_count, calendar); - - ctx.WriteBuffer(times); - - IPC::ResponseBuilder rb{ctx, 3}; - rb.Push(res); - rb.Push(count); -} - -// =============================== Implementations =========================== - -Result TimeZoneService::GetDeviceLocationName(Service::PSC::Time::LocationName& out_location_name) { R_RETURN(m_wrapped_service->GetDeviceLocationName(out_location_name)); } -Result TimeZoneService::SetDeviceLocation(Service::PSC::Time::LocationName& location_name) { +Result TimeZoneService::SetDeviceLocationName(Service::PSC::Time::LocationName& location_name) { + LOG_DEBUG(Service_Time, "called. location_name={}", location_name); + R_UNLESS(m_can_write_timezone_device_location, Service::PSC::Time::ResultPermissionDenied); R_UNLESS(IsTimeZoneBinaryValid(location_name), Service::PSC::Time::ResultTimeZoneNotFound); @@ -282,7 +80,7 @@ Result TimeZoneService::SetDeviceLocation(Service::PSC::Time::LocationName& loca Service::PSC::Time::SteadyClockTimePoint time_point{}; Service::PSC::Time::LocationName name{}; - R_TRY(m_wrapped_service->GetDeviceLocationNameAndUpdatedTime(time_point, name)); + R_TRY(m_wrapped_service->GetDeviceLocationNameAndUpdatedTime(&name, &time_point)); m_set_sys->SetDeviceTimeZoneLocationName(name); m_set_sys->SetDeviceTimeZoneLocationUpdatedTime(time_point); @@ -294,19 +92,27 @@ Result TimeZoneService::SetDeviceLocation(Service::PSC::Time::LocationName& loca R_SUCCEED(); } -Result TimeZoneService::GetTotalLocationNameCount(u32& out_count) { +Result TimeZoneService::GetTotalLocationNameCount(Out<u32> out_count) { + SCOPE_EXIT({ LOG_DEBUG(Service_Time, "called. out_count={}", *out_count); }); + R_RETURN(m_wrapped_service->GetTotalLocationNameCount(out_count)); } Result TimeZoneService::LoadLocationNameList( - u32& out_count, std::vector<Service::PSC::Time::LocationName>& out_names, size_t max_names, - u32 index) { + Out<u32> out_count, + OutArray<Service::PSC::Time::LocationName, BufferAttr_HipcMapAlias> out_names, u32 index) { + SCOPE_EXIT({ + LOG_DEBUG(Service_Time, "called. index={} out_count={} out_names[0]={} out_names[1]={}", + index, *out_count, out_names[0], out_names[1]); + }); + std::scoped_lock l{m_mutex}; - R_RETURN(GetTimeZoneLocationList(out_count, out_names, max_names, index)); + R_RETURN(GetTimeZoneLocationList(*out_count, out_names, out_names.size(), index)); } -Result TimeZoneService::LoadTimeZoneRule(Tz::Rule& out_rule, - Service::PSC::Time::LocationName& name) { +Result TimeZoneService::LoadTimeZoneRule(OutRule out_rule, Service::PSC::Time::LocationName& name) { + LOG_DEBUG(Service_Time, "called. name={}", name); + std::scoped_lock l{m_mutex}; std::span<const u8> binary{}; size_t binary_size{}; @@ -314,23 +120,43 @@ Result TimeZoneService::LoadTimeZoneRule(Tz::Rule& out_rule, R_RETURN(m_wrapped_service->ParseTimeZoneBinary(out_rule, binary)); } -Result TimeZoneService::GetTimeZoneRuleVersion(Service::PSC::Time::RuleVersion& out_rule_version) { +Result TimeZoneService::GetTimeZoneRuleVersion( + Out<Service::PSC::Time::RuleVersion> out_rule_version) { + SCOPE_EXIT({ LOG_DEBUG(Service_Time, "called. out_rule_version={}", *out_rule_version); }); + R_RETURN(m_wrapped_service->GetTimeZoneRuleVersion(out_rule_version)); } Result TimeZoneService::GetDeviceLocationNameAndUpdatedTime( - Service::PSC::Time::SteadyClockTimePoint& out_time_point, - Service::PSC::Time::LocationName& location_name) { - R_RETURN(m_wrapped_service->GetDeviceLocationNameAndUpdatedTime(out_time_point, location_name)); + Out<Service::PSC::Time::LocationName> location_name, + Out<Service::PSC::Time::SteadyClockTimePoint> out_time_point) { + SCOPE_EXIT({ + LOG_DEBUG(Service_Time, "called. location_name={} out_time_point={}", *location_name, + *out_time_point); + }); + + R_RETURN(m_wrapped_service->GetDeviceLocationNameAndUpdatedTime(location_name, out_time_point)); } -Result TimeZoneService::SetDeviceLocationNameWithTimeZoneRule() { +Result TimeZoneService::SetDeviceLocationNameWithTimeZoneRule( + Service::PSC::Time::LocationName& location_name, InBuffer<BufferAttr_HipcAutoSelect> binary) { + LOG_DEBUG(Service_Time, "called. location_name={}", location_name); + R_UNLESS(m_can_write_timezone_device_location, Service::PSC::Time::ResultPermissionDenied); R_RETURN(Service::PSC::Time::ResultNotImplemented); } +Result TimeZoneService::ParseTimeZoneBinary(OutRule out_rule, + InBuffer<BufferAttr_HipcAutoSelect> binary) { + LOG_DEBUG(Service_Time, "called."); + + R_RETURN(Service::PSC::Time::ResultNotImplemented); +} + Result TimeZoneService::GetDeviceLocationNameOperationEventReadableHandle( - Kernel::KEvent** out_event) { + OutCopyHandle<Kernel::KReadableEvent> out_event) { + LOG_DEBUG(Service_Time, "called."); + if (!operation_event_initialized) { operation_event_initialized = false; @@ -342,36 +168,56 @@ Result TimeZoneService::GetDeviceLocationNameOperationEventReadableHandle( g_list_nodes.push_back(m_operation_event); } - *out_event = m_operation_event.m_event; + *out_event = &m_operation_event.m_event->GetReadableEvent(); R_SUCCEED(); } Result TimeZoneService::ToCalendarTime( - Service::PSC::Time::CalendarTime& out_calendar_time, - Service::PSC::Time::CalendarAdditionalInfo& out_additional_info, s64 time, Tz::Rule& rule) { + Out<Service::PSC::Time::CalendarTime> out_calendar_time, + Out<Service::PSC::Time::CalendarAdditionalInfo> out_additional_info, s64 time, InRule rule) { + SCOPE_EXIT({ + LOG_DEBUG(Service_Time, "called. time={} out_calendar_time={} out_additional_info={}", time, + *out_calendar_time, *out_additional_info); + }); + R_RETURN(m_wrapped_service->ToCalendarTime(out_calendar_time, out_additional_info, time, rule)); } Result TimeZoneService::ToCalendarTimeWithMyRule( - Service::PSC::Time::CalendarTime& out_calendar_time, - Service::PSC::Time::CalendarAdditionalInfo& out_additional_info, s64 time) { + Out<Service::PSC::Time::CalendarTime> out_calendar_time, + Out<Service::PSC::Time::CalendarAdditionalInfo> out_additional_info, s64 time) { + SCOPE_EXIT({ + LOG_DEBUG(Service_Time, "called. time={} out_calendar_time={} out_additional_info={}", time, + *out_calendar_time, *out_additional_info); + }); + R_RETURN( m_wrapped_service->ToCalendarTimeWithMyRule(out_calendar_time, out_additional_info, time)); } -Result TimeZoneService::ToPosixTime(u32& out_count, std::span<s64, 2> out_times, - u32 out_times_count, - Service::PSC::Time::CalendarTime& calendar_time, - Tz::Rule& rule) { - R_RETURN( - m_wrapped_service->ToPosixTime(out_count, out_times, out_times_count, calendar_time, rule)); +Result TimeZoneService::ToPosixTime(Out<u32> out_count, + OutArray<s64, BufferAttr_HipcPointer> out_times, + const Service::PSC::Time::CalendarTime& calendar_time, + InRule rule) { + SCOPE_EXIT({ + LOG_DEBUG(Service_Time, + "called. calendar_time={} out_count={} out_times[0]={} out_times[1]={}", + calendar_time, *out_count, out_times[0], out_times[1]); + }); + + R_RETURN(m_wrapped_service->ToPosixTime(out_count, out_times, calendar_time, rule)); } -Result TimeZoneService::ToPosixTimeWithMyRule(u32& out_count, std::span<s64, 2> out_times, - u32 out_times_count, - Service::PSC::Time::CalendarTime& calendar_time) { - R_RETURN(m_wrapped_service->ToPosixTimeWithMyRule(out_count, out_times, out_times_count, - calendar_time)); +Result TimeZoneService::ToPosixTimeWithMyRule( + Out<u32> out_count, OutArray<s64, BufferAttr_HipcPointer> out_times, + const Service::PSC::Time::CalendarTime& calendar_time) { + SCOPE_EXIT({ + LOG_DEBUG(Service_Time, + "called. calendar_time={} out_count={} out_times[0]={} out_times[1]={}", + calendar_time, *out_count, out_times[0], out_times[1]); + }); + + R_RETURN(m_wrapped_service->ToPosixTimeWithMyRule(out_count, out_times, calendar_time)); } } // namespace Service::Glue::Time |