no bug - Bumping Firefox l10n changesets r=release a=l10n-bump DONTBUILD CLOSED TREE
[gecko.git] / dom / canvas / CanvasUtils.h
blob801f5e01b9306f3b032782e931cca378899a980e
1 /* -*- Mode: C++; tab-width: 20; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* This Source Code Form is subject to the terms of the Mozilla Public
3 * License, v. 2.0. If a copy of the MPL was not distributed with this
4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 #ifndef _CANVASUTILS_H_
7 #define _CANVASUTILS_H_
9 #include "CanvasRenderingContextHelper.h"
10 #include "mozilla/CheckedInt.h"
11 #include "mozilla/dom/ToJSValue.h"
12 #include "jsapi.h"
13 #include "js/Array.h" // JS::GetArrayLength
14 #include "js/PropertyAndElement.h" // JS_GetElement
15 #include "mozilla/FloatingPoint.h"
17 class nsIPrincipal;
19 namespace mozilla {
21 namespace dom {
22 class Document;
23 class HTMLCanvasElement;
24 class OffscreenCanvas;
25 } // namespace dom
27 namespace CanvasUtils {
29 bool GetCanvasContextType(const nsAString& str,
30 dom::CanvasContextType* const out_type);
32 // Check that the rectangle [x,y,w,h] is a subrectangle of
33 // [0,0,realWidth,realHeight]
35 inline bool CheckSaneSubrectSize(int32_t x, int32_t y, int32_t w, int32_t h,
36 int32_t realWidth, int32_t realHeight) {
37 CheckedInt32 checked_xmost = CheckedInt32(x) + w;
38 CheckedInt32 checked_ymost = CheckedInt32(y) + h;
40 return w >= 0 && h >= 0 && x >= 0 && y >= 0 && checked_xmost.isValid() &&
41 checked_xmost.value() <= realWidth && checked_ymost.isValid() &&
42 checked_ymost.value() <= realHeight;
45 // Flag aCanvasElement as write-only if drawing an image with aPrincipal
46 // onto it would make it such.
48 void DoDrawImageSecurityCheck(dom::HTMLCanvasElement* aCanvasElement,
49 nsIPrincipal* aPrincipal, bool forceWriteOnly,
50 bool CORSUsed);
52 void DoDrawImageSecurityCheck(dom::OffscreenCanvas* aOffscreenCanvas,
53 nsIPrincipal* aPrincipal, bool forceWriteOnly,
54 bool CORSUsed);
56 // Check if the context is chrome or has the permission to drawWindow
57 bool HasDrawWindowPrivilege(JSContext* aCx, JSObject* aObj);
59 // Check if the context has permission to use OffscreenCanvas.
60 bool IsOffscreenCanvasEnabled(JSContext* aCx, JSObject* aObj);
62 // Check site-specific permission and display prompt if appropriate.
63 bool IsImageExtractionAllowed(dom::Document* aDocument, JSContext* aCx,
64 nsIPrincipal& aPrincipal);
66 enum class ImageExtraction {
67 Unrestricted,
68 Placeholder,
69 Randomize,
72 // Returns whether the result of an image extraction should be replaced
73 // by a placeholder or randomized.
74 ImageExtraction ImageExtractionResult(dom::HTMLCanvasElement* aCanvasElement,
75 JSContext* aCx, nsIPrincipal& aPrincipal);
76 ImageExtraction ImageExtractionResult(dom::OffscreenCanvas* aOffscreenCanvas,
77 JSContext* aCx, nsIPrincipal& aPrincipal);
79 // Make a double out of |v|, treating undefined values as 0.0 (for
80 // the sake of sparse arrays). Return true iff coercion
81 // succeeded.
82 bool CoerceDouble(const JS::Value& v, double* d);
84 /* Float validation stuff */
85 #define VALIDATE(_f) \
86 if (!std::isfinite(_f)) return false
88 inline bool FloatValidate(double f1) {
89 VALIDATE(f1);
90 return true;
93 inline bool FloatValidate(double f1, double f2) {
94 VALIDATE(f1);
95 VALIDATE(f2);
96 return true;
99 inline bool FloatValidate(double f1, double f2, double f3) {
100 VALIDATE(f1);
101 VALIDATE(f2);
102 VALIDATE(f3);
103 return true;
106 inline bool FloatValidate(double f1, double f2, double f3, double f4) {
107 VALIDATE(f1);
108 VALIDATE(f2);
109 VALIDATE(f3);
110 VALIDATE(f4);
111 return true;
114 inline bool FloatValidate(double f1, double f2, double f3, double f4,
115 double f5) {
116 VALIDATE(f1);
117 VALIDATE(f2);
118 VALIDATE(f3);
119 VALIDATE(f4);
120 VALIDATE(f5);
121 return true;
124 inline bool FloatValidate(double f1, double f2, double f3, double f4, double f5,
125 double f6) {
126 VALIDATE(f1);
127 VALIDATE(f2);
128 VALIDATE(f3);
129 VALIDATE(f4);
130 VALIDATE(f5);
131 VALIDATE(f6);
132 return true;
135 #undef VALIDATE
137 template <typename T>
138 nsresult JSValToDashArray(JSContext* cx, const JS::Value& patternArray,
139 nsTArray<T>& dashes) {
140 // The cap is pretty arbitrary. 16k should be enough for
141 // anybody...
142 static const uint32_t MAX_NUM_DASHES = 1 << 14;
144 if (!patternArray.isPrimitive()) {
145 JS::Rooted<JSObject*> obj(cx, patternArray.toObjectOrNull());
146 uint32_t length;
147 if (!JS::GetArrayLength(cx, obj, &length)) {
148 // Not an array-like thing
149 return NS_ERROR_INVALID_ARG;
150 } else if (length > MAX_NUM_DASHES) {
151 // Too many dashes in the pattern
152 return NS_ERROR_ILLEGAL_VALUE;
155 bool haveNonzeroElement = false;
156 for (uint32_t i = 0; i < length; ++i) {
157 JS::Rooted<JS::Value> elt(cx);
158 double d;
159 if (!JS_GetElement(cx, obj, i, &elt)) {
160 return NS_ERROR_FAILURE;
162 if (!(CoerceDouble(elt, &d) && FloatValidate(d) && d >= 0.0)) {
163 // Pattern elements must be finite "numbers" >= 0.
164 return NS_ERROR_INVALID_ARG;
165 } else if (d > 0.0) {
166 haveNonzeroElement = true;
168 if (!dashes.AppendElement(d, mozilla::fallible)) {
169 return NS_ERROR_OUT_OF_MEMORY;
173 if (dashes.Length() > 0 && !haveNonzeroElement) {
174 // An all-zero pattern makes no sense.
175 return NS_ERROR_ILLEGAL_VALUE;
177 } else if (!(patternArray.isUndefined() || patternArray.isNull())) {
178 // undefined and null mean "reset to no dash". Any other
179 // random garbage is a type error.
180 return NS_ERROR_INVALID_ARG;
183 return NS_OK;
186 template <typename T>
187 void DashArrayToJSVal(nsTArray<T>& dashes, JSContext* cx,
188 JS::MutableHandle<JS::Value> retval,
189 mozilla::ErrorResult& rv) {
190 if (dashes.IsEmpty()) {
191 retval.setNull();
192 return;
194 JS::Rooted<JS::Value> val(cx);
195 if (!mozilla::dom::ToJSValue(cx, dashes, retval)) {
196 rv.Throw(NS_ERROR_OUT_OF_MEMORY);
200 // returns true if write-only mode must used for this principal based on
201 // the incumbent global.
202 bool CheckWriteOnlySecurity(bool aCORSUsed, nsIPrincipal* aPrincipal,
203 bool aHadCrossOriginRedirects);
205 } // namespace CanvasUtils
206 } // namespace mozilla
208 #endif /* _CANVASUTILS_H_ */