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/containers/containers_private.h" 17#include "ecmascript/containers/containers_hashmap.h" 18#include "ecmascript/ecma_runtime_call_info.h" 19#include "ecmascript/global_env.h" 20#include "ecmascript/js_handle.h" 21#include "ecmascript/js_tagged_value-inl.h" 22#include "ecmascript/js_thread.h" 23#include "ecmascript/js_api/js_api_hashmap.h" 24#include "ecmascript/js_api/js_api_hashmap_iterator.h" 25#include "ecmascript/object_factory.h" 26#include "ecmascript/tests/test_helper.h" 27#include "ecmascript/containers/tests/containers_test_helper.h" 28 29using namespace panda::ecmascript; 30using namespace panda::ecmascript::containers; 31 32namespace panda::test { 33class ContainersHashMapTest : public testing::Test { 34public: 35 static void SetUpTestCase() 36 { 37 GTEST_LOG_(INFO) << "SetUpTestCase"; 38 } 39 40 static void TearDownTestCase() 41 { 42 GTEST_LOG_(INFO) << "TearDownCase"; 43 } 44 45 void SetUp() override 46 { 47 TestHelper::CreateEcmaVMWithScope(instance, thread, scope); 48 } 49 50 void TearDown() override 51 { 52 TestHelper::DestroyEcmaVMWithScope(instance, scope); 53 } 54 55 EcmaVM *instance {nullptr}; 56 EcmaHandleScope *scope {nullptr}; 57 JSThread *thread {nullptr}; 58 59 class TestClass : public base::BuiltinsBase { 60 public: 61 static JSTaggedValue TestForEachFunc(EcmaRuntimeCallInfo *argv) 62 { 63 JSThread *thread = argv->GetThread(); 64 JSHandle<JSTaggedValue> value = GetCallArg(argv, 0); 65 JSHandle<JSTaggedValue> key = GetCallArg(argv, 1); 66 JSHandle<JSTaggedValue> map = GetCallArg(argv, 2); // 2 means the secode arg 67 if (!map->IsUndefined()) { 68 if (value->IsNumber()) { 69 JSHandle<JSTaggedValue> newValue(thread, JSTaggedValue(value->GetInt() * 2)); // 2 means mul by 2 70 JSAPIHashMap::Set(thread, JSHandle<JSAPIHashMap>::Cast(map), key, newValue); 71 } 72 } 73 JSHandle<JSAPIHashMap> jsHashMap(GetThis(argv)); 74 JSAPIHashMap::Set(thread, jsHashMap, key, value); 75 return JSTaggedValue::Undefined(); 76 } 77 }; 78protected: 79 JSTaggedValue InitializeHashMapConstructor() 80 { 81 ObjectFactory *factory = thread->GetEcmaVM()->GetFactory(); 82 JSHandle<GlobalEnv> env = thread->GetEcmaVM()->GetGlobalEnv(); 83 84 JSHandle<JSTaggedValue> globalObject = env->GetJSGlobalObject(); 85 JSHandle<JSTaggedValue> key(factory->NewFromASCII("ArkPrivate")); 86 JSHandle<JSTaggedValue> value = 87 JSObject::GetProperty(thread, JSHandle<JSTaggedValue>(globalObject), key).GetValue(); 88 89 auto objCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 90 objCallInfo->SetFunction(JSTaggedValue::Undefined()); 91 objCallInfo->SetThis(value.GetTaggedValue()); 92 objCallInfo->SetCallArg(0, JSTaggedValue(static_cast<int>(ContainerTag::HashMap))); 93 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, objCallInfo); 94 JSTaggedValue result = ContainersPrivate::Load(objCallInfo); 95 TestHelper::TearDownFrame(thread, prev); 96 97 return result; 98 } 99 100 JSHandle<JSAPIHashMap> CreateJSAPIHashMap() 101 { 102 JSHandle<JSFunction> newTarget(thread, InitializeHashMapConstructor()); 103 auto objCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 4); 104 objCallInfo->SetFunction(newTarget.GetTaggedValue()); 105 objCallInfo->SetNewTarget(newTarget.GetTaggedValue()); 106 objCallInfo->SetThis(JSTaggedValue::Undefined()); 107 108 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, objCallInfo); 109 JSTaggedValue result = ContainersHashMap::HashMapConstructor(objCallInfo); 110 TestHelper::TearDownFrame(thread, prev); 111 JSHandle<JSAPIHashMap> map(thread, result); 112 return map; 113 } 114}; 115 116// new HashMap() 117HWTEST_F_L0(ContainersHashMapTest, HashMapConstructor) 118{ 119 InitializeHashMapConstructor(); 120 JSHandle<JSFunction> newTarget(thread, InitializeHashMapConstructor()); 121 122 auto objCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 4); 123 objCallInfo->SetFunction(newTarget.GetTaggedValue()); 124 objCallInfo->SetNewTarget(newTarget.GetTaggedValue()); 125 objCallInfo->SetThis(JSTaggedValue::Undefined()); 126 127 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, objCallInfo); 128 JSTaggedValue result = ContainersHashMap::HashMapConstructor(objCallInfo); 129 TestHelper::TearDownFrame(thread, prev); 130 131 ASSERT_TRUE(result.IsJSAPIHashMap()); 132 JSHandle<JSAPIHashMap> mapHandle(thread, result); 133 JSTaggedValue resultProto = JSTaggedValue::GetPrototype(thread, JSHandle<JSTaggedValue>(mapHandle)); 134 JSTaggedValue funcProto = newTarget->GetFunctionPrototype(); 135 ASSERT_EQ(resultProto, funcProto); 136 int size = mapHandle->GetSize(); 137 ASSERT_EQ(size, 0); 138 139 // test HashMapConstructor exception 140 objCallInfo->SetNewTarget(JSTaggedValue::Undefined()); 141 CONTAINERS_API_EXCEPTION_TEST(ContainersHashMap, HashMapConstructor, objCallInfo); 142} 143 144// hashmap.set(key, value), hashmap.get(key) 145HWTEST_F_L0(ContainersHashMapTest, SetAndGet) 146{ 147 constexpr uint32_t NODE_NUMBERS = 8; 148 JSHandle<JSAPIHashMap> tMap = CreateJSAPIHashMap(); 149 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 150 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 151 callInfo->SetFunction(JSTaggedValue::Undefined()); 152 callInfo->SetThis(tMap.GetTaggedValue()); 153 callInfo->SetCallArg(0, JSTaggedValue(i)); 154 callInfo->SetCallArg(1, JSTaggedValue(i)); 155 156 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 157 JSTaggedValue result = ContainersHashMap::Set(callInfo); 158 TestHelper::TearDownFrame(thread, prev); 159 EXPECT_TRUE(result.IsJSAPIHashMap()); 160 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), i + 1); 161 } 162 163 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 164 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 165 callInfo->SetFunction(JSTaggedValue::Undefined()); 166 callInfo->SetThis(tMap.GetTaggedValue()); 167 callInfo->SetCallArg(0, JSTaggedValue(i)); 168 169 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 170 JSTaggedValue result = ContainersHashMap::Get(callInfo); 171 TestHelper::TearDownFrame(thread, prev); 172 EXPECT_EQ(result, JSTaggedValue(i)); 173 } 174} 175 176// hashmap.hasKey(key), hashmap.hasValue(value) 177HWTEST_F_L0(ContainersHashMapTest, HasKeyAndHasValue) 178{ 179 constexpr uint32_t NODE_NUMBERS = 8; 180 JSHandle<JSAPIHashMap> tMap = CreateJSAPIHashMap(); 181 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 182 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 183 callInfo->SetFunction(JSTaggedValue::Undefined()); 184 callInfo->SetThis(tMap.GetTaggedValue()); 185 callInfo->SetCallArg(0, JSTaggedValue(i)); 186 callInfo->SetCallArg(1, JSTaggedValue(i)); 187 188 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 189 JSTaggedValue result = ContainersHashMap::Set(callInfo); 190 TestHelper::TearDownFrame(thread, prev); 191 EXPECT_TRUE(result.IsJSAPIHashMap()); 192 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), i + 1); 193 } 194 195 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 196 // test hasKey 197 { 198 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 199 callInfo->SetFunction(JSTaggedValue::Undefined()); 200 callInfo->SetThis(tMap.GetTaggedValue()); 201 callInfo->SetCallArg(0, JSTaggedValue(i)); 202 203 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 204 JSTaggedValue result = ContainersHashMap::HasKey(callInfo); 205 TestHelper::TearDownFrame(thread, prev); 206 EXPECT_EQ(result, JSTaggedValue::True()); 207 } 208 // test hasValue 209 { 210 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 211 callInfo->SetFunction(JSTaggedValue::Undefined()); 212 callInfo->SetThis(tMap.GetTaggedValue()); 213 callInfo->SetCallArg(0, JSTaggedValue(i)); 214 215 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 216 JSTaggedValue result = ContainersHashMap::HasValue(callInfo); 217 TestHelper::TearDownFrame(thread, prev); 218 EXPECT_EQ(result, JSTaggedValue::True()); 219 } 220 } 221 222 // test add string 223 ObjectFactory *factory = thread->GetEcmaVM()->GetFactory(); 224 JSMutableHandle<JSTaggedValue> key(thread, JSTaggedValue::Undefined()); 225 JSMutableHandle<JSTaggedValue> value(thread, JSTaggedValue::Undefined()); 226 std::string myKey("mykey"); 227 std::string myValue("myvalue"); 228 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 229 std::string iKey = myKey + std::to_string(i); 230 std::string iValue = myValue + std::to_string(i); 231 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 232 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 233 234 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 235 callInfo->SetFunction(JSTaggedValue::Undefined()); 236 callInfo->SetThis(tMap.GetTaggedValue()); 237 callInfo->SetCallArg(0, key.GetTaggedValue()); 238 callInfo->SetCallArg(1, value.GetTaggedValue()); 239 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 240 JSTaggedValue result = ContainersHashMap::Set(callInfo); 241 TestHelper::TearDownFrame(thread, prev); 242 EXPECT_TRUE(result.IsJSAPIHashMap()); 243 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), NODE_NUMBERS + i + 1); 244 } 245 246 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 247 // test hasKey 248 { 249 std::string iKey = myKey + std::to_string(i); 250 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 251 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 252 callInfo->SetFunction(JSTaggedValue::Undefined()); 253 callInfo->SetThis(tMap.GetTaggedValue()); 254 callInfo->SetCallArg(0, key.GetTaggedValue()); 255 256 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 257 JSTaggedValue result = ContainersHashMap::HasKey(callInfo); 258 TestHelper::TearDownFrame(thread, prev); 259 EXPECT_EQ(result, JSTaggedValue::True()); 260 } 261 // test hasValue 262 { 263 std::string iValue = myValue + std::to_string(i); 264 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 265 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 266 callInfo->SetFunction(JSTaggedValue::Undefined()); 267 callInfo->SetThis(tMap.GetTaggedValue()); 268 callInfo->SetCallArg(0, value.GetTaggedValue()); 269 270 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 271 JSTaggedValue result = ContainersHashMap::HasValue(callInfo); 272 TestHelper::TearDownFrame(thread, prev); 273 EXPECT_EQ(result, JSTaggedValue::True()); 274 } 275 } 276} 277 278// hashmap.keys(), hashmap.values(), hashmap.entries() 279HWTEST_F_L0(ContainersHashMapTest, KeysAndValuesAndEntries) 280{ 281 constexpr uint32_t NODE_NUMBERS = 8; 282 JSHandle<JSAPIHashMap> tMap = CreateJSAPIHashMap(); 283 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 284 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 285 callInfo->SetFunction(JSTaggedValue::Undefined()); 286 callInfo->SetThis(tMap.GetTaggedValue()); 287 callInfo->SetCallArg(0, JSTaggedValue(i)); 288 callInfo->SetCallArg(1, JSTaggedValue(i)); 289 290 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 291 JSTaggedValue result2 = ContainersHashMap::Set(callInfo); 292 TestHelper::TearDownFrame(thread, prev); 293 EXPECT_TRUE(result2.IsJSAPIHashMap()); 294 EXPECT_EQ(JSAPIHashMap::Cast(result2.GetTaggedObject())->GetSize(), i + 1); 295 } 296 297 // test keys 298 auto callInfo1 = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 4); 299 callInfo1->SetFunction(JSTaggedValue::Undefined()); 300 callInfo1->SetThis(tMap.GetTaggedValue()); 301 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo1); 302 JSHandle<JSTaggedValue> iterKeys(thread, ContainersHashMap::Keys(callInfo1)); 303 TestHelper::TearDownFrame(thread, prev); 304 EXPECT_TRUE(iterKeys->IsJSAPIHashMapIterator()); 305 306 JSMutableHandle<JSTaggedValue> result(thread, JSTaggedValue::Undefined()); 307 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 308 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 4); 309 callInfo->SetFunction(JSTaggedValue::Undefined()); 310 callInfo->SetThis(iterKeys.GetTaggedValue()); 311 312 [[maybe_unused]] auto prev1 = TestHelper::SetupFrame(thread, callInfo); 313 result.Update(JSAPIHashMapIterator::Next(callInfo)); 314 TestHelper::TearDownFrame(thread, prev1); 315 JSHandle<JSTaggedValue> iterKey = JSIterator::IteratorValue(thread, result); 316 JSTaggedValue keyFlag = tMap->HasKey(thread, iterKey.GetTaggedValue()); 317 EXPECT_EQ(JSTaggedValue::True(), keyFlag); 318 } 319 320 // test values 321 callInfo1 = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 4); 322 callInfo1->SetFunction(JSTaggedValue::Undefined()); 323 callInfo1->SetThis(tMap.GetTaggedValue()); 324 prev = TestHelper::SetupFrame(thread, callInfo1); 325 JSHandle<JSTaggedValue> iterValues(thread, ContainersHashMap::Values(callInfo1)); 326 TestHelper::TearDownFrame(thread, prev); 327 EXPECT_TRUE(iterValues->IsJSAPIHashMapIterator()); 328 329 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 330 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 4); 331 callInfo->SetFunction(JSTaggedValue::Undefined()); 332 callInfo->SetThis(iterValues.GetTaggedValue()); 333 334 [[maybe_unused]] auto prev2 = TestHelper::SetupFrame(thread, callInfo); 335 result.Update(JSAPIHashMapIterator::Next(callInfo)); 336 TestHelper::TearDownFrame(thread, prev2); 337 JSHandle<JSTaggedValue> iterValue = JSIterator::IteratorValue(thread, result); 338 JSTaggedValue valueFlag = JSAPIHashMap::HasValue(thread, tMap, iterValue); 339 EXPECT_EQ(JSTaggedValue::True(), valueFlag); 340 } 341 342 // test add string 343 ObjectFactory *factory = thread->GetEcmaVM()->GetFactory(); 344 JSMutableHandle<JSTaggedValue> key(thread, JSTaggedValue::Undefined()); 345 JSMutableHandle<JSTaggedValue> value(thread, JSTaggedValue::Undefined()); 346 std::string myKey("mykey"); 347 std::string myValue("myvalue"); 348 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 349 std::string iKey = myKey + std::to_string(i); 350 std::string iValue = myValue + std::to_string(i); 351 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 352 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 353 354 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 355 callInfo->SetFunction(JSTaggedValue::Undefined()); 356 callInfo->SetThis(tMap.GetTaggedValue()); 357 callInfo->SetCallArg(0, key.GetTaggedValue()); 358 callInfo->SetCallArg(1, value.GetTaggedValue()); 359 [[maybe_unused]] auto prev3 = TestHelper::SetupFrame(thread, callInfo); 360 JSTaggedValue result1 = ContainersHashMap::Set(callInfo); 361 TestHelper::TearDownFrame(thread, prev3); 362 EXPECT_TRUE(result1.IsJSAPIHashMap()); 363 EXPECT_EQ(JSAPIHashMap::Cast(result1.GetTaggedObject())->GetSize(), NODE_NUMBERS + i + 1); 364 } 365 EXPECT_EQ(tMap->GetSize(), NODE_NUMBERS * 2); 366 // test keys after add 367 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 368 std::string iKey = myKey + std::to_string(i); 369 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 370 JSTaggedValue keyFlag = tMap->HasKey(thread, key.GetTaggedValue()); 371 EXPECT_EQ(JSTaggedValue::True(), keyFlag); 372 } 373 // test values after add 374 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 375 std::string iValue = myValue + std::to_string(i); 376 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 377 JSTaggedValue valueFlag = JSAPIHashMap::HasValue(thread, tMap, value); 378 EXPECT_EQ(JSTaggedValue::True(), valueFlag); 379 } 380 381 // test entries 382 { 383 auto callInfo2 = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 4); 384 callInfo2->SetFunction(JSTaggedValue::Undefined()); 385 callInfo2->SetThis(tMap.GetTaggedValue()); 386 [[maybe_unused]] auto prev6 = TestHelper::SetupFrame(thread, callInfo2); 387 JSHandle<JSTaggedValue> iter(thread, ContainersHashMap::Entries(callInfo2)); 388 TestHelper::TearDownFrame(thread, prev6); 389 EXPECT_TRUE(iter->IsJSAPIHashMapIterator()); 390 391 JSHandle<JSTaggedValue> first(thread, JSTaggedValue(0)); 392 JSHandle<JSTaggedValue> second(thread, JSTaggedValue(1)); 393 JSMutableHandle<JSTaggedValue> result3(thread, JSTaggedValue::Undefined()); 394 JSMutableHandle<JSTaggedValue> entries(thread, JSTaggedValue::Undefined()); 395 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 396 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 4); 397 callInfo->SetFunction(JSTaggedValue::Undefined()); 398 callInfo->SetThis(iter.GetTaggedValue()); 399 400 [[maybe_unused]] auto prev1 = TestHelper::SetupFrame(thread, callInfo); 401 result3.Update(JSAPIHashMapIterator::Next(callInfo)); 402 TestHelper::TearDownFrame(thread, prev1); 403 entries.Update(JSIterator::IteratorValue(thread, result3).GetTaggedValue()); 404 JSHandle<JSTaggedValue> iterKey = JSObject::GetProperty(thread, entries, first).GetValue(); 405 JSTaggedValue keyFlag = tMap->HasKey(thread, iterKey.GetTaggedValue()); 406 EXPECT_EQ(JSTaggedValue::True(), keyFlag); 407 JSHandle<JSTaggedValue> iterValue = JSObject::GetProperty(thread, entries, second).GetValue(); 408 JSTaggedValue valueFlag = JSAPIHashMap::HasValue(thread, tMap, iterValue); 409 EXPECT_EQ(JSTaggedValue::True(), valueFlag); 410 } 411 412 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 413 std::string iKey = myKey + std::to_string(i); 414 std::string iValue = myValue + std::to_string(i); 415 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 416 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 417 JSTaggedValue keyFlag = tMap->HasKey(thread, key.GetTaggedValue()); 418 EXPECT_EQ(JSTaggedValue::True(), keyFlag); 419 JSTaggedValue valueFlag = JSAPIHashMap::HasValue(thread, tMap, value); 420 EXPECT_EQ(JSTaggedValue::True(), valueFlag); 421 } 422 } 423} 424 425// hashmap.remove(key) 426HWTEST_F_L0(ContainersHashMapTest, Remove) 427{ 428 constexpr uint32_t NODE_NUMBERS = 8; 429 JSHandle<JSAPIHashMap> tMap = CreateJSAPIHashMap(); 430 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 431 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 432 callInfo->SetFunction(JSTaggedValue::Undefined()); 433 callInfo->SetThis(tMap.GetTaggedValue()); 434 callInfo->SetCallArg(0, JSTaggedValue(i)); 435 callInfo->SetCallArg(1, JSTaggedValue(i)); 436 437 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 438 JSTaggedValue result = ContainersHashMap::Set(callInfo); 439 TestHelper::TearDownFrame(thread, prev); 440 EXPECT_TRUE(result.IsJSAPIHashMap()); 441 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), i + 1); 442 } 443 444 { 445 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 446 callInfo->SetFunction(JSTaggedValue::Undefined()); 447 callInfo->SetThis(tMap.GetTaggedValue()); 448 callInfo->SetCallArg(0, JSTaggedValue(NODE_NUMBERS / 2)); 449 450 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 451 JSTaggedValue rValue = ContainersHashMap::Remove(callInfo); 452 TestHelper::TearDownFrame(thread, prev); 453 EXPECT_EQ(rValue, JSTaggedValue(NODE_NUMBERS / 2)); 454 EXPECT_EQ(tMap->GetSize(), NODE_NUMBERS - 1); 455 } 456 457 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 458 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 459 callInfo->SetFunction(JSTaggedValue::Undefined()); 460 callInfo->SetThis(tMap.GetTaggedValue()); 461 callInfo->SetCallArg(0, JSTaggedValue(i)); 462 463 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 464 JSTaggedValue result = ContainersHashMap::Get(callInfo); 465 TestHelper::TearDownFrame(thread, prev); 466 if (i == (NODE_NUMBERS / 2)) { 467 EXPECT_EQ(result, JSTaggedValue::Undefined()); 468 } else { 469 EXPECT_EQ(result, JSTaggedValue(i)); 470 } 471 } 472 473 // test add string 474 ObjectFactory *factory = thread->GetEcmaVM()->GetFactory(); 475 JSMutableHandle<JSTaggedValue> key(thread, JSTaggedValue::Undefined()); 476 JSMutableHandle<JSTaggedValue> value(thread, JSTaggedValue::Undefined()); 477 std::string myKey("mykey"); 478 std::string myValue("myvalue"); 479 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 480 std::string iKey = myKey + std::to_string(i); 481 std::string iValue = myValue + std::to_string(i); 482 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 483 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 484 485 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 486 callInfo->SetFunction(JSTaggedValue::Undefined()); 487 callInfo->SetThis(tMap.GetTaggedValue()); 488 callInfo->SetCallArg(0, key.GetTaggedValue()); 489 callInfo->SetCallArg(1, value.GetTaggedValue()); 490 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 491 JSTaggedValue result = ContainersHashMap::Set(callInfo); 492 TestHelper::TearDownFrame(thread, prev); 493 EXPECT_TRUE(result.IsJSAPIHashMap()); 494 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), NODE_NUMBERS + i); 495 } 496 497 { 498 std::string iKey = myKey + std::to_string(NODE_NUMBERS / 2); 499 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 500 std::string iValue = myValue + std::to_string(NODE_NUMBERS / 2); 501 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 502 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 503 callInfo->SetFunction(JSTaggedValue::Undefined()); 504 callInfo->SetThis(tMap.GetTaggedValue()); 505 callInfo->SetCallArg(0, key.GetTaggedValue()); 506 507 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 508 JSTaggedValue rValue = ContainersHashMap::Remove(callInfo); 509 TestHelper::TearDownFrame(thread, prev); 510 EXPECT_TRUE(JSTaggedValue::SameValue(rValue, value.GetTaggedValue())); 511 EXPECT_EQ(tMap->GetSize(), NODE_NUMBERS * 2 - 2); 512 } 513} 514 515// hashmap.setAll(map) 516HWTEST_F_L0(ContainersHashMapTest, SetAll) 517{ 518 constexpr uint32_t NODE_NUMBERS = 8; 519 JSHandle<JSAPIHashMap> sMap = CreateJSAPIHashMap(); 520 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 521 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 522 callInfo->SetFunction(JSTaggedValue::Undefined()); 523 callInfo->SetThis(sMap.GetTaggedValue()); 524 callInfo->SetCallArg(0, JSTaggedValue(i)); 525 callInfo->SetCallArg(1, JSTaggedValue(i)); 526 527 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 528 JSTaggedValue result = ContainersHashMap::Set(callInfo); 529 TestHelper::TearDownFrame(thread, prev); 530 EXPECT_TRUE(result.IsJSAPIHashMap()); 531 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), i + 1); 532 } 533 534 JSHandle<JSAPIHashMap> dMap = CreateJSAPIHashMap(); 535 { 536 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 537 callInfo->SetFunction(JSTaggedValue::Undefined()); 538 callInfo->SetThis(dMap.GetTaggedValue()); 539 callInfo->SetCallArg(0, sMap.GetTaggedValue()); 540 541 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 542 ContainersHashMap::SetAll(callInfo); 543 TestHelper::TearDownFrame(thread, prev); 544 EXPECT_EQ(dMap->GetSize(), NODE_NUMBERS); 545 } 546 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 547 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 548 callInfo->SetFunction(JSTaggedValue::Undefined()); 549 callInfo->SetThis(dMap.GetTaggedValue()); 550 callInfo->SetCallArg(0, JSTaggedValue(i)); 551 552 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 553 JSTaggedValue result = ContainersHashMap::Get(callInfo); 554 TestHelper::TearDownFrame(thread, prev); 555 EXPECT_EQ(result, JSTaggedValue(i)); 556 } 557 558 // test add string 559 ObjectFactory *factory = thread->GetEcmaVM()->GetFactory(); 560 JSMutableHandle<JSTaggedValue> key(thread, JSTaggedValue::Undefined()); 561 JSMutableHandle<JSTaggedValue> value(thread, JSTaggedValue::Undefined()); 562 std::string myKey("mykey"); 563 std::string myValue("myvalue"); 564 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 565 std::string iKey = myKey + std::to_string(i); 566 std::string iValue = myValue + std::to_string(i); 567 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 568 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 569 570 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 571 callInfo->SetFunction(JSTaggedValue::Undefined()); 572 callInfo->SetThis(sMap.GetTaggedValue()); 573 callInfo->SetCallArg(0, key.GetTaggedValue()); 574 callInfo->SetCallArg(1, value.GetTaggedValue()); 575 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 576 JSTaggedValue result = ContainersHashMap::Set(callInfo); 577 TestHelper::TearDownFrame(thread, prev); 578 EXPECT_TRUE(result.IsJSAPIHashMap()); 579 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), NODE_NUMBERS + i + 1); 580 } 581 { 582 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 583 callInfo->SetFunction(JSTaggedValue::Undefined()); 584 callInfo->SetThis(dMap.GetTaggedValue()); 585 callInfo->SetCallArg(0, sMap.GetTaggedValue()); 586 587 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 588 ContainersHashMap::SetAll(callInfo); 589 TestHelper::TearDownFrame(thread, prev); 590 EXPECT_EQ(dMap->GetSize(), NODE_NUMBERS * 2); 591 } 592 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 593 std::string iKey = myKey + std::to_string(i); 594 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 595 std::string iValue = myValue + std::to_string(i); 596 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 597 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 598 callInfo->SetFunction(JSTaggedValue::Undefined()); 599 callInfo->SetThis(dMap.GetTaggedValue()); 600 callInfo->SetCallArg(0, key.GetTaggedValue()); 601 602 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 603 JSTaggedValue result = ContainersHashMap::Get(callInfo); 604 TestHelper::TearDownFrame(thread, prev); 605 EXPECT_TRUE(JSTaggedValue::SameValue(result, value.GetTaggedValue())); 606 } 607 EXPECT_EQ(dMap->GetSize(), 2 * NODE_NUMBERS); 608} 609 610// hashmap.clear() 611HWTEST_F_L0(ContainersHashMapTest, Clear) 612{ 613 constexpr uint32_t NODE_NUMBERS = 8; 614 JSHandle<JSAPIHashMap> tMap = CreateJSAPIHashMap(); 615 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 616 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 617 callInfo->SetFunction(JSTaggedValue::Undefined()); 618 callInfo->SetThis(tMap.GetTaggedValue()); 619 callInfo->SetCallArg(0, JSTaggedValue(i)); 620 callInfo->SetCallArg(1, JSTaggedValue(i)); 621 622 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 623 JSTaggedValue result = ContainersHashMap::Set(callInfo); 624 TestHelper::TearDownFrame(thread, prev); 625 EXPECT_TRUE(result.IsJSAPIHashMap()); 626 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), i + 1); 627 } 628 629 // test clear 630 { 631 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 4); 632 callInfo->SetFunction(JSTaggedValue::Undefined()); 633 callInfo->SetThis(tMap.GetTaggedValue()); 634 635 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 636 ContainersHashMap::Clear(callInfo); 637 TestHelper::TearDownFrame(thread, prev); 638 EXPECT_EQ(tMap->GetSize(), (uint32_t)0); 639 } 640 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 641 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 642 callInfo->SetFunction(JSTaggedValue::Undefined()); 643 callInfo->SetThis(tMap.GetTaggedValue()); 644 callInfo->SetCallArg(0, JSTaggedValue(i)); 645 646 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 647 JSTaggedValue result = ContainersHashMap::Get(callInfo); 648 TestHelper::TearDownFrame(thread, prev); 649 EXPECT_EQ(result, JSTaggedValue::Undefined()); 650 } 651 652 // test add string 653 ObjectFactory *factory = thread->GetEcmaVM()->GetFactory(); 654 JSMutableHandle<JSTaggedValue> key(thread, JSTaggedValue::Undefined()); 655 JSMutableHandle<JSTaggedValue> value(thread, JSTaggedValue::Undefined()); 656 std::string myKey("mykey"); 657 std::string myValue("myvalue"); 658 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 659 std::string iKey = myKey + std::to_string(i); 660 std::string iValue = myValue + std::to_string(i); 661 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 662 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 663 664 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 665 callInfo->SetFunction(JSTaggedValue::Undefined()); 666 callInfo->SetThis(tMap.GetTaggedValue()); 667 callInfo->SetCallArg(0, key.GetTaggedValue()); 668 callInfo->SetCallArg(1, value.GetTaggedValue()); 669 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 670 JSTaggedValue result = ContainersHashMap::Set(callInfo); 671 TestHelper::TearDownFrame(thread, prev); 672 EXPECT_TRUE(result.IsJSAPIHashMap()); 673 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), i + 1); 674 } 675 676 // test clear 677 { 678 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 4); 679 callInfo->SetFunction(JSTaggedValue::Undefined()); 680 callInfo->SetThis(tMap.GetTaggedValue()); 681 682 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 683 ContainersHashMap::Clear(callInfo); 684 TestHelper::TearDownFrame(thread, prev); 685 EXPECT_EQ(tMap->GetSize(), (uint32_t)0); 686 } 687 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 688 std::string iKey = myKey + std::to_string(i); 689 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 690 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 691 callInfo->SetFunction(JSTaggedValue::Undefined()); 692 callInfo->SetThis(tMap.GetTaggedValue()); 693 callInfo->SetCallArg(0, key.GetTaggedValue()); 694 695 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 696 JSTaggedValue result = ContainersHashMap::Get(callInfo); 697 TestHelper::TearDownFrame(thread, prev); 698 EXPECT_EQ(result, JSTaggedValue::Undefined()); 699 } 700} 701 702// hashmap.replace(key, value) 703HWTEST_F_L0(ContainersHashMapTest, Replace) 704{ 705 constexpr uint32_t NODE_NUMBERS = 8; 706 JSHandle<JSAPIHashMap> tMap = CreateJSAPIHashMap(); 707 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 708 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 709 callInfo->SetFunction(JSTaggedValue::Undefined()); 710 callInfo->SetThis(tMap.GetTaggedValue()); 711 callInfo->SetCallArg(0, JSTaggedValue(i)); 712 callInfo->SetCallArg(1, JSTaggedValue(i)); 713 714 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 715 JSTaggedValue result = ContainersHashMap::Set(callInfo); 716 TestHelper::TearDownFrame(thread, prev); 717 EXPECT_TRUE(result.IsJSAPIHashMap()); 718 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), i + 1); 719 } 720 721 { 722 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 723 callInfo->SetFunction(JSTaggedValue::Undefined()); 724 callInfo->SetThis(tMap.GetTaggedValue()); 725 callInfo->SetCallArg(0, JSTaggedValue(NODE_NUMBERS / 2)); 726 callInfo->SetCallArg(1, JSTaggedValue(NODE_NUMBERS)); 727 728 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 729 JSTaggedValue result = ContainersHashMap::Replace(callInfo); 730 TestHelper::TearDownFrame(thread, prev); 731 EXPECT_EQ(result, JSTaggedValue::True()); 732 EXPECT_EQ(tMap->GetSize(), NODE_NUMBERS); 733 } 734 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 735 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 736 callInfo->SetFunction(JSTaggedValue::Undefined()); 737 callInfo->SetThis(tMap.GetTaggedValue()); 738 callInfo->SetCallArg(0, JSTaggedValue(i)); 739 740 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 741 JSTaggedValue result = ContainersHashMap::Get(callInfo); 742 TestHelper::TearDownFrame(thread, prev); 743 if (i == (NODE_NUMBERS / 2)) { 744 EXPECT_EQ(result, JSTaggedValue(NODE_NUMBERS)); 745 } else { 746 EXPECT_EQ(result, JSTaggedValue(i)); 747 } 748 } 749 750 // test add string 751 ObjectFactory *factory = thread->GetEcmaVM()->GetFactory(); 752 JSMutableHandle<JSTaggedValue> key(thread, JSTaggedValue::Undefined()); 753 JSMutableHandle<JSTaggedValue> value(thread, JSTaggedValue::Undefined()); 754 std::string myKey("mykey"); 755 std::string myValue("myvalue"); 756 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 757 std::string iKey = myKey + std::to_string(i); 758 std::string iValue = myValue + std::to_string(i); 759 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 760 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 761 762 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 763 callInfo->SetFunction(JSTaggedValue::Undefined()); 764 callInfo->SetThis(tMap.GetTaggedValue()); 765 callInfo->SetCallArg(0, key.GetTaggedValue()); 766 callInfo->SetCallArg(1, value.GetTaggedValue()); 767 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 768 JSTaggedValue result = ContainersHashMap::Set(callInfo); 769 TestHelper::TearDownFrame(thread, prev); 770 EXPECT_TRUE(result.IsJSAPIHashMap()); 771 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), NODE_NUMBERS + i + 1); 772 } 773 774 { 775 std::string iKey = myKey + std::to_string(NODE_NUMBERS / 2); 776 std::string iValue = myValue + std::to_string(NODE_NUMBERS); 777 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 778 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 779 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 780 callInfo->SetFunction(JSTaggedValue::Undefined()); 781 callInfo->SetThis(tMap.GetTaggedValue()); 782 callInfo->SetCallArg(0, key.GetTaggedValue()); 783 callInfo->SetCallArg(1, value.GetTaggedValue()); 784 785 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 786 JSTaggedValue result = ContainersHashMap::Replace(callInfo); 787 TestHelper::TearDownFrame(thread, prev); 788 EXPECT_EQ(result, JSTaggedValue::True()); 789 EXPECT_EQ(tMap->GetSize(), NODE_NUMBERS * 2); 790 } 791 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 792 std::string iKey = myKey + std::to_string(i); 793 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 794 std::string iValue; 795 if (i == (NODE_NUMBERS / 2)) { 796 iValue = myValue + std::to_string(NODE_NUMBERS); 797 } else { 798 iValue = myValue + std::to_string(i); 799 } 800 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 801 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 802 callInfo->SetFunction(JSTaggedValue::Undefined()); 803 callInfo->SetThis(tMap.GetTaggedValue()); 804 callInfo->SetCallArg(0, key.GetTaggedValue()); 805 806 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 807 JSTaggedValue result = ContainersHashMap::Get(callInfo); 808 TestHelper::TearDownFrame(thread, prev); 809 EXPECT_TRUE(JSTaggedValue::SameValue(result, value.GetTaggedValue())); 810 } 811} 812 813// hashmap.ForEach(callbackfn, this) 814HWTEST_F_L0(ContainersHashMapTest, ForEach) 815{ 816 constexpr uint32_t NODE_NUMBERS = 8; 817 JSHandle<JSAPIHashMap> tMap = CreateJSAPIHashMap(); 818 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 819 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 820 callInfo->SetFunction(JSTaggedValue::Undefined()); 821 callInfo->SetThis(tMap.GetTaggedValue()); 822 callInfo->SetCallArg(0, JSTaggedValue(i)); 823 callInfo->SetCallArg(1, JSTaggedValue(i)); 824 825 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 826 JSTaggedValue result = ContainersHashMap::Set(callInfo); 827 TestHelper::TearDownFrame(thread, prev); 828 EXPECT_TRUE(result.IsJSAPIHashMap()); 829 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), i + 1); 830 } 831 // test foreach function with TestForEachFunc; 832 ObjectFactory *factory = thread->GetEcmaVM()->GetFactory(); 833 JSHandle<JSAPIHashMap> dMap = CreateJSAPIHashMap(); 834 { 835 JSHandle<GlobalEnv> env = thread->GetEcmaVM()->GetGlobalEnv(); 836 JSHandle<JSFunction> func = factory->NewJSFunction(env, reinterpret_cast<void *>(TestClass::TestForEachFunc)); 837 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 838 callInfo->SetFunction(JSTaggedValue::Undefined()); 839 callInfo->SetThis(tMap.GetTaggedValue()); 840 callInfo->SetCallArg(0, func.GetTaggedValue()); 841 callInfo->SetCallArg(1, dMap.GetTaggedValue()); 842 843 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 844 ContainersHashMap::ForEach(callInfo); 845 TestHelper::TearDownFrame(thread, prev); 846 } 847 EXPECT_EQ(dMap->GetSize(), NODE_NUMBERS); 848 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 849 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 850 callInfo->SetFunction(JSTaggedValue::Undefined()); 851 callInfo->SetThis(tMap.GetTaggedValue()); 852 callInfo->SetCallArg(0, JSTaggedValue(i)); 853 854 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 855 JSTaggedValue result = ContainersHashMap::Get(callInfo); 856 TestHelper::TearDownFrame(thread, prev); 857 EXPECT_EQ(result, JSTaggedValue(i * 2)); 858 } 859 860 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 861 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 862 callInfo->SetFunction(JSTaggedValue::Undefined()); 863 callInfo->SetThis(dMap.GetTaggedValue()); 864 callInfo->SetCallArg(0, JSTaggedValue(i)); 865 866 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 867 JSTaggedValue result = ContainersHashMap::Get(callInfo); 868 TestHelper::TearDownFrame(thread, prev); 869 EXPECT_EQ(result, JSTaggedValue(i)); 870 } 871 872 // test add string 873 JSMutableHandle<JSTaggedValue> key(thread, JSTaggedValue::Undefined()); 874 JSMutableHandle<JSTaggedValue> value(thread, JSTaggedValue::Undefined()); 875 std::string myKey("mykey"); 876 std::string myValue("myvalue"); 877 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 878 std::string iKey = myKey + std::to_string(i); 879 std::string iValue = myValue + std::to_string(i); 880 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 881 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 882 883 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 884 callInfo->SetFunction(JSTaggedValue::Undefined()); 885 callInfo->SetThis(tMap.GetTaggedValue()); 886 callInfo->SetCallArg(0, key.GetTaggedValue()); 887 callInfo->SetCallArg(1, value.GetTaggedValue()); 888 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 889 JSTaggedValue result = ContainersHashMap::Set(callInfo); 890 TestHelper::TearDownFrame(thread, prev); 891 EXPECT_TRUE(result.IsJSAPIHashMap()); 892 EXPECT_EQ(JSAPIHashMap::Cast(result.GetTaggedObject())->GetSize(), NODE_NUMBERS + i + 1); 893 } 894 EXPECT_EQ(tMap->GetSize(), NODE_NUMBERS * 2); 895 EXPECT_EQ(dMap->GetSize(), NODE_NUMBERS); 896 897 // test foreach function with TestForEachFunc; 898 { 899 JSHandle<GlobalEnv> env = thread->GetEcmaVM()->GetGlobalEnv(); 900 JSHandle<JSFunction> func = factory->NewJSFunction(env, reinterpret_cast<void *>(TestClass::TestForEachFunc)); 901 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 902 callInfo->SetFunction(JSTaggedValue::Undefined()); 903 callInfo->SetThis(tMap.GetTaggedValue()); 904 callInfo->SetCallArg(0, func.GetTaggedValue()); 905 callInfo->SetCallArg(1, dMap.GetTaggedValue()); 906 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 907 ContainersHashMap::ForEach(callInfo); 908 TestHelper::TearDownFrame(thread, prev); 909 } 910 911 EXPECT_EQ(dMap->GetSize(), NODE_NUMBERS * 2); 912 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 913 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 914 callInfo->SetFunction(JSTaggedValue::Undefined()); 915 callInfo->SetThis(tMap.GetTaggedValue()); 916 callInfo->SetCallArg(0, JSTaggedValue(i)); 917 918 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 919 JSTaggedValue result = ContainersHashMap::Get(callInfo); 920 TestHelper::TearDownFrame(thread, prev); 921 EXPECT_EQ(result, JSTaggedValue(i * 4)); // 4 means 4 times 922 } 923 924 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 925 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 926 callInfo->SetFunction(JSTaggedValue::Undefined()); 927 callInfo->SetThis(dMap.GetTaggedValue()); 928 callInfo->SetCallArg(0, JSTaggedValue(i)); 929 930 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 931 JSTaggedValue result = ContainersHashMap::Get(callInfo); 932 TestHelper::TearDownFrame(thread, prev); 933 EXPECT_EQ(result, JSTaggedValue(i * 2)); 934 } 935 936 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 937 std::string iKey = myKey + std::to_string(i); 938 std::string iValue = myValue + std::to_string(i); 939 key.Update(factory->NewFromStdString(iKey).GetTaggedValue()); 940 value.Update(factory->NewFromStdString(iValue).GetTaggedValue()); 941 942 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6); 943 callInfo->SetFunction(JSTaggedValue::Undefined()); 944 callInfo->SetThis(dMap.GetTaggedValue()); 945 callInfo->SetCallArg(0, key.GetTaggedValue()); 946 947 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 948 JSTaggedValue result = ContainersHashMap::Get(callInfo); 949 TestHelper::TearDownFrame(thread, prev); 950 EXPECT_EQ(result, value.GetTaggedValue()); 951 } 952} 953 954HWTEST_F_L0(ContainersHashMapTest, ProxyOfGetLength) 955{ 956 constexpr uint32_t NODE_NUMBERS = 8; 957 JSHandle<JSAPIHashMap> treeMap = CreateJSAPIHashMap(); 958 auto callInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8); 959 callInfo->SetFunction(JSTaggedValue::Undefined()); 960 JSHandle<JSProxy> proxy = CreateJSProxyHandle(thread); 961 proxy->SetTarget(thread, treeMap.GetTaggedValue()); 962 callInfo->SetThis(proxy.GetTaggedValue()); 963 964 for (uint32_t i = 0; i < NODE_NUMBERS; i++) { 965 callInfo->SetCallArg(0, JSTaggedValue(i)); 966 callInfo->SetCallArg(1, JSTaggedValue(i + 1)); 967 [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, callInfo); 968 ContainersHashMap::Set(callInfo); 969 TestHelper::TearDownFrame(thread, prev); 970 971 [[maybe_unused]] auto prev1 = TestHelper::SetupFrame(thread, callInfo); 972 JSTaggedValue retult = ContainersHashMap::GetLength(callInfo); 973 TestHelper::TearDownFrame(thread, prev1); 974 EXPECT_EQ(retult, JSTaggedValue(i + 1)); 975 } 976} 977 978HWTEST_F_L0(ContainersHashMapTest, ExceptionReturn) 979{ 980 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, SetAll); 981 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, Keys); 982 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, Values); 983 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, Entries); 984 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, ForEach); 985 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, Set); 986 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, Get); 987 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, Remove); 988 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, HasKey); 989 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, HasValue); 990 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, Replace); 991 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, Clear); 992 CONTAINERS_API_TYPE_MISMATCH_EXCEPTION_TEST(ContainersHashMap, GetLength); 993 994 JSHandle<JSAPIHashMap> treeMap = CreateJSAPIHashMap(); 995 { 996 auto callInfo = NewEmptyCallInfo(thread); 997 callInfo->SetThis(treeMap.GetTaggedValue()); 998 CONTAINERS_API_EXCEPTION_TEST(ContainersHashMap, SetAll, callInfo); 999 } 1000} 1001} // namespace panda::test 1002