/*
 * Copyright (C) 2011 Google Inc. All rights reserved.
 * Copyright (C) 2017 Apple Inc. All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
 * THE POSSIBILITY OF SUCH DAMAGE.
 */

#include "config.h"

#include "Helpers/Counters.h"
#include "DeletedAddressOfOperator.h"
#include "MoveOnly.h"
#include "RefLogger.h"
#include "Helpers/Test.h"
#include <string>
#include <wtf/HashMap.h>
#include <wtf/InlineWeakPtr.h>
#include <wtf/Ref.h>
#include <wtf/RefCountedAndCanMakeWeakPtr.h>
#include <wtf/RefCountedWithInlineWeakPtr.h>
#include <wtf/UniqueRef.h>
#include <wtf/WeakPtr.h>
#include <wtf/text/MakeString.h>
#include <wtf/text/StringHash.h>

namespace {

class InlineWeakPtrObject : public RefCountedWithInlineWeakPtr<InlineWeakPtrObject> {
public:
    static Ref<InlineWeakPtrObject> create()
    {
        return createRefCountedWithInlineWeakPtr<InlineWeakPtrObject>();
    }
};

}

namespace TestWebKitAPI {

typedef WTF::HashMap<int, int> IntHashMap;

TEST(WTF_HashMap, HashTableIteratorComparison)
{
    IntHashMap map;
    map.add(1, 2);
    ASSERT_TRUE(map.begin() != map.end());
    ASSERT_FALSE(map.begin() == map.end());

    IntHashMap::const_iterator begin = map.begin();
    ASSERT_TRUE(begin == map.begin());
    ASSERT_TRUE(map.begin() == begin);
    ASSERT_TRUE(begin != map.end());
    ASSERT_TRUE(map.end() != begin);
    ASSERT_FALSE(begin != map.begin());
    ASSERT_FALSE(map.begin() != begin);
    ASSERT_FALSE(begin == map.end());
    ASSERT_FALSE(map.end() == begin);
}

struct TestDoubleHashTraits : HashTraits<double> {
    static constexpr unsigned minimumTableSize = 8;
};

typedef HashMap<double, int64_t, DefaultHash<double>, TestDoubleHashTraits> DoubleHashMap;

static int bucketForKey(double key)
{
    return DefaultHash<double>::hash(key) & (TestDoubleHashTraits::minimumTableSize - 1);
}

template<typename T> struct BigTableHashTraits : public HashTraits<T> {
    static const int minimumTableSize = WTF::HashTableCapacityForSize<4096>::value;
};

template<typename T> struct ZeroHash : public IntHash<T> {
    static unsigned hash(const T&) { return 0; }
};

TEST(WTF_HashMap, DoubleHashCollisions)
{
    // The "clobber" key here is one that ends up stealing the bucket that the -0 key
    // originally wants to be in. This makes the 0 and -0 keys collide and the test then
    // fails unless the FloatHash::equals() implementation can distinguish them.
    const double clobberKey = 7;
    const double zeroKey = 0;
    const double negativeZeroKey = -zeroKey;

    DoubleHashMap map;
#if !CHECK_HASHTABLE_ITERATORS &&!DUMP_HASHTABLE_STATS_PER_TABLE
    static_assert(sizeof(map) == sizeof(void*));
#endif

    map.add(clobberKey, 1);
    map.add(zeroKey, 2);
    map.add(negativeZeroKey, 3);

    ASSERT_EQ(bucketForKey(clobberKey), bucketForKey(negativeZeroKey));
    ASSERT_EQ(map.get(clobberKey), 1);
    ASSERT_EQ(map.get(zeroKey), 2);
    ASSERT_EQ(map.get(negativeZeroKey), 3);
}

TEST(WTF_HashMap, MoveOnlyValues)
{
    HashMap<unsigned, MoveOnly> moveOnlyValues;

    for (size_t i = 0; i < 100; ++i) {
        MoveOnly moveOnly(i + 1);
        moveOnlyValues.set(i + 1, WTF::move(moveOnly));
    }

    for (size_t i = 0; i < 100; ++i) {
        auto it = moveOnlyValues.find(i + 1);
        ASSERT_FALSE(it == moveOnlyValues.end());
    }

    for (size_t i = 0; i < 50; ++i)
        ASSERT_EQ(moveOnlyValues.take(i + 1).value(), i + 1);

    for (size_t i = 50; i < 100; ++i)
        ASSERT_TRUE(moveOnlyValues.remove(i + 1));

    ASSERT_TRUE(moveOnlyValues.isEmpty());
}

TEST(WTF_HashMap, MoveOnlyKeys)
{
    HashMap<MoveOnly, unsigned> moveOnlyKeys;

    for (size_t i = 0; i < 100; ++i) {
        MoveOnly moveOnly(i + 1);
        moveOnlyKeys.set(WTF::move(moveOnly), i + 1);
    }

    for (size_t i = 0; i < 100; ++i) {
        auto it = moveOnlyKeys.find(MoveOnly(i + 1));
        ASSERT_FALSE(it == moveOnlyKeys.end());
    }

    for (size_t i = 0; i < 100; ++i)
        ASSERT_FALSE(moveOnlyKeys.add(MoveOnly(i + 1), i + 1).isNewEntry);

    for (size_t i = 0; i < 100; ++i)
        ASSERT_TRUE(moveOnlyKeys.remove(MoveOnly(i + 1)));

    ASSERT_TRUE(moveOnlyKeys.isEmpty());
}

TEST(WTF_HashMap, InitializerList)
{
    HashMap<unsigned, std::string> map = {
        { 1, "one" },
        { 2, "two" },
        { 3, "three" },
        { 4, "four" },
    };

    EXPECT_EQ(4u, map.size());

    EXPECT_EQ("one", map.get(1));
    EXPECT_EQ("two", map.get(2));
    EXPECT_EQ("three", map.get(3));
    EXPECT_EQ("four", map.get(4));
    EXPECT_EQ(std::string(), map.get(5));
}

TEST(WTF_HashMap, EfficientGetter)
{
    HashMap<unsigned, CopyMoveCounter> map;
    map.set(1, CopyMoveCounter());

    {
        CopyMoveCounter::TestingScope scope;
        map.get(1);
        EXPECT_EQ(0U, CopyMoveCounter::constructionCount);
        EXPECT_EQ(1U, CopyMoveCounter::copyCount);
        EXPECT_EQ(0U, CopyMoveCounter::moveCount);
    }

    {
        CopyMoveCounter::TestingScope scope;
        map.get(2);
        EXPECT_EQ(1U, CopyMoveCounter::constructionCount);
        EXPECT_EQ(0U, CopyMoveCounter::copyCount);
        EXPECT_EQ(1U, CopyMoveCounter::moveCount);
    }
}

TEST(WTF_HashMap, UniquePtrKey)
{
    ConstructorDestructorCounter::TestingScope scope;

    HashMap<std::unique_ptr<ConstructorDestructorCounter>, int> map;

    auto uniquePtr = makeUnique<ConstructorDestructorCounter>();
    map.add(WTF::move(uniquePtr), 2);

    EXPECT_EQ(1u, ConstructorDestructorCounter::constructionCount);
    EXPECT_EQ(0u, ConstructorDestructorCounter::destructionCount);

    map.clear();
    
    EXPECT_EQ(1u, ConstructorDestructorCounter::constructionCount);
    EXPECT_EQ(1u, ConstructorDestructorCounter::destructionCount);
}

TEST(WTF_HashMap, UniquePtrKey_CustomDeleter)
{
    ConstructorDestructorCounter::TestingScope constructorDestructorCounterScope;
    DeleterCounter<ConstructorDestructorCounter>::TestingScope deleterCounterScope;

    HashMap<std::unique_ptr<ConstructorDestructorCounter, DeleterCounter<ConstructorDestructorCounter>>, int> map;

    std::unique_ptr<ConstructorDestructorCounter, DeleterCounter<ConstructorDestructorCounter>> uniquePtr(new ConstructorDestructorCounter(), DeleterCounter<ConstructorDestructorCounter>());
    map.add(WTF::move(uniquePtr), 2);

    EXPECT_EQ(1u, ConstructorDestructorCounter::constructionCount);
    EXPECT_EQ(0u, ConstructorDestructorCounter::destructionCount);

    EXPECT_EQ(0u, DeleterCounter<ConstructorDestructorCounter>::deleterCount());

    map.clear();
    
    EXPECT_EQ(1u, ConstructorDestructorCounter::constructionCount);
    EXPECT_EQ(1u, ConstructorDestructorCounter::destructionCount);

    EXPECT_EQ(1u, DeleterCounter<ConstructorDestructorCounter>::deleterCount());
}

TEST(WTF_HashMap, UniquePtrKey_FindUsingRawPointer)
{
    HashMap<std::unique_ptr<int>, int> map;

    auto uniquePtr = makeUniqueWithoutFastMallocCheck<int>(5);
    int* ptr = uniquePtr.get();
    map.add(WTF::move(uniquePtr), 2);

    auto it = map.find(ptr);
    ASSERT_TRUE(it != map.end());
    EXPECT_EQ(ptr, it->key.get());
    EXPECT_EQ(2, it->value);
}

TEST(WTF_HashMap, UniquePtrKey_ContainsUsingRawPointer)
{
    HashMap<std::unique_ptr<int>, int> map;

    auto uniquePtr = makeUniqueWithoutFastMallocCheck<int>(5);
    int* ptr = uniquePtr.get();
    map.add(WTF::move(uniquePtr), 2);

    EXPECT_EQ(true, map.contains(ptr));
}

TEST(WTF_HashMap, UniquePtrKey_GetUsingRawPointer)
{
    HashMap<std::unique_ptr<int>, int> map;

    auto uniquePtr = makeUniqueWithoutFastMallocCheck<int>(5);
    int* ptr = uniquePtr.get();
    map.add(WTF::move(uniquePtr), 2);

    int value = map.get(ptr);
    EXPECT_EQ(2, value);
}

TEST(WTF_HashMap, UniquePtrKey_RemoveUsingRawPointer)
{
    ConstructorDestructorCounter::TestingScope scope;

    HashMap<std::unique_ptr<ConstructorDestructorCounter>, int> map;

    auto uniquePtr = makeUnique<ConstructorDestructorCounter>();
    ConstructorDestructorCounter* ptr = uniquePtr.get();
    map.add(WTF::move(uniquePtr), 2);

    EXPECT_EQ(1u, ConstructorDestructorCounter::constructionCount);
    EXPECT_EQ(0u, ConstructorDestructorCounter::destructionCount);

    bool result = map.remove(ptr);
    EXPECT_EQ(true, result);

    EXPECT_EQ(1u, ConstructorDestructorCounter::constructionCount);
    EXPECT_EQ(1u, ConstructorDestructorCounter::destructionCount);
}

TEST(WTF_HashMap, UniquePtrKey_TakeUsingRawPointer)
{
    ConstructorDestructorCounter::TestingScope scope;

    HashMap<std::unique_ptr<ConstructorDestructorCounter>, int> map;

    auto uniquePtr = makeUnique<ConstructorDestructorCounter>();
    ConstructorDestructorCounter* ptr = uniquePtr.get();
    map.add(WTF::move(uniquePtr), 2);

    EXPECT_EQ(1u, ConstructorDestructorCounter::constructionCount);
    EXPECT_EQ(0u, ConstructorDestructorCounter::destructionCount);

    int result = map.take(ptr);
    EXPECT_EQ(2, result);

    EXPECT_EQ(1u, ConstructorDestructorCounter::constructionCount);
    EXPECT_EQ(1u, ConstructorDestructorCounter::destructionCount);
}

TEST(WTF_HashMap, UniqueRefValue)
{
    HashMap<int, UniqueRef<int>> map;
    UniqueRef<int> five = makeUniqueRefWithoutFastMallocCheck<int>(5);
    map.add(5, WTF::move(five));
    EXPECT_TRUE(map.contains(5));
    int* shouldBeFive = map.get(5);
    EXPECT_EQ(*shouldBeFive, 5);
    std::unique_ptr<int> takenFive = map.take(5);
    EXPECT_EQ(*takenFive, 5);
    map.ensure(6, [] {
        return makeUniqueRefWithoutFastMallocCheck<int>(6);
    });
    EXPECT_FALSE(map.contains(5));
    EXPECT_TRUE(map.contains(6));
    for (UniqueRef<int>& a : map.values())
        EXPECT_EQ(a.get(), 6);
}

TEST(WTF_HashMap, RefPtrKey_Add)
{
    {
        DerivedRefLogger a("a");

        HashMap<RefPtr<RefLogger>, int> map;

        RefPtr<RefLogger> ptr(&a);
        map.add(ptr, 0);
    }

    ASSERT_STREQ("ref(a) ref(a) deref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_AddUsingRelease)
{
    {
        DerivedRefLogger a("a");

        HashMap<RefPtr<RefLogger>, int> map;

        RefPtr<RefLogger> ptr(&a);
        map.add(WTF::move(ptr), 0);
    }

    EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_AddUsingMove)
{
    {
        DerivedRefLogger a("a");

        HashMap<RefPtr<RefLogger>, int> map;

        RefPtr<RefLogger> ptr(&a);
        map.add(WTF::move(ptr), 0);
    }

    EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_AddUsingRaw)
{
    {
        DerivedRefLogger a("a");

        HashMap<RefPtr<RefLogger>, int> map;

        RefPtr<RefLogger> ptr(&a);
        map.add(ptr.get(), 0);
    }

    EXPECT_STREQ("ref(a) ref(a) deref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_AddKeyAlreadyPresent)
{
    DerivedRefLogger a("a");

    HashMap<RefPtr<RefLogger>, int> map;

    {
        RefPtr<RefLogger> ptr(&a);
        map.add(ptr, 0);
    }

    EXPECT_STREQ("ref(a) ref(a) deref(a) ", takeLogStr().c_str());

    {
        RefPtr<RefLogger> ptr2(&a);
        auto addResult = map.add(ptr2, 0);
        EXPECT_FALSE(addResult.isNewEntry);
    }

    EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    map.clear();

    EXPECT_STREQ("deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_AddUsingReleaseKeyAlreadyPresent)
{
    DerivedRefLogger a("a");

    HashMap<RefPtr<RefLogger>, int> map;

    {
        RefPtr<RefLogger> ptr(&a);
        map.add(ptr, 0);
    }

    EXPECT_STREQ("ref(a) ref(a) deref(a) ", takeLogStr().c_str());

    {
        RefPtr<RefLogger> ptr2(&a);
        auto addResult = map.add(WTF::move(ptr2), 0);
        EXPECT_FALSE(addResult.isNewEntry);
    }

    EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    map.clear();

    EXPECT_STREQ("deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_AddUsingMoveKeyAlreadyPresent)
{
    DerivedRefLogger a("a");

    HashMap<RefPtr<RefLogger>, int> map;

    {
        RefPtr<RefLogger> ptr(&a);
        map.add(ptr, 0);
    }

    EXPECT_STREQ("ref(a) ref(a) deref(a) ", takeLogStr().c_str());

    {
        RefPtr<RefLogger> ptr2(&a);
        auto addResult = map.add(WTF::move(ptr2), 0);
        EXPECT_FALSE(addResult.isNewEntry);
    }

    EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    map.clear();

    EXPECT_STREQ("deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_Set)
{
    {
        DerivedRefLogger a("a");

        HashMap<RefPtr<RefLogger>, int> map;

        RefPtr<RefLogger> ptr(&a);
        map.set(ptr, 0);
    }

    ASSERT_STREQ("ref(a) ref(a) deref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_SetUsingRelease)
{
    {
        DerivedRefLogger a("a");

        HashMap<RefPtr<RefLogger>, int> map;

        RefPtr<RefLogger> ptr(&a);
        map.set(WTF::move(ptr), 0);
    }

    EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());
}


TEST(WTF_HashMap, RefPtrKey_SetUsingMove)
{
    {
        DerivedRefLogger a("a");

        HashMap<RefPtr<RefLogger>, int> map;

        RefPtr<RefLogger> ptr(&a);
        map.set(WTF::move(ptr), 0);
    }

    EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_SetUsingRaw)
{
    {
        DerivedRefLogger a("a");

        HashMap<RefPtr<RefLogger>, int> map;

        RefPtr<RefLogger> ptr(&a);
        map.set(ptr.get(), 0);
    }

    EXPECT_STREQ("ref(a) ref(a) deref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_SetKeyAlreadyPresent)
{
    {
        DerivedRefLogger a("a");

        HashMap<RefPtr<RefLogger>, int> map;

        RefPtr<RefLogger> ptr(&a);
        map.set(ptr, 0);

        EXPECT_STREQ("ref(a) ref(a) ", takeLogStr().c_str());

        {
            RefPtr<RefLogger> ptr2(&a);
            auto addResult = map.set(ptr2, 1);
            EXPECT_FALSE(addResult.isNewEntry);
            EXPECT_EQ(1, map.get(ptr.get()));
        }

        EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());
    }

    EXPECT_STREQ("deref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_SetUsingReleaseKeyAlreadyPresent)
{
    {
        DerivedRefLogger a("a");

        HashMap<RefPtr<RefLogger>, int> map;

        RefPtr<RefLogger> ptr(&a);
        map.set(ptr, 0);

        EXPECT_STREQ("ref(a) ref(a) ", takeLogStr().c_str());

        {
            RefPtr<RefLogger> ptr2(&a);
            auto addResult = map.set(WTF::move(ptr2), 1);
            EXPECT_FALSE(addResult.isNewEntry);
            EXPECT_EQ(1, map.get(ptr.get()));
        }

        EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());
    }

    EXPECT_STREQ("deref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, RefPtrKey_SetUsingMoveKeyAlreadyPresent)
{
    {
        DerivedRefLogger a("a");

        HashMap<RefPtr<RefLogger>, int> map;

        RefPtr<RefLogger> ptr(&a);
        map.set(ptr, 0);

        EXPECT_STREQ("ref(a) ref(a) ", takeLogStr().c_str());

        {
            RefPtr<RefLogger> ptr2(&a);
            auto addResult = map.set(WTF::move(ptr2), 1);
            EXPECT_FALSE(addResult.isNewEntry);
            EXPECT_EQ(1, map.get(ptr.get()));
        }

        EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());
    }

    EXPECT_STREQ("deref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, Ensure)
{
    HashMap<unsigned, unsigned> map;
    {
        auto addResult = map.ensure(1, [] { return 1; });
        EXPECT_EQ(1u, addResult.iterator->value);
        EXPECT_EQ(1u, addResult.iterator->key);
        EXPECT_TRUE(addResult.isNewEntry);
        auto addResult2 = map.ensure(1, [] { return 2; });
        EXPECT_EQ(1u, addResult2.iterator->value);
        EXPECT_EQ(1u, addResult2.iterator->key);
        EXPECT_FALSE(addResult2.isNewEntry);
    }
}

TEST(WTF_HashMap, Ensure_MoveOnlyValues)
{
    HashMap<unsigned, MoveOnly> moveOnlyValues;
    {
        auto addResult = moveOnlyValues.ensure(1, [] { return MoveOnly(1); });
        EXPECT_EQ(1u, addResult.iterator->value.value());
        EXPECT_EQ(1u, addResult.iterator->key);
        EXPECT_TRUE(addResult.isNewEntry);
        auto addResult2 = moveOnlyValues.ensure(1, [] { return MoveOnly(2); });
        EXPECT_EQ(1u, addResult2.iterator->value.value());
        EXPECT_EQ(1u, addResult2.iterator->key);
        EXPECT_FALSE(addResult2.isNewEntry);
    }
}

TEST(WTF_HashMap, Ensure_UniquePointer)
{
    HashMap<unsigned, std::unique_ptr<unsigned>> map;
    {
        auto addResult = map.ensure(1, [] { return makeUniqueWithoutFastMallocCheck<unsigned>(1); });
        EXPECT_EQ(1u, *map.get(1));
        EXPECT_EQ(1u, *addResult.iterator->value.get());
        EXPECT_EQ(1u, addResult.iterator->key);
        EXPECT_TRUE(addResult.isNewEntry);
        auto addResult2 = map.ensure(1, [] { return makeUniqueWithoutFastMallocCheck<unsigned>(2); });
        EXPECT_EQ(1u, *map.get(1));
        EXPECT_EQ(1u, *addResult2.iterator->value.get());
        EXPECT_EQ(1u, addResult2.iterator->key);
        EXPECT_FALSE(addResult2.isNewEntry);
    }
}

TEST(WTF_HashMap, Ensure_RefPtr)
{
    DerivedRefLogger a("a");

    HashMap<unsigned, RefPtr<RefLogger>> map;

    map.ensure(1, [&] { return RefPtr<RefLogger>(&a); });
    EXPECT_STREQ("ref(a) ", takeLogStr().c_str());

    map.ensure(1, [&] { return RefPtr<RefLogger>(&a); });
    EXPECT_STREQ("", takeLogStr().c_str());

    map.clear();

    EXPECT_STREQ("deref(a) ", takeLogStr().c_str());
}

class ObjectWithRefLogger {
    WTF_DEPRECATED_MAKE_FAST_ALLOCATED(ObjectWithRefLogger);
public:
    ObjectWithRefLogger(Ref<RefLogger>&& logger)
        : m_logger(WTF::move(logger))
    {
    }

    Ref<RefLogger> m_logger;
};


static void testMovingUsingEnsure(Ref<RefLogger>&& logger)
{
    HashMap<unsigned, std::unique_ptr<ObjectWithRefLogger>> map;
    
    map.ensure(1, [&] { return makeUnique<ObjectWithRefLogger>(WTF::move(logger)); });
}

static void testMovingUsingAdd(Ref<RefLogger>&& logger)
{
    HashMap<unsigned, std::unique_ptr<ObjectWithRefLogger>> map;

    auto& slot = map.add(1, nullptr).iterator->value;
    slot = makeUnique<ObjectWithRefLogger>(WTF::move(logger));
}

TEST(WTF_HashMap, Ensure_LambdasCapturingByReference)
{
    {
        DerivedRefLogger a("a");
        Ref<RefLogger> ref(a);
        testMovingUsingEnsure(WTF::move(ref));

        EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());
    }

    {
        DerivedRefLogger a("a");
        Ref<RefLogger> ref(a);
        testMovingUsingAdd(WTF::move(ref));

        EXPECT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());
    }
}


TEST(WTF_HashMap, ValueIsDestructedOnRemove)
{
    struct DestructorObserver {
        DestructorObserver() = default;

        DestructorObserver(bool* destructed)
            : destructed(destructed)
        {
        }

        ~DestructorObserver()
        {
            if (destructed)
                *destructed = true;
        }

        DestructorObserver(DestructorObserver&& other)
            : destructed(other.destructed)
        {
            other.destructed = nullptr;
        }

        DestructorObserver& operator=(DestructorObserver&& other)
        {
            destructed = other.destructed;
            other.destructed = nullptr;
            return *this;
        }

        bool* destructed { nullptr };
    };

    HashMap<int, DestructorObserver> map;

    bool destructed = false;
    map.add(5, DestructorObserver { &destructed });

    EXPECT_FALSE(destructed);

    bool removeResult = map.remove(5);

    EXPECT_TRUE(removeResult);
    EXPECT_TRUE(destructed);
}

struct DerefObserver {
    WTF_DEPRECATED_MAKE_STRUCT_FAST_ALLOCATED(DerefObserver);
    NEVER_INLINE void ref()
    {
        ++count;
    }
    NEVER_INLINE void deref()
    {
        --count;
        observedBucket = bucketAddress->get();
    }
    unsigned count { 1 };
    const RefPtr<DerefObserver>* bucketAddress { nullptr };
    const DerefObserver* observedBucket { nullptr };
};

TEST(WTF_HashMap, RefPtrNotZeroedBeforeDeref)
{
    auto observer = makeUniqueWithoutRefCountedCheck<DerefObserver>();

    HashMap<RefPtr<DerefObserver>, int> map;
    map.add(adoptRef(observer.get()), 5);

    auto iterator = map.find(observer.get());
    EXPECT_TRUE(iterator != map.end());

    observer->bucketAddress = &iterator->key;

    EXPECT_TRUE(observer->observedBucket == nullptr);
    EXPECT_TRUE(map.remove(observer.get()));

    // It if fine to either leave the old value intact at deletion or already set it to the deleted
    // value.
    // A zero would be a incorrect outcome as it would mean we nulled the bucket before an opaque
    // call.
    EXPECT_TRUE(observer->observedBucket == observer.get() || observer->observedBucket == RefPtr<DerefObserver>::PtrTraits::hashTableDeletedValue());
    EXPECT_EQ(observer->count, 0u);
}

TEST(WTF_HashMap, Ref_Key)
{
    {
        RefLogger a("a");

        HashMap<Ref<RefLogger>, int> map;

        Ref<RefLogger> ref(a);
        map.add(WTF::move(ref), 1);
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        RefLogger a("a");

        HashMap<Ref<RefLogger>, int> map;

        Ref<RefLogger> ref(a);
        map.set(WTF::move(ref), 1);
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        RefLogger a("a");

        HashMap<Ref<RefLogger>, int> map;

        Ref<RefLogger> refA(a);
        map.add(WTF::move(refA), 1);

        Ref<RefLogger> refA2(a);
        map.set(WTF::move(refA2), 1);
    }

    ASSERT_STREQ("ref(a) ref(a) deref(a) deref(a) ", takeLogStr().c_str());

    {
        RefLogger a("a");

        HashMap<Ref<RefLogger>, int> map;

        Ref<RefLogger> ref(a);
        map.ensure(WTF::move(ref), []() { 
            return 1; 
        });
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        RefLogger a("a");

        HashMap<Ref<RefLogger>, int> map;

        Ref<RefLogger> ref(a);
        map.add(WTF::move(ref), 1);
        
        auto it = map.find(&a);
        ASSERT_TRUE(it != map.end());
        
        ASSERT_EQ(it->key.ptr(), &a);
        ASSERT_EQ(it->value, 1);
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        RefLogger a("a");

        HashMap<Ref<RefLogger>, int> map;

        Ref<RefLogger> ref(a);
        map.add(WTF::move(ref), 1);

        map.remove(&a);
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        RefLogger a("a");

        HashMap<Ref<RefLogger>, int> map;

        Ref<RefLogger> ref(a);
        map.add(WTF::move(ref), 1);

        int i = map.take(&a);
        ASSERT_EQ(i, 1);
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        HashMap<Ref<RefLogger>, int> map;
        for (int i = 0; i < 64; ++i) {
            // FIXME: All of these RefLogger objects leak. No big deal for a test I guess.
            Ref<RefLogger> ref = adoptRef(*new RefLogger("a"));
            auto* pointer = ref.ptr();
            map.add(WTF::move(ref), i + 1);
            ASSERT_TRUE(map.contains(pointer));
        }
    }

    ASSERT_STREQ("deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, Ref_Value)
{
    {
        RefLogger a("a");

        HashMap<int, Ref<RefLogger>> map;

        Ref<RefLogger> ref(a);
        map.add(1, WTF::move(ref));
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        RefLogger a("a");

        HashMap<int, Ref<RefLogger>> map;

        Ref<RefLogger> ref(a);
        map.set(1, WTF::move(ref));
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        RefLogger a("a");
        RefLogger b("b");

        HashMap<int, Ref<RefLogger>> map;

        Ref<RefLogger> refA(a);
        map.add(1, WTF::move(refA));

        Ref<RefLogger> refB(b);
        map.set(1, WTF::move(refB));
    }

    ASSERT_STREQ("ref(a) ref(b) deref(a) deref(b) ", takeLogStr().c_str());

    {
        RefLogger a("a");

        HashMap<int, Ref<RefLogger>> map;

        Ref<RefLogger> ref(a);
        map.add(1, WTF::move(ref));
        
        auto aGet = map.get(1);
        ASSERT_EQ(aGet, &a);
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        HashMap<int, Ref<RefLogger>> map;
        
        auto emptyGet = map.get(1);
        ASSERT_TRUE(emptyGet == nullptr);
    }

    {
        RefLogger a("a");

        HashMap<int, Ref<RefLogger>> map;

        Ref<RefLogger> ref(a);
        map.add(1, WTF::move(ref));
        
        auto aOut = map.take(1);
        ASSERT_TRUE(static_cast<bool>(aOut));
        ASSERT_EQ(&a, aOut.get());
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        HashMap<int, Ref<RefLogger>> map;
        
        auto emptyTake = map.take(1);
        ASSERT_FALSE(static_cast<bool>(emptyTake));
    }

    {
        RefLogger a("a");

        HashMap<int, Ref<RefLogger>> map;

        Ref<RefLogger> ref(a);
        map.add(1, WTF::move(ref));
        map.remove(1);
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        RefLogger a("a");

        HashMap<int, Ref<RefLogger>> map;

        map.ensure(1, [&] {
            Ref<RefLogger> ref(a);
            return ref; 
        });
    }

    ASSERT_STREQ("ref(a) deref(a) ", takeLogStr().c_str());

    {
        HashMap<int, Ref<RefLogger>> map;
        for (int i = 0; i < 64; ++i) {
            // FIXME: All of these RefLogger objects leak. No big deal for a test I guess.
            Ref<RefLogger> ref = adoptRef(*new RefLogger("a"));
            map.add(i + 1, WTF::move(ref));
            ASSERT_TRUE(map.contains(i + 1));
        }
    }

    ASSERT_STREQ("deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) deref(a) ", takeLogStr().c_str());
}

TEST(WTF_HashMap, DeletedAddressOfOperator)
{
    HashMap<int, DeletedAddressOfOperator> map1;
    for (auto& value : map1.values())
        (void)value;
}

TEST(WTF_HashMap, RefMappedToNonZeroEmptyValue)
{
    class Value {
    public:
        Value() = default;
        Value(Value&&) = default;
        Value(const Value&) = default;
        Value& operator=(Value&&) = default;

        Value(int32_t f)
            : m_field(f)
        { }

        int32_t field() { return m_field; }

    private:
        int32_t m_field { 0xbadbeef };
    };

    class Key : public RefCounted<Key> {
        Key() = default;
    public:
        static Ref<Key> create() { return adoptRef(*new Key); }
    };

    static_assert(!WTF::HashTraits<Value>::emptyValueIsZero);

    HashMap<Ref<Key>, Value> map;
    Vector<std::pair<Ref<Key>, int32_t>> vectorMap;

    for (int32_t i = 0; i < 160; ++i) {
        Ref<Key> key = Key::create();
        map.add(Ref<Key>(key.get()), Value { i });
        vectorMap.append({ WTF::move(key), i });
    }

    for (auto& pair : vectorMap)
        ASSERT_EQ(pair.second, map.get(pair.first).field());

    for (auto& pair : vectorMap)
        ASSERT_TRUE(map.remove(pair.first));
}

TEST(WTF_HashMap, Random_Empty)
{
    HashMap<unsigned, unsigned> map;

    auto result = map.random();
    ASSERT_EQ(result, map.end());
}

TEST(WTF_HashMap, Random_WrapAround)
{
    HashMap<unsigned, unsigned, ZeroHash<unsigned>, BigTableHashTraits<unsigned>> map;
    map.add(1, 1);

    auto result = map.random();
    ASSERT_EQ(result, map.begin());
}

TEST(WTF_HashMap, Random_IsEvenlyDistributed)
{
    HashMap<unsigned, unsigned, DefaultHash<unsigned>, WTF::UnsignedWithZeroKeyHashTraits<unsigned>> map;
    map.add(0, 0);
    map.add(1, 1);

    unsigned zeros = 0;
    unsigned ones = 0;

    for (unsigned i = 0; i < 1000; ++i) {
        auto it = map.random();
        if (!it->value)
            ++zeros;
        else {
            ASSERT_EQ(it->value, 1u);
            ++ones;
        }
    }

    ASSERT_EQ(zeros + ones, 1000u);
    ASSERT_LE(zeros, 600u);
    ASSERT_LE(ones, 600u);
}

TEST(WTF_HashMap, ReserveInitialCapacity)
{
    HashMap<String, String> map;
    EXPECT_EQ(0u, map.size());
    EXPECT_EQ(0u, map.capacity());

    map.reserveInitialCapacity(9999);
    EXPECT_EQ(0u, map.size());
    EXPECT_EQ(32768u, map.capacity());

    for (int i = 0; i < 9999; ++i)
        map.add(makeString("foo"_s, i), makeString("bar"_s, i));
    EXPECT_EQ(9999u, map.size());
    EXPECT_EQ(32768u, map.capacity());
    EXPECT_TRUE(map.contains("foo3"_str));
    EXPECT_STREQ("bar3", map.get("foo3"_str).utf8().data());

    for (int i = 0; i < 9999; ++i)
        map.add(makeString("excess"_s, i), makeString("baz"_s, i));
    EXPECT_EQ(9999u + 9999u, map.size());
    EXPECT_EQ(32768u + 32768u, map.capacity());

    for (int i = 0; i < 9999; ++i)
        EXPECT_TRUE(map.remove(makeString("foo"_s, i)));
    EXPECT_EQ(9999u, map.size());
    EXPECT_EQ(32768u, map.capacity());
    EXPECT_STREQ("baz3", map.get("excess3"_str).utf8().data());

    for (int i = 0; i < 9999; ++i)
        EXPECT_TRUE(map.remove(makeString("excess"_s, i)));
    EXPECT_EQ(0u, map.size());
    EXPECT_EQ(8u, map.capacity());

    HashMap<String, String> map2;
    map2.reserveInitialCapacity(9999);
    EXPECT_FALSE(map2.remove("foo1"_s));

    for (int i = 0; i < 2000; ++i)
        map2.add(makeString("foo"_s, i), makeString("bar"_s, i));
    EXPECT_EQ(2000u, map2.size());
    EXPECT_EQ(32768u, map2.capacity());

    for (int i = 0; i < 2000; ++i)
        EXPECT_TRUE(map2.remove(makeString("foo"_s, i)));
    EXPECT_EQ(0u, map2.size());
    EXPECT_EQ(8u, map2.capacity());
}

TEST(WTF_HashMap, Random_IsEvenlyDistributedAfterRemove)
{
    for (size_t tableSize = 2; tableSize <= 2 * 6; ++tableSize) { // Our hash tables shrink at a load factor of 1 / 6.
        HashMap<unsigned, unsigned, DefaultHash<unsigned>, WTF::UnsignedWithZeroKeyHashTraits<unsigned>> map;
        for (size_t i = 0; i < tableSize; ++i)
            map.add(i, i);
        for (size_t i = 2; i < tableSize; ++i)
            map.remove(i);

        unsigned zeros = 0;
        unsigned ones = 0;

        for (unsigned i = 0; i < 1000; ++i) {
            auto it = map.random();
            if (!it->value)
                ++zeros;
            else {
                ASSERT_EQ(it->value, 1u);
                ++ones;
            }
        }

        ASSERT_EQ(zeros + ones, 1000u);
        ASSERT_LE(zeros, 600u);
        ASSERT_LE(ones, 600u);
    }
}

class TestObjectWithCustomDestructor {
    WTF_DEPRECATED_MAKE_FAST_ALLOCATED(TestObjectWithCustomDestructor);
public:
    TestObjectWithCustomDestructor(Function<void()>&& runInDestructor)
        : m_runInDestructor(WTF::move(runInDestructor))
    { }

    ~TestObjectWithCustomDestructor()
    {
        m_runInDestructor();
    }

private:
    Function<void()> m_runInDestructor;
};

TEST(WTF_HashMap, Clear_Reenter)
{
    HashMap<uint64_t, std::unique_ptr<TestObjectWithCustomDestructor>> map;
    for (unsigned i = 1; i <= 10; ++i) {
        map.add(i, makeUnique<TestObjectWithCustomDestructor>([&map] {
            map.clear();
            EXPECT_EQ(0U, map.size());
            EXPECT_TRUE(map.isEmpty());
        }));
    }
    EXPECT_EQ(10U, map.size());
    map.clear();
    EXPECT_EQ(0U, map.size());
    EXPECT_TRUE(map.isEmpty());
}

TEST(WTF_HashMap, Set_Reenter)
{
    HashMap<uint64_t, Variant<std::unique_ptr<TestObjectWithCustomDestructor>, int>> map;
    map.add(1, makeUnique<TestObjectWithCustomDestructor>([&map] {
        auto it = map.find(1);
        EXPECT_TRUE(std::holds_alternative<std::unique_ptr<TestObjectWithCustomDestructor>>(it->value));
    }));
    map.set(1, 1);
}

TEST(WTF_HashMap, Take_Set_Reenter)
{
    HashMap<uint64_t, Variant<std::unique_ptr<TestObjectWithCustomDestructor>, int>> map;
    map.add(1, makeUnique<TestObjectWithCustomDestructor>([&map] {
        auto it = map.find(1);
        EXPECT_FALSE(std::holds_alternative<std::unique_ptr<TestObjectWithCustomDestructor>>(it->value));
    }));
    auto value = map.take(1);
    map.set(1, 1);
}

TEST(WTF_HashMap, Ensure_Translator)
{
    HashMap<String, unsigned> map;
    auto addResult = map.ensure<StringViewHashTranslator>(StringView { "foo"_s }, [] { return 1u; });
    EXPECT_TRUE(addResult.isNewEntry);
    EXPECT_TRUE(map.contains<StringViewHashTranslator>(StringView { "foo"_s }));
    EXPECT_EQ(map.size(), 1u);
    unsigned existingValue = map.get<StringViewHashTranslator>(StringView { "foo"_s });
    EXPECT_EQ(existingValue, 1u);
    existingValue = map.get<StringViewHashTranslator>("foo"_str);
    EXPECT_EQ(existingValue, 1u);
    addResult = map.ensure<StringViewHashTranslator>(StringView { "foo"_s }, [] {
        EXPECT_TRUE(false);
        return 2u;
    });
    EXPECT_FALSE(addResult.isNewEntry);
    EXPECT_EQ(map.size(), 1u);
    existingValue = map.get<StringViewHashTranslator>("foo"_str);
    EXPECT_EQ(existingValue, 1u);
    bool didRemove = map.remove<StringViewHashTranslator>(StringView { "foo"_s });
    EXPECT_TRUE(didRemove);
    EXPECT_EQ(map.size(), 0u);
}

TEST(WTF_HashMap, GetOptional)
{
    {
        struct Value {
            int a;
            int b;
        };

        HashMap<unsigned, Value> map;
        map.add(2, Value { 1, 2 });
        map.add(1000, Value { 3, 4 });

        auto optionalValue = map.getOptional(1);
        EXPECT_FALSE(optionalValue.has_value());

        optionalValue = map.getOptional(2);
        EXPECT_TRUE(optionalValue.has_value());
        EXPECT_EQ(1, optionalValue->a);
        EXPECT_EQ(2, optionalValue->b);

        optionalValue = map.getOptional(1000);
        EXPECT_TRUE(optionalValue.has_value());
        EXPECT_EQ(3, optionalValue->a);
        EXPECT_EQ(4, optionalValue->b);

        optionalValue = map.getOptional(10000);
        EXPECT_FALSE(optionalValue.has_value());
    }

    {
        struct CountedValue : public RefCounted<CountedValue> {
            CountedValue() = default;
            int a { 123 };
        };

        HashMap<unsigned, Ref<CountedValue>> map;
        map.add(2, adoptRef(*new CountedValue { }));

        auto optionalValue = map.getOptional(1);
        EXPECT_FALSE(optionalValue.has_value());

        optionalValue = map.getOptional(2);
        EXPECT_TRUE(optionalValue.has_value());
        EXPECT_EQ(123, optionalValue.value().get().a);
    }

}

TEST(WTF_HashMap, KeysValuesRangesAllAnyNoneOf)
{
    IntHashMap map;
    map.add(1, 1);
    map.add(2, 2);
    map.add(3, 3);

    EXPECT_TRUE(std::ranges::all_of(map.keys(), [] (int el) {
        return el < 4;
    }));
    EXPECT_TRUE(std::ranges::none_of(map.keys(), [] (int el) {
        return el > 4;
    }));
    EXPECT_TRUE(std::ranges::any_of(map.keys(), [] (int el) {
        return el < 2;
    }));
    EXPECT_TRUE(std::ranges::all_of(map.values(), [] (int el) {
        return el < 4;
    }));
    EXPECT_TRUE(std::ranges::none_of(map.values(), [] (int el) {
        return el > 4;
    }));
    EXPECT_TRUE(std::ranges::any_of(map.values(), [] (int el) {
        return el < 2;
    }));
}

TEST(WTF_HashMap, fromRangeConstructorBasicTypes)
{
    Vector<KeyValuePair<int, String>> pairs {
        { 1, "one"_s },
        { 2, "two"_s },
        { 3, "three"_s }
    };
    HashMap<int, String> wtfMap = pairs | rangeTo<HashMap<int, String>>();

    EXPECT_EQ(3U, wtfMap.size());
    EXPECT_EQ("one"_s, wtfMap.get(1));
    EXPECT_EQ("two"_s, wtfMap.get(2));
    EXPECT_EQ("three"_s, wtfMap.get(3));
}

TEST(WTF_HashMap, fromRangeConstructorInitializerList)
{
    auto initList = {
        KeyValuePair { 10, 100 },
        KeyValuePair(20, 200),
        KeyValuePair(30, 300)
    };
    HashMap<int, int> wtfMap(fromRange, initList);

    EXPECT_EQ(3U, wtfMap.size());
    EXPECT_EQ(100, wtfMap.get(10));
    EXPECT_EQ(200, wtfMap.get(20));
    EXPECT_EQ(300, wtfMap.get(30));
}

TEST(WTF_HashMap, fromRangeConstructorEmptyRange)
{
    Vector<KeyValuePair<int, int>> emptyVec;
    HashMap<int, int> wtfMap(fromRange, emptyVec);

    EXPECT_TRUE(wtfMap.isEmpty());
    EXPECT_EQ(0U, wtfMap.size());
}

TEST(WTF_HashMap, fromRangeConstructorMoveOnlyValues)
{
    Vector<KeyValuePair<int, MoveOnly>> stdVec;
    stdVec.append({ 1, MoveOnly { 42 } });
    stdVec.append({ 2, MoveOnly { 99 } });

    HashMap<int, MoveOnly> wtfMap(fromRange, WTF::move(stdVec));

    EXPECT_EQ(2U, wtfMap.size());

    auto it1 = wtfMap.find(1);
    auto it2 = wtfMap.find(2);

    ASSERT_NE(wtfMap.end(), it1);
    ASSERT_NE(wtfMap.end(), it2);

    EXPECT_EQ(42U, it1->value.value());
    EXPECT_EQ(99U, it2->value.value());
}

TEST(WTF_HashMap, fromRangeConstructorStringKeys)
{
    Vector<KeyValuePair<String, double>> stdVec {
        { "pi"_s, 3.14159 },
        { "e"_s, 2.71828 },
        { "sqrt2"_s, 1.41421 }
    };
    HashMap<String, double> wtfMap(fromRange, stdVec);

    EXPECT_EQ(3U, wtfMap.size());
    EXPECT_DOUBLE_EQ(3.14159, wtfMap.get("pi"_s));
    EXPECT_DOUBLE_EQ(2.71828, wtfMap.get("e"_s));
    EXPECT_DOUBLE_EQ(1.41421, wtfMap.get("sqrt2"_s));
}

TEST(WTF_HashMap, fromRangeConstructorCustomHashTraits)
{
    // Test with custom hash map configuration
    using CustomHashMap = HashMap<double, int64_t, DefaultHash<double>, TestDoubleHashTraits>;

    Vector<KeyValuePair<double, int64_t>> stdVec {
        { 1.1, 11 },
        { 2.2, 22 },
        { 3.3, 33 }
    };
    CustomHashMap wtfMap(fromRange, stdVec);

    EXPECT_EQ(3U, wtfMap.size());
    EXPECT_EQ(11, wtfMap.get(1.1));
    EXPECT_EQ(22, wtfMap.get(2.2));
    EXPECT_EQ(33, wtfMap.get(3.3));
}

TEST(WTF_HashMap, RangeToBasicUsage)
{
    // Test the rangeTo range adaptor with HashMap
    Vector<KeyValuePair<int, String>> stdVec {
        { 1, "one"_s },
        { 2, "two"_s },
        { 3, "three"_s }
    };
    auto wtfMap = stdVec | rangeTo<HashMap<int, String>>();

    EXPECT_EQ(3U, wtfMap.size());
    EXPECT_EQ("one"_s, wtfMap.get(1));
    EXPECT_EQ("two"_s, wtfMap.get(2));
    EXPECT_EQ("three"_s, wtfMap.get(3));
}

TEST(WTF_HashMap, RangeToChainedOperations)
{
    Vector<KeyValuePair<int, int>> stdVec {
        { 1, 10 },
        { 2, 20 },
        { 3, 30 },
        { 4, 40 }
    };

    auto result = stdVec
        | std::views::filter([](const auto& pair) { return !(pair.key % 2); })
        | std::views::transform([](const auto& pair) -> KeyValuePair<int, int> { return { pair.key, pair.value * 2 }; })
        | rangeTo<HashMap<int, int>>();

    EXPECT_EQ(2U, result.size());
    EXPECT_EQ(40, result.get(2)); // 20 * 2
    EXPECT_EQ(80, result.get(4)); // 40 * 2
}

class Object : public WTF::RefCountedAndCanMakeWeakPtr<Object> {
public:
    static Ref<Object> create() { return adoptRef(*new Object); }

private:
    Object() = default;
};

TEST(WTF_HashMap, WeakPtr)
{
    HashMap<WeakPtr<Object>, int> map;

    RefPtr object1 = Object::create();
    map.add(object1.get(), 1);

    Ref object2 = Object::create();

    // Present when live
    EXPECT_TRUE(map.contains(object1.get()));
    EXPECT_EQ(map.find(object1.get())->value, 1);
    EXPECT_EQ(1u, map.size());
    for (auto& entry : map) {
        EXPECT_EQ(entry.key, object1.get());
        EXPECT_EQ(entry.value, 1);
    }

    EXPECT_FALSE(map.contains(&object2.get()));
    EXPECT_EQ(map.find(&object2.get()), map.end());

    Object* rawObject1 = object1.get();
    object1 = nullptr;

    // Absent when dead
    EXPECT_EQ(map.get(rawObject1), 0);
    EXPECT_FALSE(map.contains(rawObject1));
    EXPECT_EQ(map.find(rawObject1), map.end());
    EXPECT_EQ(map.begin(), map.end());

    // Accurate size after removing weak nulls
    EXPECT_EQ(1u, map.size());
    map.removeWeakNullEntries();
    EXPECT_EQ(0u, map.size());

    // Bounded growth as added objects die
    for (size_t i = 0; i < 128; ++i)
        map.add(&Object::create().get(), 1);
    EXPECT_LT(map.size(), 16u);
}

TEST(WTF_HashMap, InlineWeakPtr)
{
    HashMap<InlineWeakPtr<InlineWeakPtrObject>, int> map;

    RefPtr object1 = InlineWeakPtrObject::create();
    map.add(object1.get(), 1);

    Ref object2 = InlineWeakPtrObject::create();

    // Present when live
    EXPECT_TRUE(map.contains(object1.get()));
    EXPECT_EQ(map.find(object1.get())->value, 1);
    EXPECT_EQ(1u, map.size());
    for (auto& entry : map) {
        EXPECT_EQ(entry.key, object1.get());
        EXPECT_EQ(entry.value, 1);
    }

    EXPECT_FALSE(map.contains(&object2.get()));
    EXPECT_EQ(map.find(&object2.get()), map.end());

    InlineWeakPtrObject* rawObject1 = object1.get();
    object1 = nullptr;

    // Absent when dead
    EXPECT_EQ(map.get(rawObject1), 0);
    EXPECT_FALSE(map.contains(rawObject1));
    EXPECT_EQ(map.find(rawObject1), map.end());
    EXPECT_EQ(map.begin(), map.end());

    // Accurate size after removing weak nulls
    EXPECT_EQ(1u, map.size());
    map.removeWeakNullEntries();
    EXPECT_EQ(0u, map.size());

    // Bounded growth as added objects die
    for (size_t i = 0; i < 128; ++i)
        map.add(&InlineWeakPtrObject::create().get(), 1);
    EXPECT_LT(map.size(), 16u);
}

} // namespace TestWebKitAPI
