1 /*
2 * Copyright (c) 2021 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "ecmascript/builtins/builtins_errors.h"
17
18 #include "ecmascript/base/error_helper.h"
19 #include "ecmascript/ecma_macros.h"
20 #include "ecmascript/global_env.h"
21 #include "ecmascript/js_tagged_value-inl.h"
22 #include "ecmascript/js_array.h"
23 #include "ecmascript/js_primitive_ref.h"
24 #include "ecmascript/js_iterator.h"
25
26 namespace panda::ecmascript::builtins {
27 using ErrorHelper = base::ErrorHelper;
28 using ErrorType = base::ErrorType;
29 // Error
ErrorConstructor(EcmaRuntimeCallInfo * argv)30 JSTaggedValue BuiltinsError::ErrorConstructor(EcmaRuntimeCallInfo *argv)
31 {
32 BUILTINS_API_TRACE(argv->GetThread(), Error, ErrorConstructor);
33 return ErrorHelper::ErrorCommonConstructor(argv, ErrorType::ERROR);
34 }
35
ToString(EcmaRuntimeCallInfo * argv)36 JSTaggedValue BuiltinsError::ToString(EcmaRuntimeCallInfo *argv)
37 {
38 BUILTINS_API_TRACE(argv->GetThread(), Error, ErrorToString);
39 return ErrorHelper::ErrorCommonToString(argv, ErrorType::ERROR);
40 }
41
42 // RangeError
RangeErrorConstructor(EcmaRuntimeCallInfo * argv)43 JSTaggedValue BuiltinsRangeError::RangeErrorConstructor(EcmaRuntimeCallInfo *argv)
44 {
45 BUILTINS_API_TRACE(argv->GetThread(), Error, RangeErrorConstructor);
46 return ErrorHelper::ErrorCommonConstructor(argv, ErrorType::RANGE_ERROR);
47 }
48
ToString(EcmaRuntimeCallInfo * argv)49 JSTaggedValue BuiltinsRangeError::ToString(EcmaRuntimeCallInfo *argv)
50 {
51 BUILTINS_API_TRACE(argv->GetThread(), Error, RangeErrorToString);
52 return ErrorHelper::ErrorCommonToString(argv, ErrorType::RANGE_ERROR);
53 }
54
55 // ReferenceError
ReferenceErrorConstructor(EcmaRuntimeCallInfo * argv)56 JSTaggedValue BuiltinsReferenceError::ReferenceErrorConstructor(EcmaRuntimeCallInfo *argv)
57 {
58 BUILTINS_API_TRACE(argv->GetThread(), Error, ReferenceErrorConstructor);
59 return ErrorHelper::ErrorCommonConstructor(argv, ErrorType::REFERENCE_ERROR);
60 }
61
ToString(EcmaRuntimeCallInfo * argv)62 JSTaggedValue BuiltinsReferenceError::ToString(EcmaRuntimeCallInfo *argv)
63 {
64 BUILTINS_API_TRACE(argv->GetThread(), Error, ReferenceErrorToString);
65 return ErrorHelper::ErrorCommonToString(argv, ErrorType::REFERENCE_ERROR);
66 }
67
68 // TypeError
TypeErrorConstructor(EcmaRuntimeCallInfo * argv)69 JSTaggedValue BuiltinsTypeError::TypeErrorConstructor(EcmaRuntimeCallInfo *argv)
70 {
71 BUILTINS_API_TRACE(argv->GetThread(), Error, TypeErrorConstructor);
72 return ErrorHelper::ErrorCommonConstructor(argv, ErrorType::TYPE_ERROR);
73 }
74
ToString(EcmaRuntimeCallInfo * argv)75 JSTaggedValue BuiltinsTypeError::ToString(EcmaRuntimeCallInfo *argv)
76 {
77 BUILTINS_API_TRACE(argv->GetThread(), Error, TypeErrorToString);
78 return ErrorHelper::ErrorCommonToString(argv, ErrorType::TYPE_ERROR);
79 }
80
ThrowTypeError(EcmaRuntimeCallInfo * argv)81 JSTaggedValue BuiltinsTypeError::ThrowTypeError(EcmaRuntimeCallInfo *argv)
82 {
83 JSThread *thread = argv->GetThread();
84 BUILTINS_API_TRACE(thread, Error, ThrowTypeError);
85 [[maybe_unused]] EcmaHandleScope handleScope(thread);
86 THROW_TYPE_ERROR_AND_RETURN(thread, "type error", JSTaggedValue::Exception());
87 }
88
89 // URIError
URIErrorConstructor(EcmaRuntimeCallInfo * argv)90 JSTaggedValue BuiltinsURIError::URIErrorConstructor(EcmaRuntimeCallInfo *argv)
91 {
92 BUILTINS_API_TRACE(argv->GetThread(), Error, URIErrorConstructor);
93 return ErrorHelper::ErrorCommonConstructor(argv, ErrorType::URI_ERROR);
94 }
95
ToString(EcmaRuntimeCallInfo * argv)96 JSTaggedValue BuiltinsURIError::ToString(EcmaRuntimeCallInfo *argv)
97 {
98 BUILTINS_API_TRACE(argv->GetThread(), Error, URIErrorToString);
99 return ErrorHelper::ErrorCommonToString(argv, ErrorType::URI_ERROR);
100 }
101
102 // SyntaxError
SyntaxErrorConstructor(EcmaRuntimeCallInfo * argv)103 JSTaggedValue BuiltinsSyntaxError::SyntaxErrorConstructor(EcmaRuntimeCallInfo *argv)
104 {
105 BUILTINS_API_TRACE(argv->GetThread(), Error, SyntaxErrorConstructor);
106 return ErrorHelper::ErrorCommonConstructor(argv, ErrorType::SYNTAX_ERROR);
107 }
108
ToString(EcmaRuntimeCallInfo * argv)109 JSTaggedValue BuiltinsSyntaxError::ToString(EcmaRuntimeCallInfo *argv)
110 {
111 BUILTINS_API_TRACE(argv->GetThread(), Error, SyntaxErrorToString);
112 return ErrorHelper::ErrorCommonToString(argv, ErrorType::SYNTAX_ERROR);
113 }
114
115 // EvalError
EvalErrorConstructor(EcmaRuntimeCallInfo * argv)116 JSTaggedValue BuiltinsEvalError::EvalErrorConstructor(EcmaRuntimeCallInfo *argv)
117 {
118 BUILTINS_API_TRACE(argv->GetThread(), Error, EvalErrorConstructor);
119 return ErrorHelper::ErrorCommonConstructor(argv, ErrorType::EVAL_ERROR);
120 }
121
ToString(EcmaRuntimeCallInfo * argv)122 JSTaggedValue BuiltinsEvalError::ToString(EcmaRuntimeCallInfo *argv)
123 {
124 BUILTINS_API_TRACE(argv->GetThread(), Error, EvalErrorToString);
125 return ErrorHelper::ErrorCommonToString(argv, ErrorType::EVAL_ERROR);
126 }
127
128 // AggregateError
AggregateErrorConstructor(EcmaRuntimeCallInfo * argv)129 JSTaggedValue BuiltinsAggregateError::AggregateErrorConstructor(EcmaRuntimeCallInfo *argv)
130 {
131 JSThread *thread = argv->GetThread();
132 BUILTINS_API_TRACE(argv->GetThread(), Error, AggregateErrorConstructor);
133 [[maybe_unused]] EcmaHandleScope scope(thread);
134 EcmaVM *ecmaVm = thread->GetEcmaVM();
135 ObjectFactory *factory = ecmaVm->GetFactory();
136 const GlobalEnvConstants *globalConst = thread->GlobalConstants();
137 // 1. If NewTarget is undefined, let newTarget be the active function object; else let newTarget be NewTarget.
138 JSHandle<JSTaggedValue> constructor = GetConstructor(argv);
139 JSMutableHandle<JSTaggedValue> newTarget(thread, GetNewTarget(argv));
140 if (newTarget->IsUndefined()) {
141 newTarget.Update(constructor.GetTaggedValue());
142 }
143 JSHandle<JSTaggedValue> errors = BuiltinsBase::GetCallArg(argv, 0);
144 JSHandle<JSTaggedValue> message = BuiltinsBase::GetCallArg(argv, 1);
145 // 2. Let O be ? OrdinaryCreateFromConstructor(newTarget, "%AggregateError.prototype%", « [[ErrorData]] »).
146 JSHandle<JSObject> objValues = factory->NewJSObjectByConstructor(JSHandle<JSFunction>(constructor), newTarget);
147 RETURN_EXCEPTION_IF_ABRUPT_COMPLETION(thread);
148 JSHandle<JSTaggedValue> taggedObj = JSHandle<JSTaggedValue>::Cast(objValues);
149 // 3. If message is not undefined, then
150 // a. Let msg be ? ToString(message).
151 // b. Let msgDesc be the PropertyDescriptor
152 // { [[Value]]: msg, [[Writable]]: true, [[Enumerable]]: false, [[Configurable]]: true }.
153 // c. Perform ! DefinePropertyOrThrow(O, "message", msgDesc).
154 JSHandle<JSTaggedValue> msgKey = globalConst->GetHandledMessageString();
155 JSHandle<JSTaggedValue> errorsKey = globalConst->GetHandledErrorsString();
156 if (!message->IsUndefined()) {
157 JSHandle<EcmaString> handleStr = JSTaggedValue::ToString(thread, message);
158 RETURN_EXCEPTION_IF_ABRUPT_COMPLETION(thread);
159 PropertyDescriptor msgDesc(thread, JSHandle<JSTaggedValue>::Cast(handleStr), true, false, true);
160 JSTaggedValue::DefinePropertyOrThrow(thread, taggedObj, msgKey, msgDesc);
161 }
162 // InstallErrorCause
163 JSHandle<JSTaggedValue> options = BuiltinsBase::GetCallArg(argv, 2); // 2 : Third parameter
164 // If options is an Object and ? HasProperty(options, "cause") is true, then
165 // a. Let cause be ? Get(options, "cause").
166 // b. Perform CreateNonEnumerableDataPropertyOrThrow(O, "cause", cause).
167 if (options->IsECMAObject()) {
168 JSHandle<JSTaggedValue> causeKey = globalConst->GetHandledCauseString();
169 bool causePresent = JSTaggedValue::HasProperty(thread, options, causeKey);
170 RETURN_EXCEPTION_IF_ABRUPT_COMPLETION(thread);
171 if (causePresent) {
172 JSHandle<JSTaggedValue> cause = JSObject::GetProperty(thread, options, causeKey).GetValue();
173 RETURN_EXCEPTION_IF_ABRUPT_COMPLETION(thread);
174 PropertyDescriptor causeDesc(thread, cause, true, false, true);
175 JSTaggedValue::DefinePropertyOrThrow(thread, taggedObj, causeKey, causeDesc);
176 }
177 }
178 // 4. Let errorsList be ? IterableToList(errors).
179 JSHandle<JSTaggedValue> errorsList = JSObject::IterableToList(thread, errors);
180 RETURN_EXCEPTION_IF_ABRUPT_COMPLETION(thread);
181 // 5. Perform ! DefinePropertyOrThrow(O, "errors", PropertyDescriptor { [[Configurable]]: true,
182 // [[Enumerable]]: false, [[Writable]]: true, [[Value]]: !CreateArrayFromList(errorsList) }).
183 JSHandle<TaggedArray> errorsArray = JSArray::ToTaggedArray(thread, errorsList);
184 JSHandle<JSTaggedValue> errorsValues(JSArray::CreateArrayFromList(thread, errorsArray));
185 PropertyDescriptor msgDesc(thread, errorsValues, true, false, true);
186 JSTaggedValue::DefinePropertyOrThrow(thread, taggedObj, errorsKey, msgDesc);
187 RETURN_EXCEPTION_IF_ABRUPT_COMPLETION(thread);
188 // 6. Return O.
189 return taggedObj.GetTaggedValue();
190 }
191
ToString(EcmaRuntimeCallInfo * argv)192 JSTaggedValue BuiltinsAggregateError::ToString(EcmaRuntimeCallInfo *argv)
193 {
194 BUILTINS_API_TRACE(argv->GetThread(), Error, AggregateErrorToString);
195 return ErrorHelper::ErrorCommonToString(argv, ErrorType::AGGREGATE_ERROR);
196 }
197
198 // OOMError
OOMErrorConstructor(EcmaRuntimeCallInfo * argv)199 JSTaggedValue BuiltinsOOMError::OOMErrorConstructor(EcmaRuntimeCallInfo *argv)
200 {
201 BUILTINS_API_TRACE(argv->GetThread(), Error, OOMErrorConstructor);
202 return ErrorHelper::ErrorCommonConstructor(argv, ErrorType::OOM_ERROR);
203 }
204
ToString(EcmaRuntimeCallInfo * argv)205 JSTaggedValue BuiltinsOOMError::ToString(EcmaRuntimeCallInfo *argv)
206 {
207 BUILTINS_API_TRACE(argv->GetThread(), Error, OOMErrorToString);
208 return ErrorHelper::ErrorCommonToString(argv, ErrorType::OOM_ERROR);
209 }
210 } // namespace panda::ecmascript::builtins
211