1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7 #include "mozilla/dom/ServiceWorkerRegistrationDescriptor.h"
9 #include "mozilla/dom/IPCServiceWorkerRegistrationDescriptor.h"
10 #include "mozilla/ipc/PBackgroundSharedTypes.h"
11 #include "ServiceWorkerInfo.h"
13 namespace mozilla::dom
{
15 using mozilla::ipc::PrincipalInfo
;
16 using mozilla::ipc::PrincipalInfoToPrincipal
;
18 Maybe
<IPCServiceWorkerDescriptor
>
19 ServiceWorkerRegistrationDescriptor::NewestInternal() const {
20 Maybe
<IPCServiceWorkerDescriptor
> result
;
21 if (mData
->installing().isSome()) {
22 result
.emplace(mData
->installing().ref());
23 } else if (mData
->waiting().isSome()) {
24 result
.emplace(mData
->waiting().ref());
25 } else if (mData
->active().isSome()) {
26 result
.emplace(mData
->active().ref());
31 ServiceWorkerRegistrationDescriptor::ServiceWorkerRegistrationDescriptor(
32 uint64_t aId
, uint64_t aVersion
, nsIPrincipal
* aPrincipal
,
33 const nsACString
& aScope
, ServiceWorkerUpdateViaCache aUpdateViaCache
)
34 : mData(MakeUnique
<IPCServiceWorkerRegistrationDescriptor
>()) {
36 PrincipalToPrincipalInfo(aPrincipal
, &mData
->principalInfo()));
39 mData
->version() = aVersion
;
40 mData
->scope() = aScope
;
41 mData
->updateViaCache() = aUpdateViaCache
;
42 mData
->installing() = Nothing();
43 mData
->waiting() = Nothing();
44 mData
->active() = Nothing();
47 ServiceWorkerRegistrationDescriptor::ServiceWorkerRegistrationDescriptor(
48 uint64_t aId
, uint64_t aVersion
,
49 const mozilla::ipc::PrincipalInfo
& aPrincipalInfo
, const nsACString
& aScope
,
50 ServiceWorkerUpdateViaCache aUpdateViaCache
)
51 : mData(MakeUnique
<IPCServiceWorkerRegistrationDescriptor
>(
52 aId
, aVersion
, aPrincipalInfo
, nsCString(aScope
), aUpdateViaCache
,
53 Nothing(), Nothing(), Nothing())) {}
55 ServiceWorkerRegistrationDescriptor::ServiceWorkerRegistrationDescriptor(
56 const IPCServiceWorkerRegistrationDescriptor
& aDescriptor
)
57 : mData(MakeUnique
<IPCServiceWorkerRegistrationDescriptor
>(aDescriptor
)) {
58 MOZ_DIAGNOSTIC_ASSERT(IsValid());
61 ServiceWorkerRegistrationDescriptor::ServiceWorkerRegistrationDescriptor(
62 const ServiceWorkerRegistrationDescriptor
& aRight
) {
63 // UniquePtr doesn't have a default copy constructor, so we can't rely
64 // on default copy construction. Use the assignment operator to
65 // minimize duplication.
69 ServiceWorkerRegistrationDescriptor
&
70 ServiceWorkerRegistrationDescriptor::operator=(
71 const ServiceWorkerRegistrationDescriptor
& aRight
) {
72 if (this == &aRight
) {
76 mData
= MakeUnique
<IPCServiceWorkerRegistrationDescriptor
>(*aRight
.mData
);
77 MOZ_DIAGNOSTIC_ASSERT(IsValid());
81 ServiceWorkerRegistrationDescriptor::ServiceWorkerRegistrationDescriptor(
82 ServiceWorkerRegistrationDescriptor
&& aRight
)
83 : mData(std::move(aRight
.mData
)) {
84 MOZ_DIAGNOSTIC_ASSERT(IsValid());
87 ServiceWorkerRegistrationDescriptor
&
88 ServiceWorkerRegistrationDescriptor::operator=(
89 ServiceWorkerRegistrationDescriptor
&& aRight
) {
91 mData
= std::move(aRight
.mData
);
92 MOZ_DIAGNOSTIC_ASSERT(IsValid());
96 ServiceWorkerRegistrationDescriptor::~ServiceWorkerRegistrationDescriptor() {
97 // Non-default destructor to avoid exposing the IPC type in the header.
100 bool ServiceWorkerRegistrationDescriptor::operator==(
101 const ServiceWorkerRegistrationDescriptor
& aRight
) const {
102 return *mData
== *aRight
.mData
;
105 uint64_t ServiceWorkerRegistrationDescriptor::Id() const { return mData
->id(); }
107 uint64_t ServiceWorkerRegistrationDescriptor::Version() const {
108 return mData
->version();
111 ServiceWorkerUpdateViaCache
112 ServiceWorkerRegistrationDescriptor::UpdateViaCache() const {
113 return mData
->updateViaCache();
116 const mozilla::ipc::PrincipalInfo
&
117 ServiceWorkerRegistrationDescriptor::PrincipalInfo() const {
118 return mData
->principalInfo();
121 Result
<nsCOMPtr
<nsIPrincipal
>, nsresult
>
122 ServiceWorkerRegistrationDescriptor::GetPrincipal() const {
123 AssertIsOnMainThread();
124 return PrincipalInfoToPrincipal(mData
->principalInfo());
127 const nsCString
& ServiceWorkerRegistrationDescriptor::Scope() const {
128 return mData
->scope();
131 Maybe
<ServiceWorkerDescriptor
>
132 ServiceWorkerRegistrationDescriptor::GetInstalling() const {
133 Maybe
<ServiceWorkerDescriptor
> result
;
135 if (mData
->installing().isSome()) {
136 result
.emplace(ServiceWorkerDescriptor(mData
->installing().ref()));
142 Maybe
<ServiceWorkerDescriptor
> ServiceWorkerRegistrationDescriptor::GetWaiting()
144 Maybe
<ServiceWorkerDescriptor
> result
;
146 if (mData
->waiting().isSome()) {
147 result
.emplace(ServiceWorkerDescriptor(mData
->waiting().ref()));
153 Maybe
<ServiceWorkerDescriptor
> ServiceWorkerRegistrationDescriptor::GetActive()
155 Maybe
<ServiceWorkerDescriptor
> result
;
157 if (mData
->active().isSome()) {
158 result
.emplace(ServiceWorkerDescriptor(mData
->active().ref()));
164 Maybe
<ServiceWorkerDescriptor
> ServiceWorkerRegistrationDescriptor::Newest()
166 Maybe
<ServiceWorkerDescriptor
> result
;
167 Maybe
<IPCServiceWorkerDescriptor
> newest(NewestInternal());
168 if (newest
.isSome()) {
169 result
.emplace(ServiceWorkerDescriptor(newest
.ref()));
174 bool ServiceWorkerRegistrationDescriptor::HasWorker(
175 const ServiceWorkerDescriptor
& aDescriptor
) const {
176 Maybe
<ServiceWorkerDescriptor
> installing
= GetInstalling();
177 Maybe
<ServiceWorkerDescriptor
> waiting
= GetWaiting();
178 Maybe
<ServiceWorkerDescriptor
> active
= GetActive();
179 return (installing
.isSome() && installing
.ref().Matches(aDescriptor
)) ||
180 (waiting
.isSome() && waiting
.ref().Matches(aDescriptor
)) ||
181 (active
.isSome() && active
.ref().Matches(aDescriptor
));
187 const Maybe
<IPCServiceWorkerDescriptor
>& aWorker
, const nsACString
& aScope
,
188 const mozilla::ipc::ContentPrincipalInfo
& aContentPrincipal
) {
189 if (aWorker
.isNothing()) {
193 auto& worker
= aWorker
.ref();
194 if (worker
.scope() != aScope
) {
198 auto& principalInfo
= worker
.principalInfo();
199 if (principalInfo
.type() !=
200 mozilla::ipc::PrincipalInfo::TContentPrincipalInfo
) {
204 auto& contentPrincipal
= principalInfo
.get_ContentPrincipalInfo();
205 if (contentPrincipal
.originNoSuffix() != aContentPrincipal
.originNoSuffix() ||
206 contentPrincipal
.attrs() != aContentPrincipal
.attrs()) {
213 } // anonymous namespace
215 bool ServiceWorkerRegistrationDescriptor::IsValid() const {
216 auto& principalInfo
= PrincipalInfo();
217 if (principalInfo
.type() !=
218 mozilla::ipc::PrincipalInfo::TContentPrincipalInfo
) {
222 auto& contentPrincipal
= principalInfo
.get_ContentPrincipalInfo();
223 if (!IsValidWorker(mData
->installing(), Scope(), contentPrincipal
) ||
224 !IsValidWorker(mData
->waiting(), Scope(), contentPrincipal
) ||
225 !IsValidWorker(mData
->active(), Scope(), contentPrincipal
)) {
232 void ServiceWorkerRegistrationDescriptor::SetUpdateViaCache(
233 ServiceWorkerUpdateViaCache aUpdateViaCache
) {
234 mData
->updateViaCache() = aUpdateViaCache
;
237 void ServiceWorkerRegistrationDescriptor::SetWorkers(
238 ServiceWorkerInfo
* aInstalling
, ServiceWorkerInfo
* aWaiting
,
239 ServiceWorkerInfo
* aActive
) {
241 aInstalling
->SetRegistrationVersion(Version());
242 mData
->installing() = Some(aInstalling
->Descriptor().ToIPC());
244 mData
->installing() = Nothing();
248 aWaiting
->SetRegistrationVersion(Version());
249 mData
->waiting() = Some(aWaiting
->Descriptor().ToIPC());
251 mData
->waiting() = Nothing();
255 aActive
->SetRegistrationVersion(Version());
256 mData
->active() = Some(aActive
->Descriptor().ToIPC());
258 mData
->active() = Nothing();
261 MOZ_DIAGNOSTIC_ASSERT(IsValid());
264 void ServiceWorkerRegistrationDescriptor::SetVersion(uint64_t aVersion
) {
265 MOZ_DIAGNOSTIC_ASSERT(aVersion
> mData
->version());
266 mData
->version() = aVersion
;
269 const IPCServiceWorkerRegistrationDescriptor
&
270 ServiceWorkerRegistrationDescriptor::ToIPC() const {
274 } // namespace mozilla::dom