1 /*
2 * Copyright (c) 2022 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/base/typed_array_helper-inl.h"
17 #include "ecmascript/builtins/builtins_arraybuffer.h"
18 #include "ecmascript/global_env.h"
19 #include "ecmascript/tests/test_helper.h"
20
21 using namespace panda::ecmascript;
22 using namespace panda::ecmascript::base;
23
24 namespace panda::test {
25 class TypedArrayHelperTest : public testing::Test {
26 public:
SetUpTestCase()27 static void SetUpTestCase()
28 {
29 GTEST_LOG_(INFO) << "SetUpTestCase";
30 }
31
TearDownTestCase()32 static void TearDownTestCase()
33 {
34 GTEST_LOG_(INFO) << "TearDownCase";
35 }
36
SetUp()37 void SetUp() override
38 {
39 TestHelper::CreateEcmaVMWithScope(instance, thread, scope);
40 }
41
TearDown()42 void TearDown() override
43 {
44 TestHelper::DestroyEcmaVMWithScope(instance, scope);
45 }
46
47 EcmaVM *instance {nullptr};
48 EcmaHandleScope *scope {nullptr};
49 JSThread *thread {nullptr};
50 };
51
CreateTypedArrayCallInfo(JSThread * thread,const JSHandle<TaggedArray> & array,DataViewType type)52 EcmaRuntimeCallInfo *CreateTypedArrayCallInfo(JSThread *thread, const JSHandle<TaggedArray> &array, DataViewType type)
53 {
54 auto vm = thread->GetEcmaVM();
55 auto env = vm->GetGlobalEnv();
56 JSHandle<JSTaggedValue> jsarray(JSArray::CreateArrayFromList(thread, array));
57 JSHandle<JSFunction> arrayFunc;
58 switch (type) {
59 case DataViewType::BIGINT64: {
60 arrayFunc = JSHandle<JSFunction>(env->GetBigInt64ArrayFunction());
61 break;
62 }
63 case DataViewType::BIGUINT64: {
64 arrayFunc = JSHandle<JSFunction>(env->GetBigUint64ArrayFunction());
65 break;
66 }
67 case DataViewType::FLOAT32: {
68 arrayFunc = JSHandle<JSFunction>(env->GetFloat32ArrayFunction());
69 break;
70 }
71 case DataViewType::FLOAT64: {
72 arrayFunc = JSHandle<JSFunction>(env->GetFloat64ArrayFunction());
73 break;
74 }
75 case DataViewType::INT16: {
76 arrayFunc = JSHandle<JSFunction>(env->GetInt16ArrayFunction());
77 break;
78 }
79 case DataViewType::INT32: {
80 arrayFunc = JSHandle<JSFunction>(env->GetInt32ArrayFunction());
81 break;
82 }
83 case DataViewType::INT8: {
84 arrayFunc = JSHandle<JSFunction>(env->GetInt8ArrayFunction());
85 break;
86 }
87 case DataViewType::UINT16: {
88 arrayFunc = JSHandle<JSFunction>(env->GetUint16ArrayFunction());
89 break;
90 }
91 case DataViewType::UINT32: {
92 arrayFunc = JSHandle<JSFunction>(env->GetUint32ArrayFunction());
93 break;
94 }
95 case DataViewType::UINT8: {
96 arrayFunc = JSHandle<JSFunction>(env->GetUint8ArrayFunction());
97 break;
98 }
99 case DataViewType::UINT8_CLAMPED: {
100 arrayFunc = JSHandle<JSFunction>(env->GetUint8ClampedArrayFunction());
101 break;
102 }
103 default: {
104 JSHandle<JSTaggedValue> undefined(thread, JSTaggedValue::Undefined());
105 arrayFunc = JSHandle<JSFunction>(undefined);
106 break;
107 }
108 }
109 JSHandle<JSObject> globalObject(thread, env->GetGlobalObject());
110 EcmaRuntimeCallInfo* ecmaRuntimeCallInfo =
111 TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue(*arrayFunc), 6); // 6 : arguments length
112 ecmaRuntimeCallInfo->SetFunction(JSTaggedValue(*arrayFunc));
113 ecmaRuntimeCallInfo->SetThis(JSTaggedValue(*globalObject));
114 ecmaRuntimeCallInfo->SetCallArg(0, jsarray.GetTaggedValue());
115 return ecmaRuntimeCallInfo;
116 }
117
HWTEST_F_L0(TypedArrayHelperTest,TypedArrayConstructor)118 HWTEST_F_L0(TypedArrayHelperTest, TypedArrayConstructor)
119 {
120 auto factory = thread->GetEcmaVM()->GetFactory();
121 JSHandle<TaggedArray> array(factory->NewTaggedArray(3));
122 array->Set(thread, 0, JSTaggedValue(-129)); // Int8 min minus 1
123 array->Set(thread, 1, JSTaggedValue(-128)); // Int8 min
124 array->Set(thread, 2, JSTaggedValue(128)); // Int8 max plus 1
125 EcmaRuntimeCallInfo* argv = CreateTypedArrayCallInfo(thread, array, DataViewType::INT8);
126 JSHandle<JSTaggedValue> constructorName = thread->GlobalConstants()->GetHandledInt8ArrayString();
127 auto prev = TestHelper::SetupFrame(thread, argv);
128 JSHandle<JSTaggedValue> int8Array(thread, TypedArrayHelper::TypedArrayConstructor(argv, constructorName,
129 DataViewType::INT8));
130 TestHelper::TearDownFrame(thread, prev);
131 OperationResult result0 = JSTypedArray::GetProperty(thread, int8Array, 0U);
132 OperationResult result1 = JSTypedArray::GetProperty(thread, int8Array, 1U);
133 OperationResult result2 = JSTypedArray::GetProperty(thread, int8Array, 2U);
134 EXPECT_EQ(result0.GetRawValue().GetTaggedValue().GetInt(), 127); // 127 : -129 to int8 127
135 EXPECT_EQ(result1.GetRawValue().GetTaggedValue().GetInt(), -128); // -128 : -128 to int8 -128
136 EXPECT_EQ(result2.GetRawValue().GetTaggedValue().GetInt(), -128); // -128 : 128 to int8 -128
137 }
138
HWTEST_F_L0(TypedArrayHelperTest,AllocateTypedArray_001)139 HWTEST_F_L0(TypedArrayHelperTest, AllocateTypedArray_001)
140 {
141 auto ecmaVm = thread->GetEcmaVM();
142 auto factory = ecmaVm->GetFactory();
143 JSHandle<TaggedArray> array(factory->NewTaggedArray(0));
144 EcmaRuntimeCallInfo* argv = CreateTypedArrayCallInfo(thread, array, DataViewType::UINT8);
145 JSHandle<JSTaggedValue> constructorName = thread->GlobalConstants()->GetHandledUint8ArrayString();
146 auto prev = TestHelper::SetupFrame(thread, argv);
147 JSHandle<JSTaggedValue> newTarget = BuiltinsBase::GetNewTarget(argv);
148 JSHandle<JSObject> arrayObj =
149 TypedArrayHelper::AllocateTypedArray(factory, ecmaVm, constructorName, newTarget, DataViewType::UINT8);
150 TestHelper::TearDownFrame(thread, prev);
151 JSTypedArray *jsTypedArray = JSTypedArray::Cast(*arrayObj);
152 EXPECT_EQ(jsTypedArray->GetContentType(), ContentType::Number);
153 EXPECT_EQ(jsTypedArray->GetTypedArrayName().GetRawData(), constructorName.GetTaggedValue().GetRawData());
154 EXPECT_EQ(jsTypedArray->GetByteLength(), 0U);
155 EXPECT_EQ(jsTypedArray->GetByteOffset(), 0U);
156 EXPECT_EQ(jsTypedArray->GetArrayLength(), 0U);
157 }
158
HWTEST_F_L0(TypedArrayHelperTest,AllocateTypedArray_002)159 HWTEST_F_L0(TypedArrayHelperTest, AllocateTypedArray_002)
160 {
161 auto ecmaVm = thread->GetEcmaVM();
162 auto factory = ecmaVm->GetFactory();
163 int32_t length = 256;
164 JSHandle<TaggedArray> array(factory->NewTaggedArray(3));
165 EcmaRuntimeCallInfo* argv = CreateTypedArrayCallInfo(thread, array, DataViewType::UINT8);
166 JSHandle<JSTaggedValue> constructorName = thread->GlobalConstants()->GetHandledUint8ArrayString();
167 auto prev = TestHelper::SetupFrame(thread, argv);
168 JSHandle<JSTaggedValue> newTarget = BuiltinsBase::GetNewTarget(argv);
169 JSHandle<JSObject> arrayObj =
170 TypedArrayHelper::AllocateTypedArray(factory, ecmaVm, constructorName, newTarget, length, DataViewType::UINT8);
171 TestHelper::TearDownFrame(thread, prev);
172 JSTypedArray *jsTypedArray = JSTypedArray::Cast(*arrayObj);
173 EXPECT_EQ(jsTypedArray->GetContentType(), ContentType::Number);
174 EXPECT_EQ(jsTypedArray->GetTypedArrayName().GetRawData(), constructorName.GetTaggedValue().GetRawData());
175 EXPECT_EQ(jsTypedArray->GetByteLength(), 256U);
176 EXPECT_EQ(jsTypedArray->GetByteOffset(), 0U);
177 EXPECT_EQ(jsTypedArray->GetArrayLength(), 256U);
178 }
179
HWTEST_F_L0(TypedArrayHelperTest,TypedArraySpeciesCreate)180 HWTEST_F_L0(TypedArrayHelperTest, TypedArraySpeciesCreate)
181 {
182 auto factory = thread->GetEcmaVM()->GetFactory();
183 uint32_t lenVal = 3;
184 JSHandle<TaggedArray> array(factory->NewTaggedArray(lenVal));
185 EcmaRuntimeCallInfo* argv = CreateTypedArrayCallInfo(thread, array, DataViewType::INT16);
186 JSHandle<JSTaggedValue> constructorName = thread->GlobalConstants()->GetHandledInt16ArrayString();
187 auto prev = TestHelper::SetupFrame(thread, argv);
188 JSHandle<JSTaggedValue> int16Array(thread, TypedArrayHelper::TypedArrayConstructor(argv, constructorName,
189 DataViewType::INT16));
190 TestHelper::TearDownFrame(thread, prev);
191 JSHandle<JSTypedArray> arrayObj(int16Array);
192 uint32_t len = arrayObj->GetArrayLength();
193 EXPECT_EQ(len, 3U);
194
195 uint32_t newLenVal = 6;
196 JSTaggedType args[1] = {JSTaggedValue(newLenVal).GetRawData()};
197 JSHandle<JSObject> newArrObj = TypedArrayHelper::TypedArraySpeciesCreate(thread, arrayObj, 1, args); // 1 : one arg
198 uint32_t newLen = JSHandle<JSTypedArray>::Cast(newArrObj)->GetArrayLength();
199 EXPECT_EQ(newLen, 6U);
200 }
201
HWTEST_F_L0(TypedArrayHelperTest,TypedArrayCreate)202 HWTEST_F_L0(TypedArrayHelperTest, TypedArrayCreate)
203 {
204 auto vm = thread->GetEcmaVM();
205 auto env = vm->GetGlobalEnv();
206 JSHandle<JSTaggedValue> constructor = env->GetUint16ArrayFunction();
207 JSHandle<JSTaggedValue> constructorName = thread->GlobalConstants()->GetHandledUint16ArrayString();
208 EXPECT_TRUE(constructor->IsConstructor());
209
210 uint32_t lenVal = 256;
211 JSTaggedType args[1] = {JSTaggedValue(lenVal).GetRawData()};
212 JSHandle<JSObject> newArrObj = TypedArrayHelper::TypedArrayCreate(thread, constructor, 1, args); // 1 : one arg
213 uint32_t len = JSHandle<JSTypedArray>::Cast(newArrObj)->GetArrayLength();
214 JSHandle<JSTaggedValue> type(thread, JSHandle<JSTypedArray>::Cast(newArrObj)->GetTypedArrayName());
215 EXPECT_EQ(len, 256U);
216 EXPECT_EQ(type.GetTaggedValue().GetRawData(), constructorName.GetTaggedValue().GetRawData());
217 }
218
HWTEST_F_L0(TypedArrayHelperTest,ValidateTypedArray)219 HWTEST_F_L0(TypedArrayHelperTest, ValidateTypedArray)
220 {
221 auto factory = thread->GetEcmaVM()->GetFactory();
222 JSHandle<TaggedArray> array(factory->NewTaggedArray(0));
223 EcmaRuntimeCallInfo* argv = CreateTypedArrayCallInfo(thread, array, DataViewType::UINT32);
224 JSHandle<JSTaggedValue> constructorName = thread->GlobalConstants()->GetHandledUint32ArrayString();
225 auto prev = TestHelper::SetupFrame(thread, argv);
226 JSHandle<JSTaggedValue> uint32Array(thread, TypedArrayHelper::TypedArrayConstructor(argv, constructorName,
227 DataViewType::UINT32));
228 TestHelper::TearDownFrame(thread, prev);
229 JSHandle<JSTaggedValue> buffer(thread, TypedArrayHelper::ValidateTypedArray(thread, uint32Array));
230 JSTaggedValue result = JSHandle<JSTypedArray>::Cast(uint32Array)->GetViewedArrayBuffer();
231 EXPECT_EQ(buffer.GetTaggedValue().GetRawData(), result.GetRawData());
232 }
233
HWTEST_F_L0(TypedArrayHelperTest,GetType_001)234 HWTEST_F_L0(TypedArrayHelperTest, GetType_001)
235 {
236 auto factory = thread->GetEcmaVM()->GetFactory();
237 JSHandle<TaggedArray> array(factory->NewTaggedArray(0));
238 EcmaRuntimeCallInfo* argv1 = CreateTypedArrayCallInfo(thread, array, DataViewType::INT8);
239 EcmaRuntimeCallInfo* argv2 = CreateTypedArrayCallInfo(thread, array, DataViewType::BIGUINT64);
240 EcmaRuntimeCallInfo* argv3 = CreateTypedArrayCallInfo(thread, array, DataViewType::UINT8_CLAMPED);
241 JSHandle<JSTaggedValue> constructorName1 = thread->GlobalConstants()->GetHandledInt8ArrayString();
242 JSHandle<JSTaggedValue> constructorName2 = thread->GlobalConstants()->GetHandledBigUint64ArrayString();
243 JSHandle<JSTaggedValue> constructorName3 = thread->GlobalConstants()->GetHandledUint8ClampedArrayString();
244 auto prev1 = TestHelper::SetupFrame(thread, argv1);
245 JSHandle<JSTaggedValue> int8ArrayVal(thread, TypedArrayHelper::TypedArrayConstructor(argv1, constructorName1,
246 DataViewType::INT8));
247 TestHelper::TearDownFrame(thread, prev1);
248 auto prev2 = TestHelper::SetupFrame(thread, argv2);
249 JSHandle<JSTaggedValue> bigUint64ArrayVal(thread, TypedArrayHelper::TypedArrayConstructor(argv2, constructorName2,
250 DataViewType::BIGUINT64));
251 TestHelper::TearDownFrame(thread, prev2);
252 auto prev3 = TestHelper::SetupFrame(thread, argv3);
253 JSHandle<JSTaggedValue> uint8ClampedArrayVal(thread, TypedArrayHelper::TypedArrayConstructor(argv3,
254 constructorName3, DataViewType::UINT8_CLAMPED));
255 TestHelper::TearDownFrame(thread, prev3);
256 JSHandle<JSTypedArray> int8Array(int8ArrayVal);
257 JSHandle<JSTypedArray> bigUint64Array(bigUint64ArrayVal);
258 JSHandle<JSTypedArray> uint8ClampedArray(uint8ClampedArrayVal);
259 DataViewType type1 = TypedArrayHelper::GetType(int8Array);
260 DataViewType type2 = TypedArrayHelper::GetType(JSHandle<JSTypedArray>::Cast(bigUint64Array));
261 DataViewType type3 = TypedArrayHelper::GetType(JSHandle<JSTypedArray>::Cast(uint8ClampedArray));
262 EXPECT_EQ(type1, DataViewType::INT8);
263 EXPECT_EQ(type2, DataViewType::BIGUINT64);
264 EXPECT_EQ(type3, DataViewType::UINT8_CLAMPED);
265 }
266
HWTEST_F_L0(TypedArrayHelperTest,GetType_002)267 HWTEST_F_L0(TypedArrayHelperTest, GetType_002)
268 {
269 EXPECT_EQ(TypedArrayHelper::GetType(JSType::JS_INT8_ARRAY), DataViewType::INT8);
270 EXPECT_EQ(TypedArrayHelper::GetType(JSType::JS_UINT8_ARRAY), DataViewType::UINT8);
271 EXPECT_EQ(TypedArrayHelper::GetType(JSType::JS_UINT8_CLAMPED_ARRAY), DataViewType::UINT8_CLAMPED);
272 EXPECT_EQ(TypedArrayHelper::GetType(JSType::JS_INT16_ARRAY), DataViewType::INT16);
273 EXPECT_EQ(TypedArrayHelper::GetType(JSType::JS_UINT16_ARRAY), DataViewType::UINT16);
274 EXPECT_EQ(TypedArrayHelper::GetType(JSType::JS_INT32_ARRAY), DataViewType::INT32);
275 EXPECT_EQ(TypedArrayHelper::GetType(JSType::JS_UINT32_ARRAY), DataViewType::UINT32);
276 EXPECT_EQ(TypedArrayHelper::GetType(JSType::JS_FLOAT32_ARRAY), DataViewType::FLOAT32);
277 EXPECT_EQ(TypedArrayHelper::GetType(JSType::JS_FLOAT64_ARRAY), DataViewType::FLOAT64);
278 EXPECT_EQ(TypedArrayHelper::GetType(JSType::JS_BIGINT64_ARRAY), DataViewType::BIGINT64);
279 EXPECT_EQ(TypedArrayHelper::GetType(JSType::JS_OBJECT), DataViewType::BIGUINT64);
280 }
281
HWTEST_F_L0(TypedArrayHelperTest,GetElementSize_001)282 HWTEST_F_L0(TypedArrayHelperTest, GetElementSize_001)
283 {
284 auto factory = thread->GetEcmaVM()->GetFactory();
285 JSHandle<TaggedArray> array(factory->NewTaggedArray(0));
286 EcmaRuntimeCallInfo* argv1 = CreateTypedArrayCallInfo(thread, array, DataViewType::INT8);
287 EcmaRuntimeCallInfo* argv2 = CreateTypedArrayCallInfo(thread, array, DataViewType::INT16);
288 EcmaRuntimeCallInfo* argv3 = CreateTypedArrayCallInfo(thread, array, DataViewType::INT32);
289 EcmaRuntimeCallInfo* argv4 = CreateTypedArrayCallInfo(thread, array, DataViewType::BIGUINT64);
290 JSHandle<JSTaggedValue> constructorName1 = thread->GlobalConstants()->GetHandledInt8ArrayString();
291 JSHandle<JSTaggedValue> constructorName2 = thread->GlobalConstants()->GetHandledInt16ArrayString();
292 JSHandle<JSTaggedValue> constructorName3 = thread->GlobalConstants()->GetHandledInt32ArrayString();
293 JSHandle<JSTaggedValue> constructorName4 = thread->GlobalConstants()->GetHandledBigUint64ArrayString();
294 auto prev1 = TestHelper::SetupFrame(thread, argv1);
295 JSHandle<JSTaggedValue> int8ArrayVal(thread, TypedArrayHelper::TypedArrayConstructor(argv1, constructorName1,
296 DataViewType::INT8));
297 TestHelper::TearDownFrame(thread, prev1);
298 auto prev2 = TestHelper::SetupFrame(thread, argv2);
299 JSHandle<JSTaggedValue> int16ArrayVal(thread, TypedArrayHelper::TypedArrayConstructor(argv2, constructorName2,
300 DataViewType::INT16));
301 TestHelper::TearDownFrame(thread, prev2);
302 auto prev3 = TestHelper::SetupFrame(thread, argv3);
303 JSHandle<JSTaggedValue> int32ArrayVal(thread, TypedArrayHelper::TypedArrayConstructor(argv3, constructorName3,
304 DataViewType::INT32));
305 TestHelper::TearDownFrame(thread, prev3);
306 auto prev4 = TestHelper::SetupFrame(thread, argv4);
307 JSHandle<JSTaggedValue> bigUint64ArrayVal(thread, TypedArrayHelper::TypedArrayConstructor(argv3, constructorName4,
308 DataViewType::BIGUINT64));
309 TestHelper::TearDownFrame(thread, prev4);
310 JSHandle<JSTypedArray> int8Array(int8ArrayVal);
311 JSHandle<JSTypedArray> int16Array(int16ArrayVal);
312 JSHandle<JSTypedArray> int32Array(int32ArrayVal);
313 JSHandle<JSTypedArray> bigUint64Array(bigUint64ArrayVal);
314 uint32_t elementSize1 = TypedArrayHelper::GetElementSize(int8Array);
315 uint32_t elementSize2 = TypedArrayHelper::GetElementSize(JSHandle<JSTypedArray>::Cast(int16Array));
316 uint32_t elementSize3 = TypedArrayHelper::GetElementSize(JSHandle<JSTypedArray>::Cast(int32Array));
317 uint32_t elementSize4 = TypedArrayHelper::GetElementSize(JSHandle<JSTypedArray>::Cast(bigUint64Array));
318 EXPECT_EQ(elementSize1, 1U);
319 EXPECT_EQ(elementSize2, 2U);
320 EXPECT_EQ(elementSize3, 4U);
321 EXPECT_EQ(elementSize4, 8U);
322 }
323
HWTEST_F_L0(TypedArrayHelperTest,GetElementSize_002)324 HWTEST_F_L0(TypedArrayHelperTest, GetElementSize_002)
325 {
326 EXPECT_EQ(TypedArrayHelper::GetElementSize(JSType::JS_INT8_ARRAY), 1U);
327 EXPECT_EQ(TypedArrayHelper::GetElementSize(JSType::JS_UINT8_ARRAY), 1U);
328 EXPECT_EQ(TypedArrayHelper::GetElementSize(JSType::JS_UINT8_CLAMPED_ARRAY), 1U);
329 EXPECT_EQ(TypedArrayHelper::GetElementSize(JSType::JS_INT16_ARRAY), 2U);
330 EXPECT_EQ(TypedArrayHelper::GetElementSize(JSType::JS_UINT16_ARRAY), 2U);
331 EXPECT_EQ(TypedArrayHelper::GetElementSize(JSType::JS_INT32_ARRAY), 4U);
332 EXPECT_EQ(TypedArrayHelper::GetElementSize(JSType::JS_UINT32_ARRAY), 4U);
333 EXPECT_EQ(TypedArrayHelper::GetElementSize(JSType::JS_FLOAT32_ARRAY), 4U);
334 EXPECT_EQ(TypedArrayHelper::GetElementSize(JSType::JS_FLOAT64_ARRAY), 8U);
335 EXPECT_EQ(TypedArrayHelper::GetElementSize(JSType::JS_BIGINT64_ARRAY), 8U);
336 EXPECT_EQ(TypedArrayHelper::GetElementSize(JSType::JS_OBJECT), 8U);
337 }
338
HWTEST_F_L0(TypedArrayHelperTest,GetConstructor)339 HWTEST_F_L0(TypedArrayHelperTest, GetConstructor)
340 {
341 auto factory = thread->GetEcmaVM()->GetFactory();
342 JSHandle<GlobalEnv> env = thread->GetEcmaVM()->GetGlobalEnv();
343 JSHandle<TaggedArray> array(factory->NewTaggedArray(0));
344 EcmaRuntimeCallInfo* argv1 = CreateTypedArrayCallInfo(thread, array, DataViewType::INT8);
345 EcmaRuntimeCallInfo* argv2 = CreateTypedArrayCallInfo(thread, array, DataViewType::BIGUINT64);
346 EcmaRuntimeCallInfo* argv3 = CreateTypedArrayCallInfo(thread, array, DataViewType::UINT8_CLAMPED);
347 JSHandle<JSTaggedValue> constructorName1 = thread->GlobalConstants()->GetHandledInt8ArrayString();
348 JSHandle<JSTaggedValue> constructorName2 = thread->GlobalConstants()->GetHandledBigUint64ArrayString();
349 JSHandle<JSTaggedValue> constructorName3 = thread->GlobalConstants()->GetHandledUint8ClampedArrayString();
350 auto prev1 = TestHelper::SetupFrame(thread, argv1);
351 JSHandle<JSTaggedValue> int8ArrayVal(thread, TypedArrayHelper::TypedArrayConstructor(argv1, constructorName1,
352 DataViewType::INT8));
353 TestHelper::TearDownFrame(thread, prev1);
354 auto prev2 = TestHelper::SetupFrame(thread, argv2);
355 JSHandle<JSTaggedValue> bigUint64ArrayVal(thread, TypedArrayHelper::TypedArrayConstructor(argv2, constructorName2,
356 DataViewType::BIGUINT64));
357 TestHelper::TearDownFrame(thread, prev2);
358 auto prev3 = TestHelper::SetupFrame(thread, argv3);
359 JSHandle<JSTaggedValue> uint8ClampedArrayVal(thread, TypedArrayHelper::TypedArrayConstructor(argv3,
360 constructorName3, DataViewType::UINT8_CLAMPED));
361 TestHelper::TearDownFrame(thread, prev3);
362 JSHandle<JSTaggedValue> constructor1 = TypedArrayHelper::GetConstructor(thread, int8ArrayVal);
363 JSHandle<JSTaggedValue> constructor2 = TypedArrayHelper::GetConstructor(thread, bigUint64ArrayVal);
364 JSHandle<JSTaggedValue> constructor3 = TypedArrayHelper::GetConstructor(thread, uint8ClampedArrayVal);
365 EXPECT_EQ(constructor1.GetTaggedValue(), env->GetInt8ArrayFunction().GetTaggedValue());
366 EXPECT_EQ(constructor2.GetTaggedValue(), env->GetBigUint64ArrayFunction().GetTaggedValue());
367 EXPECT_EQ(constructor3.GetTaggedValue(), env->GetUint8ClampedArrayFunction().GetTaggedValue());
368 }
369
HWTEST_F_L0(TypedArrayHelperTest,GetConstructorFromType)370 HWTEST_F_L0(TypedArrayHelperTest, GetConstructorFromType)
371 {
372 JSHandle<GlobalEnv> env = thread->GetEcmaVM()->GetGlobalEnv();
373 EXPECT_EQ(TypedArrayHelper::GetConstructorFromType(thread, DataViewType::INT8).GetTaggedValue(),
374 env->GetInt8ArrayFunction().GetTaggedValue());
375 EXPECT_EQ(TypedArrayHelper::GetConstructorFromType(thread, DataViewType::UINT8).GetTaggedValue(),
376 env->GetUint8ArrayFunction().GetTaggedValue());
377 EXPECT_EQ(TypedArrayHelper::GetConstructorFromType(thread, DataViewType::UINT8_CLAMPED).GetTaggedValue(),
378 env->GetUint8ClampedArrayFunction().GetTaggedValue());
379 EXPECT_EQ(TypedArrayHelper::GetConstructorFromType(thread, DataViewType::INT16).GetTaggedValue(),
380 env->GetInt16ArrayFunction().GetTaggedValue());
381 EXPECT_EQ(TypedArrayHelper::GetConstructorFromType(thread, DataViewType::UINT16).GetTaggedValue(),
382 env->GetUint16ArrayFunction().GetTaggedValue());
383 EXPECT_EQ(TypedArrayHelper::GetConstructorFromType(thread, DataViewType::INT32).GetTaggedValue(),
384 env->GetInt32ArrayFunction().GetTaggedValue());
385 EXPECT_EQ(TypedArrayHelper::GetConstructorFromType(thread, DataViewType::UINT32).GetTaggedValue(),
386 env->GetUint32ArrayFunction().GetTaggedValue());
387 EXPECT_EQ(TypedArrayHelper::GetConstructorFromType(thread, DataViewType::FLOAT32).GetTaggedValue(),
388 env->GetFloat32ArrayFunction().GetTaggedValue());
389 EXPECT_EQ(TypedArrayHelper::GetConstructorFromType(thread, DataViewType::FLOAT64).GetTaggedValue(),
390 env->GetFloat64ArrayFunction().GetTaggedValue());
391 EXPECT_EQ(TypedArrayHelper::GetConstructorFromType(thread, DataViewType::BIGINT64).GetTaggedValue(),
392 env->GetBigInt64ArrayFunction().GetTaggedValue());
393 EXPECT_EQ(TypedArrayHelper::GetConstructorFromType(thread, DataViewType::BIGUINT64).GetTaggedValue(),
394 env->GetBigUint64ArrayFunction().GetTaggedValue());
395 }
396
HWTEST_F_L0(TypedArrayHelperTest,GetSizeFromType)397 HWTEST_F_L0(TypedArrayHelperTest, GetSizeFromType)
398 {
399 EXPECT_EQ(TypedArrayHelper::GetSizeFromType(DataViewType::INT8), 1U);
400 EXPECT_EQ(TypedArrayHelper::GetSizeFromType(DataViewType::UINT8), 1U);
401 EXPECT_EQ(TypedArrayHelper::GetSizeFromType(DataViewType::UINT8_CLAMPED), 1U);
402 EXPECT_EQ(TypedArrayHelper::GetSizeFromType(DataViewType::INT16), 2U);
403 EXPECT_EQ(TypedArrayHelper::GetSizeFromType(DataViewType::UINT16), 2U);
404 EXPECT_EQ(TypedArrayHelper::GetSizeFromType(DataViewType::INT32), 4U);
405 EXPECT_EQ(TypedArrayHelper::GetSizeFromType(DataViewType::UINT32), 4U);
406 EXPECT_EQ(TypedArrayHelper::GetSizeFromType(DataViewType::FLOAT32), 4U);
407 EXPECT_EQ(TypedArrayHelper::GetSizeFromType(DataViewType::FLOAT64), 8U);
408 EXPECT_EQ(TypedArrayHelper::GetSizeFromType(DataViewType::BIGINT64), 8U);
409 EXPECT_EQ(TypedArrayHelper::GetSizeFromType(DataViewType::BIGUINT64), 8U);
410 }
411
HWTEST_F_L0(TypedArrayHelperTest,SortCompare)412 HWTEST_F_L0(TypedArrayHelperTest, SortCompare)
413 {
414 auto factory = thread->GetEcmaVM()->GetFactory();
415 JSHandle<TaggedArray> array(factory->NewTaggedArray(0));
416 EcmaRuntimeCallInfo* argv = CreateTypedArrayCallInfo(thread, array, DataViewType::UINT32);
417 JSHandle<JSTaggedValue> constructorName = thread->GlobalConstants()->GetHandledUint32ArrayString();
418 auto prev = TestHelper::SetupFrame(thread, argv);
419 JSHandle<JSTaggedValue> uint32Array(thread, TypedArrayHelper::TypedArrayConstructor(argv, constructorName,
420 DataViewType::UINT32));
421 TestHelper::TearDownFrame(thread, prev);
422 JSHandle<JSTaggedValue> buffer(thread, TypedArrayHelper::ValidateTypedArray(thread, uint32Array));
423 EXPECT_FALSE(builtins::BuiltinsArrayBuffer::IsDetachedBuffer(buffer.GetTaggedValue()));
424
425 JSHandle<JSTaggedValue> callbackfnHandle(thread, JSTaggedValue::Undefined());
426 JSHandle<JSTaggedValue> nan(thread, JSTaggedValue(base::NAN_VALUE));
427 JSHandle<JSTaggedValue> eZero(thread, JSTaggedValue(-0.0));
428 JSHandle<JSTaggedValue> pZero(thread, JSTaggedValue(+0.0));
429 JSHandle<JSTaggedValue> larger(thread, JSTaggedValue(321));
430 JSHandle<JSTaggedValue> smaller(thread, JSTaggedValue(123));
431
432 // if first value and second value are both NaN, return +0.
433 int32_t result = TypedArrayHelper::SortCompare(thread, callbackfnHandle, buffer, nan, nan);
434 EXPECT_EQ(result, +0);
435
436 // if first value is NaN, return 1.
437 result = TypedArrayHelper::SortCompare(thread, callbackfnHandle, buffer, nan, smaller);
438 EXPECT_EQ(result, 1);
439
440 // if second value is NaN, return -1.
441 result = TypedArrayHelper::SortCompare(thread, callbackfnHandle, buffer, smaller, nan);
442 EXPECT_EQ(result, -1);
443
444 // if first value is smaller than second value, return -1.
445 result = TypedArrayHelper::SortCompare(thread, callbackfnHandle, buffer, smaller, larger);
446 EXPECT_EQ(result, -1);
447
448 // if first value is larger than second value, return 1.
449 result = TypedArrayHelper::SortCompare(thread, callbackfnHandle, buffer, larger, smaller);
450 EXPECT_EQ(result, 1);
451
452 // "-0.0" sort compare with "+0.0", retrun -1
453 result = TypedArrayHelper::SortCompare(thread, callbackfnHandle, buffer, eZero, pZero);
454 EXPECT_EQ(result, -1);
455
456 // "+0.0" sort compare with "-0.0", retrun 1
457 result = TypedArrayHelper::SortCompare(thread, callbackfnHandle, buffer, pZero, eZero);
458 EXPECT_EQ(result, 1);
459 }
460 } // namespace panda::test
461