test/hotspot/gtest/utilities/test_concurrentHashtable.cpp
author rehn
Thu, 17 May 2018 10:32:26 +0200
changeset 50158 8e4fcfb4cfe4
child 50445 bd6b78feb6a3
permissions -rw-r--r--
8195098: Low latency hashtable for read-mostly scenarios Summary: This implement a concurrent hashtable using chaining and the GlobalCounter for ABA problems. Reviewed-by: acorn, coleenp, dcubed, eosterlund, gziemski, mlarsson
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
50158
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
     1
/*
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
     2
 * Copyright (c) 2018, Oracle and/or its affiliates. All rights reserved.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
     3
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
     4
 *
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
     5
 * This code is free software; you can redistribute it and/or modify it
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
     6
 * under the terms of the GNU General Public License version 2 only, as
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
     7
 * published by the Free Software Foundation.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
     8
 *
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
     9
 * This code is distributed in the hope that it will be useful, but WITHOUT
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    10
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    11
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    12
 * version 2 for more details (a copy is included in the LICENSE file that
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    13
 * accompanied this code).
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    14
 *
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    15
 * You should have received a copy of the GNU General Public License version
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    16
 * 2 along with this work; if not, write to the Free Software Foundation,
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    17
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    18
 *
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    19
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    20
 * or visit www.oracle.com if you need additional information or have any
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    21
 * questions.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    22
 */
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    23
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    24
#include "precompiled.hpp"
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    25
#include "runtime/mutex.hpp"
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    26
#include "runtime/semaphore.hpp"
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    27
#include "runtime/thread.hpp"
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    28
#include "runtime/vmThread.hpp"
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    29
#include "runtime/vm_operations.hpp"
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    30
#include "utilities/concurrentHashTable.inline.hpp"
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    31
#include "utilities/concurrentHashTableTasks.inline.hpp"
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    32
#include "utilitiesHelper.inline.hpp"
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    33
#include "unittest.hpp"
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    34
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    35
// NOTE: On win32 gtest asserts are not mt-safe.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    36
// Amusingly as long as they do not assert they are mt-safe.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    37
#define SIZE_32 5
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    38
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    39
struct Pointer;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    40
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    41
typedef ConcurrentHashTable<uintptr_t, Pointer, mtInternal> SimpleTestTable;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    42
typedef ConcurrentHashTable<uintptr_t, Pointer, mtInternal>::MultiGetHandle SimpleTestGetHandle;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    43
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    44
// Simplest working CRPT implementation for the hash-table.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    45
struct Pointer : public SimpleTestTable::BaseConfig {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    46
  static uintx get_hash(const uintptr_t& value, bool* dead_hash) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    47
    return (uintx)value;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    48
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    49
  static const uintptr_t& notfound() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    50
    static uintptr_t notfound = 0;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    51
    return notfound;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    52
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    53
  static void* allocate_node(size_t size, const uintptr_t& value) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    54
    return ::malloc(size);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    55
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    56
  static void free_node(void* memory, const uintptr_t& value) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    57
    ::free(memory);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    58
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    59
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    60
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    61
struct SimpleTestLookup {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    62
  uintptr_t _val;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    63
  SimpleTestLookup(uintptr_t val) : _val(val) {}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    64
  uintx get_hash() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    65
    return Pointer::get_hash(_val, NULL);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    66
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    67
  bool equals(const uintptr_t* value, bool* is_dead) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    68
    return _val == *value;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    69
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    70
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    71
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    72
static void cht_insert(Thread* thr) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    73
  uintptr_t val = 0x2;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    74
  SimpleTestLookup stl(val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    75
  SimpleTestTable* cht = new SimpleTestTable();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    76
  EXPECT_TRUE(cht->insert(thr, stl, val)) << "Insert unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    77
  EXPECT_EQ(cht->get_copy(thr, stl), val) << "Getting an existing value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    78
  EXPECT_TRUE(cht->remove(thr, stl)) << "Removing an existing value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    79
  EXPECT_FALSE(cht->remove(thr, stl)) << "Removing an already removed item succeeded.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    80
  EXPECT_NE(cht->get_copy(thr, stl), val) << "Getting a removed value succeeded.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    81
  delete cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    82
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    83
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    84
struct ValVerify {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    85
  uintptr_t _val;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    86
  bool called_get;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    87
  bool called_insert;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    88
  ValVerify(uintptr_t val) : called_get(false), called_insert(false), _val(val) {}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    89
  void operator()(bool inserted, uintptr_t* val) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    90
    EXPECT_EQ(_val, *val) << "The value inserted is not correct.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    91
    if (inserted) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    92
      called_insert = true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    93
    } else {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    94
      called_get = true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    95
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    96
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    97
  void verify(bool get, bool insert) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    98
    EXPECT_EQ(called_get, get) << "Get unexpected";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
    99
    EXPECT_EQ(called_insert, insert) << "Insert unexpected";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   100
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   101
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   102
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   103
static void cht_get_insert_helper(Thread* thr, SimpleTestTable* cht, uintptr_t val) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   104
  {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   105
    SimpleTestLookup stl(val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   106
    ValVerify vv(val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   107
    EXPECT_EQ(cht->get_insert(thr, stl, val, vv), false) << "Inserting an unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   108
    vv.verify(false, true);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   109
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   110
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   111
  {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   112
    SimpleTestLookup stl(val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   113
    ValVerify vv(val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   114
    EXPECT_EQ(cht->get_insert(thr, stl, val, vv), true) << "Getting an old value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   115
    vv.verify(true, false);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   116
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   117
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   118
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   119
static void cht_get_insert(Thread* thr) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   120
  uintptr_t val = 0x2;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   121
  SimpleTestLookup stl(val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   122
  SimpleTestTable* cht = new SimpleTestTable();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   123
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   124
  {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   125
    SCOPED_TRACE("First");
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   126
    cht_get_insert_helper(thr, cht, val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   127
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   128
  EXPECT_EQ(cht->get_copy(thr, stl), val) << "Get an old value failed";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   129
  EXPECT_TRUE(cht->remove(thr, stl)) << "Removing existing value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   130
  EXPECT_NE(cht->get_copy(thr, stl), val) << "Got an already removed item.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   131
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   132
  {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   133
    SCOPED_TRACE("Second");
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   134
    cht_get_insert_helper(thr, cht, val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   135
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   136
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   137
  delete cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   138
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   139
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   140
static bool getinsert_bulkdelete_eval(uintptr_t* val) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   141
  EXPECT_TRUE(*val > 0 && *val < 4) << "Val wrong for this test.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   142
  return (*val & 0x1); // Delete all values ending with first bit set.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   143
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   144
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   145
static void getinsert_bulkdelete_del(uintptr_t* val) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   146
  EXPECT_EQ(*val & 0x1, (uintptr_t)1) << "Deleting wrong value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   147
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   148
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   149
static void cht_getinsert_bulkdelete_insert_verified(Thread* thr, SimpleTestTable* cht, uintptr_t val,
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   150
                                                     bool verify_expect_get, bool verify_expect_inserted) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   151
  ValVerify vv(val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   152
  SimpleTestLookup stl(val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   153
  EXPECT_EQ(cht->get_insert(thr, stl, val, vv), verify_expect_get) << "Inserting an unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   154
  vv.verify(verify_expect_get, verify_expect_inserted);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   155
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   156
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   157
static void cht_getinsert_bulkdelete(Thread* thr) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   158
  uintptr_t val1 = 1;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   159
  uintptr_t val2 = 2;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   160
  uintptr_t val3 = 3;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   161
  SimpleTestLookup stl1(val1), stl2(val2), stl3(val3);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   162
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   163
  SimpleTestTable* cht = new SimpleTestTable();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   164
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val1, false, true);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   165
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val2, false, true);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   166
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val3, false, true);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   167
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   168
  EXPECT_TRUE(cht->remove(thr, stl2)) << "Remove did not find value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   169
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   170
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val1, true, false); // val1 should be present
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   171
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val2, false, true); // val2 should be inserted
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   172
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val3, true, false); // val3 should be present
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   173
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   174
  EXPECT_EQ(cht->get_copy(thr, stl1), val1) << "Get did not find value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   175
  EXPECT_EQ(cht->get_copy(thr, stl2), val2) << "Get did not find value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   176
  EXPECT_EQ(cht->get_copy(thr, stl3), val3) << "Get did not find value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   177
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   178
  // Removes all odd values.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   179
  cht->bulk_delete(thr, getinsert_bulkdelete_eval, getinsert_bulkdelete_del);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   180
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   181
  EXPECT_EQ(cht->get_copy(thr, stl1), (uintptr_t)0) << "Odd value should not exist.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   182
  EXPECT_FALSE(cht->remove(thr, stl1)) << "Odd value should not exist.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   183
  EXPECT_EQ(cht->get_copy(thr, stl2), val2) << "Even value should not have been removed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   184
  EXPECT_EQ(cht->get_copy(thr, stl3), (uintptr_t)0) << "Add value should not exists.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   185
  EXPECT_FALSE(cht->remove(thr, stl3)) << "Odd value should not exists.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   186
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   187
  delete cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   188
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   189
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   190
static void cht_getinsert_bulkdelete_task(Thread* thr) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   191
  uintptr_t val1 = 1;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   192
  uintptr_t val2 = 2;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   193
  uintptr_t val3 = 3;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   194
  SimpleTestLookup stl1(val1), stl2(val2), stl3(val3);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   195
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   196
  SimpleTestTable* cht = new SimpleTestTable();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   197
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val1, false, true);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   198
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val2, false, true);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   199
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val3, false, true);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   200
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   201
  EXPECT_TRUE(cht->remove(thr, stl2)) << "Remove did not find value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   202
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   203
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val1, true, false); // val1 should be present
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   204
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val2, false, true); // val2 should be inserted
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   205
  cht_getinsert_bulkdelete_insert_verified(thr, cht, val3, true, false); // val3 should be present
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   206
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   207
  EXPECT_EQ(cht->get_copy(thr, stl1), val1) << "Get did not find value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   208
  EXPECT_EQ(cht->get_copy(thr, stl2), val2) << "Get did not find value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   209
  EXPECT_EQ(cht->get_copy(thr, stl3), val3) << "Get did not find value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   210
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   211
  // Removes all odd values.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   212
  SimpleTestTable::BulkDeleteTask bdt(cht);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   213
  if (bdt.prepare(thr)) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   214
    while(bdt.doTask(thr, getinsert_bulkdelete_eval, getinsert_bulkdelete_del)) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   215
      bdt.pause(thr);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   216
      EXPECT_TRUE(bdt.cont(thr)) << "Uncontended continue should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   217
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   218
    bdt.done(thr);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   219
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   220
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   221
  EXPECT_EQ(cht->get_copy(thr, stl1), (uintptr_t)0) << "Odd value should not exist.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   222
  EXPECT_FALSE(cht->remove(thr, stl1)) << "Odd value should not exist.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   223
  EXPECT_EQ(cht->get_copy(thr, stl2), val2) << "Even value should not have been removed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   224
  EXPECT_EQ(cht->get_copy(thr, stl3), (uintptr_t)0) << "Add value should not exists.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   225
  EXPECT_FALSE(cht->remove(thr, stl3)) << "Odd value should not exists.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   226
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   227
  delete cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   228
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   229
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   230
static void cht_scope(Thread* thr) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   231
  uintptr_t val = 0x2;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   232
  SimpleTestLookup stl(val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   233
  SimpleTestTable* cht = new SimpleTestTable();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   234
  EXPECT_TRUE(cht->insert(thr, stl, val)) << "Insert unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   235
  {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   236
    SimpleTestGetHandle get_handle(thr, cht);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   237
    EXPECT_EQ(*get_handle.get(stl), val) << "Getting a pre-existing value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   238
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   239
  // We do remove here to make sure the value-handle 'unlocked' the table when leaving the scope.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   240
  EXPECT_TRUE(cht->remove(thr, stl)) << "Removing a pre-existing value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   241
  EXPECT_FALSE(cht->get_copy(thr, stl) == val) << "Got a removed value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   242
  delete cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   243
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   244
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   245
struct ChtScan {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   246
  size_t _count;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   247
  ChtScan() : _count(0) {}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   248
  bool operator()(uintptr_t* val) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   249
    EXPECT_EQ(*val, (uintptr_t)0x2) << "Got an unknown value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   250
    EXPECT_EQ(_count, 0u) << "Only one value should be in table.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   251
    _count++;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   252
    return true; /* continue scan */
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   253
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   254
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   255
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   256
static void cht_scan(Thread* thr) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   257
  uintptr_t val = 0x2;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   258
  SimpleTestLookup stl(val);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   259
  ChtScan scan;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   260
  SimpleTestTable* cht = new SimpleTestTable();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   261
  EXPECT_TRUE(cht->insert(thr, stl, val)) << "Insert unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   262
  EXPECT_EQ(cht->try_scan(thr, scan), true) << "Scanning an non-growing/shrinking table should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   263
  EXPECT_TRUE(cht->remove(thr, stl)) << "Removing a pre-existing value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   264
  EXPECT_FALSE(cht->get_copy(thr, stl) == val) << "Got a removed value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   265
  delete cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   266
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   267
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   268
static void cht_grow(Thread* thr) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   269
  uintptr_t val = 0x2;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   270
  uintptr_t val2 = 0x22;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   271
  uintptr_t val3 = 0x222;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   272
  SimpleTestLookup stl(val), stl2(val2), stl3(val3);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   273
  SimpleTestTable* cht = new SimpleTestTable();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   274
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   275
  EXPECT_TRUE(cht->insert(thr, stl, val)) << "Insert unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   276
  EXPECT_TRUE(cht->insert(thr, stl2, val2)) << "Insert unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   277
  EXPECT_TRUE(cht->insert(thr, stl3, val3)) << "Insert unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   278
  EXPECT_FALSE(cht->insert(thr, stl3, val3)) << "Insert duplicate value should have failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   279
  EXPECT_TRUE(cht->get_copy(thr, stl) == val) << "Getting an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   280
  EXPECT_TRUE(cht->get_copy(thr, stl2) == val2) << "Getting an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   281
  EXPECT_TRUE(cht->get_copy(thr, stl3) == val3) << "Getting an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   282
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   283
  EXPECT_TRUE(cht->remove(thr, stl2)) << "Removing an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   284
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   285
  EXPECT_TRUE(cht->get_copy(thr, stl) == val) << "Getting an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   286
  EXPECT_FALSE(cht->get_copy(thr, stl2) == val2) << "Getting a removed value should have failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   287
  EXPECT_TRUE(cht->get_copy(thr, stl3) == val3) << "Getting an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   288
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   289
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   290
  EXPECT_TRUE(cht->grow(thr)) << "Growing uncontended should not fail.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   291
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   292
  EXPECT_TRUE(cht->get_copy(thr, stl) == val) << "Getting an item after grow failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   293
  EXPECT_FALSE(cht->get_copy(thr, stl2) == val2) << "Getting a removed value after grow should have failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   294
  EXPECT_TRUE(cht->get_copy(thr, stl3) == val3) << "Getting an item after grow failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   295
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   296
  EXPECT_TRUE(cht->insert(thr, stl2, val2)) << "Insert unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   297
  EXPECT_TRUE(cht->remove(thr, stl3)) << "Removing an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   298
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   299
  EXPECT_TRUE(cht->shrink(thr)) << "Shrinking uncontended should not fail.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   300
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   301
  EXPECT_TRUE(cht->get_copy(thr, stl) == val) << "Getting an item after shrink failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   302
  EXPECT_TRUE(cht->get_copy(thr, stl2) == val2) << "Getting an item after shrink failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   303
  EXPECT_FALSE(cht->get_copy(thr, stl3) == val3) << "Getting a removed value after shrink should have failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   304
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   305
  delete cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   306
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   307
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   308
static void cht_task_grow(Thread* thr) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   309
  uintptr_t val = 0x2;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   310
  uintptr_t val2 = 0x22;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   311
  uintptr_t val3 = 0x222;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   312
  SimpleTestLookup stl(val), stl2(val2), stl3(val3);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   313
  SimpleTestTable* cht = new SimpleTestTable();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   314
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   315
  EXPECT_TRUE(cht->insert(thr, stl, val)) << "Insert unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   316
  EXPECT_TRUE(cht->insert(thr, stl2, val2)) << "Insert unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   317
  EXPECT_TRUE(cht->insert(thr, stl3, val3)) << "Insert unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   318
  EXPECT_FALSE(cht->insert(thr, stl3, val3)) << "Insert duplicate value should have failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   319
  EXPECT_TRUE(cht->get_copy(thr, stl) == val) << "Getting an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   320
  EXPECT_TRUE(cht->get_copy(thr, stl2) == val2) << "Getting an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   321
  EXPECT_TRUE(cht->get_copy(thr, stl3) == val3) << "Getting an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   322
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   323
  EXPECT_TRUE(cht->remove(thr, stl2)) << "Removing an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   324
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   325
  EXPECT_TRUE(cht->get_copy(thr, stl) == val) << "Getting an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   326
  EXPECT_FALSE(cht->get_copy(thr, stl2) == val2) << "Getting a removed value should have failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   327
  EXPECT_TRUE(cht->get_copy(thr, stl3) == val3) << "Getting an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   328
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   329
  SimpleTestTable::GrowTask gt(cht);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   330
  EXPECT_TRUE(gt.prepare(thr)) << "Growing uncontended should not fail.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   331
  while(gt.doTask(thr)) { /* grow */  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   332
  gt.done(thr);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   333
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   334
  EXPECT_TRUE(cht->get_copy(thr, stl) == val) << "Getting an item after grow failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   335
  EXPECT_FALSE(cht->get_copy(thr, stl2) == val2) << "Getting a removed value after grow should have failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   336
  EXPECT_TRUE(cht->get_copy(thr, stl3) == val3) << "Getting an item after grow failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   337
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   338
  EXPECT_TRUE(cht->insert(thr, stl2, val2)) << "Insert unique value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   339
  EXPECT_TRUE(cht->remove(thr, stl3)) << "Removing an inserted value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   340
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   341
  EXPECT_TRUE(cht->shrink(thr)) << "Shrinking uncontended should not fail.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   342
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   343
  EXPECT_TRUE(cht->get_copy(thr, stl) == val) << "Getting an item after shrink failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   344
  EXPECT_TRUE(cht->get_copy(thr, stl2) == val2) << "Getting an item after shrink failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   345
  EXPECT_FALSE(cht->get_copy(thr, stl3) == val3) << "Getting a removed value after shrink should have failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   346
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   347
  delete cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   348
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   349
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   350
TEST_VM(ConcurrentHashTable, basic_insert) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   351
  nomt_test_doer(cht_insert);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   352
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   353
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   354
TEST_VM(ConcurrentHashTable, basic_get_insert) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   355
  nomt_test_doer(cht_get_insert);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   356
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   357
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   358
TEST_VM(ConcurrentHashTable, basic_scope) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   359
  nomt_test_doer(cht_scope);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   360
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   361
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   362
TEST_VM(ConcurrentHashTable, basic_get_insert_bulk_delete) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   363
  nomt_test_doer(cht_getinsert_bulkdelete);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   364
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   365
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   366
TEST_VM(ConcurrentHashTable, basic_get_insert_bulk_delete_task) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   367
  nomt_test_doer(cht_getinsert_bulkdelete_task);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   368
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   369
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   370
TEST_VM(ConcurrentHashTable, basic_scan) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   371
  nomt_test_doer(cht_scan);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   372
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   373
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   374
TEST_VM(ConcurrentHashTable, basic_grow) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   375
  nomt_test_doer(cht_grow);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   376
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   377
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   378
TEST_VM(ConcurrentHashTable, task_grow) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   379
  nomt_test_doer(cht_task_grow);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   380
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   381
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   382
//#############################################################################################
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   383
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   384
class TestInterface;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   385
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   386
typedef ConcurrentHashTable<uintptr_t, TestInterface, mtInternal> TestTable;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   387
typedef ConcurrentHashTable<uintptr_t, TestInterface, mtInternal>::MultiGetHandle TestGetHandle;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   388
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   389
class TestInterface : public TestTable::BaseConfig {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   390
public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   391
  static uintx get_hash(const uintptr_t& value, bool* dead_hash) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   392
    return (uintx)(value + 18446744073709551557ul) * 18446744073709551557ul;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   393
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   394
  static const uintptr_t& notfound() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   395
    static uintptr_t notfound = 0;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   396
    return notfound;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   397
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   398
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   399
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   400
struct TestLookup {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   401
  uintptr_t _val;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   402
  TestLookup(uintptr_t val) : _val(val) {}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   403
  uintx get_hash() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   404
    return TestInterface::get_hash(_val, NULL);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   405
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   406
  bool equals(const uintptr_t* value, bool* is_dead) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   407
    return _val == *value;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   408
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   409
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   410
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   411
class CHTTestThread : public JavaTestThread {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   412
  public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   413
  uintptr_t _start;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   414
  uintptr_t _stop;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   415
  TestTable *_cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   416
  jlong _stop_ms;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   417
  CHTTestThread(uintptr_t start, uintptr_t stop, TestTable* cht, Semaphore* post)
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   418
    : JavaTestThread(post), _start(start), _stop(stop), _cht(cht) {}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   419
  virtual void premain() {}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   420
  void main_run() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   421
    premain();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   422
    _stop_ms = os::javaTimeMillis() + 2000; // 2 seconds max test time
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   423
    while (keep_looping() && test_loop()) { /* */ }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   424
    postmain();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   425
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   426
  virtual void postmain() {}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   427
  virtual bool keep_looping() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   428
    return _stop_ms > os::javaTimeMillis();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   429
  };
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   430
  virtual bool test_loop() = 0;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   431
  virtual ~CHTTestThread() {}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   432
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   433
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   434
class ValueSaver {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   435
  uintptr_t* _vals;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   436
  size_t _it;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   437
  size_t _size;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   438
 public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   439
  ValueSaver() : _it(0), _size(1024) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   440
      _vals = NEW_C_HEAP_ARRAY(uintptr_t, _size, mtInternal);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   441
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   442
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   443
  bool operator()(uintptr_t* val) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   444
    _vals[_it++] = *val;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   445
    if (_it == _size) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   446
      _size *= 2;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   447
      _vals = REALLOC_RESOURCE_ARRAY(uintptr_t, _vals, _size/2, _size);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   448
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   449
    return true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   450
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   451
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   452
  void check() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   453
    for (size_t i = 0; i < _it; i++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   454
      size_t count = 0;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   455
      for (size_t j = (i + 1u); j < _it; j++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   456
        if (_vals[i] == _vals[j]) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   457
          count++;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   458
        }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   459
      }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   460
      EXPECT_EQ(count, 0u);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   461
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   462
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   463
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   464
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   465
static void integrity_check(Thread* thr, TestTable* cht)
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   466
{
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   467
  ValueSaver vs;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   468
  cht->do_scan(thr, vs);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   469
  vs.check();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   470
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   471
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   472
//#############################################################################################
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   473
// All threads are working on different items
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   474
// This item should only be delete by this thread
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   475
// Thus get_unsafe is safe for this test.
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   476
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   477
class SimpleInserterThread : public CHTTestThread {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   478
public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   479
  static volatile bool _exit;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   480
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   481
  SimpleInserterThread(uintptr_t start, uintptr_t stop, TestTable* cht, Semaphore* post)
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   482
    : CHTTestThread(start, stop, cht, post) {};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   483
  virtual ~SimpleInserterThread(){}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   484
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   485
  bool keep_looping() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   486
    return !_exit;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   487
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   488
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   489
  bool test_loop() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   490
    bool grow;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   491
    for (uintptr_t v = _start; v <= _stop; v++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   492
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   493
      EXPECT_TRUE(_cht->insert(this, tl, v, &grow)) << "Inserting an unique value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   494
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   495
    for (uintptr_t v = _start; v <= _stop; v++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   496
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   497
      EXPECT_TRUE(_cht->get_copy(this, tl) == v) << "Getting an previously inserted value unsafe failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   498
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   499
    for (uintptr_t v = _start; v <= _stop; v++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   500
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   501
      EXPECT_TRUE(_cht->remove(this, tl)) << "Removing an existing value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   502
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   503
    for (uintptr_t v = _start; v <= _stop; v++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   504
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   505
      EXPECT_TRUE(_cht->get_copy(this, tl) == TestInterface::notfound()) << "Got a removed value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   506
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   507
    return true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   508
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   509
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   510
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   511
volatile bool SimpleInserterThread::_exit = false;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   512
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   513
class RunnerSimpleInserterThread : public CHTTestThread {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   514
public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   515
  Semaphore _done;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   516
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   517
  RunnerSimpleInserterThread(Semaphore* post) : CHTTestThread(0, 0, NULL, post) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   518
    _cht = new TestTable(SIZE_32, SIZE_32);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   519
  };
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   520
  virtual ~RunnerSimpleInserterThread(){}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   521
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   522
  void premain() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   523
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   524
    SimpleInserterThread* ins1 = new SimpleInserterThread((uintptr_t)0x100, (uintptr_t) 0x1FF, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   525
    SimpleInserterThread* ins2 = new SimpleInserterThread((uintptr_t)0x200, (uintptr_t) 0x2FF, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   526
    SimpleInserterThread* ins3 = new SimpleInserterThread((uintptr_t)0x300, (uintptr_t) 0x3FF, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   527
    SimpleInserterThread* ins4 = new SimpleInserterThread((uintptr_t)0x400, (uintptr_t) 0x4FF, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   528
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   529
    for (uintptr_t v = 0x500; v < 0x5FF; v++ ) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   530
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   531
      EXPECT_TRUE(_cht->insert(this, tl, v)) << "Inserting an unique value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   532
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   533
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   534
    ins1->doit();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   535
    ins2->doit();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   536
    ins3->doit();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   537
    ins4->doit();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   538
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   539
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   540
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   541
  bool test_loop() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   542
    for (uintptr_t v = 0x500; v < 0x5FF; v++ ) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   543
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   544
      EXPECT_TRUE(_cht->get_copy(this, tl) == v) << "Getting an previously inserted value unsafe failed.";;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   545
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   546
    return true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   547
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   548
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   549
  void postmain() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   550
    SimpleInserterThread::_exit = true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   551
    for (int i = 0; i < 4; i++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   552
      _done.wait();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   553
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   554
    for (uintptr_t v = 0x500; v < 0x5FF; v++ ) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   555
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   556
      EXPECT_TRUE(_cht->remove(this, tl)) << "Removing an existing value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   557
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   558
    integrity_check(this, _cht);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   559
    delete _cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   560
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   561
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   562
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   563
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   564
TEST_VM(ConcurrentHashTable, concurrent_simple) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   565
  SimpleInserterThread::_exit = false;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   566
  mt_test_doer<RunnerSimpleInserterThread>();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   567
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   568
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   569
//#############################################################################################
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   570
// In this test we try to get a 'bad' value
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   571
class DeleteInserterThread : public CHTTestThread {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   572
public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   573
  static volatile bool _exit;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   574
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   575
  DeleteInserterThread(uintptr_t start, uintptr_t stop, TestTable* cht, Semaphore* post) : CHTTestThread(start, stop, cht, post) {};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   576
  virtual ~DeleteInserterThread(){}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   577
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   578
  bool keep_looping() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   579
    return !_exit;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   580
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   581
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   582
  bool test_loop() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   583
    for (uintptr_t v = _start; v <= _stop; v++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   584
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   585
      _cht->insert(this, tl, v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   586
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   587
    for (uintptr_t v = _start; v <= _stop; v++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   588
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   589
      _cht->remove(this, tl);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   590
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   591
    return true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   592
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   593
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   594
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   595
volatile bool DeleteInserterThread::_exit = true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   596
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   597
class RunnerDeleteInserterThread : public CHTTestThread {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   598
public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   599
  Semaphore _done;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   600
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   601
  RunnerDeleteInserterThread(Semaphore* post) : CHTTestThread(0, 0, NULL, post) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   602
    _cht = new TestTable(SIZE_32, SIZE_32);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   603
  };
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   604
  virtual ~RunnerDeleteInserterThread(){}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   605
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   606
  void premain() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   607
    DeleteInserterThread* ins1 = new DeleteInserterThread((uintptr_t)0x1, (uintptr_t) 0xFFF, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   608
    DeleteInserterThread* ins2 = new DeleteInserterThread((uintptr_t)0x1, (uintptr_t) 0xFFF, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   609
    DeleteInserterThread* ins3 = new DeleteInserterThread((uintptr_t)0x1, (uintptr_t) 0xFFF, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   610
    DeleteInserterThread* ins4 = new DeleteInserterThread((uintptr_t)0x1, (uintptr_t) 0xFFF, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   611
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   612
    ins1->doit();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   613
    ins2->doit();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   614
    ins3->doit();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   615
    ins4->doit();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   616
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   617
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   618
  bool test_loop() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   619
    for (uintptr_t v = 0x1; v < 0xFFF; v++ ) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   620
      uintptr_t tv;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   621
      if (v & 0x1) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   622
        TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   623
        tv = _cht->get_copy(this, tl);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   624
      } else {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   625
        TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   626
        TestGetHandle value_handle(this, _cht);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   627
        uintptr_t* tmp = value_handle.get(tl);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   628
        tv = tmp != NULL ? *tmp : 0;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   629
      }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   630
      EXPECT_TRUE(tv == 0 || tv == v) << "Got unknown value.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   631
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   632
    return true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   633
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   634
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   635
  void postmain() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   636
    DeleteInserterThread::_exit = true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   637
    for (int i = 0; i < 4; i++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   638
      _done.wait();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   639
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   640
    integrity_check(this, _cht);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   641
    delete _cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   642
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   643
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   644
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   645
TEST_VM(ConcurrentHashTable, concurrent_deletes) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   646
  DeleteInserterThread::_exit = false;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   647
  mt_test_doer<RunnerDeleteInserterThread>();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   648
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   649
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   650
//#############################################################################################
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   651
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   652
#define START_SIZE 13
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   653
#define END_SIZE 17
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   654
#define START (uintptr_t)0x10000
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   655
#define RANGE (uintptr_t)0xFFFF
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   656
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   657
#define GSTEST_THREAD_COUNT 5
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   658
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   659
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   660
class GSInserterThread: public CHTTestThread {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   661
public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   662
  static volatile bool _shrink;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   663
  GSInserterThread(uintptr_t start, uintptr_t stop, TestTable* cht, Semaphore* post) : CHTTestThread(start, stop, cht, post) {};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   664
  virtual ~GSInserterThread(){}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   665
  bool keep_looping() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   666
    return !(_shrink && _cht->get_size_log2(this) == START_SIZE);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   667
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   668
  bool test_loop() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   669
    bool grow;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   670
    for (uintptr_t v = _start; v <= _stop; v++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   671
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   672
      EXPECT_TRUE(_cht->insert(this, tl, v, &grow)) << "Inserting an unique value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   673
      if (grow && !_shrink) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   674
        _cht->grow(this);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   675
      }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   676
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   677
    for (uintptr_t v = _start; v <= _stop; v++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   678
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   679
      EXPECT_TRUE(_cht->get_copy(this, tl) == v) <<  "Getting an previously inserted value unsafe failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   680
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   681
    for (uintptr_t v = _start; v <= _stop; v++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   682
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   683
      EXPECT_TRUE(_cht->remove(this, tl)) << "Removing an existing value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   684
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   685
    if (_shrink) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   686
      _cht->shrink(this);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   687
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   688
    for (uintptr_t v = _start; v <= _stop; v++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   689
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   690
      EXPECT_FALSE(_cht->get_copy(this, tl) == v)  << "Getting a removed value should have failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   691
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   692
    if (!_shrink && _cht->get_size_log2(this) == END_SIZE) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   693
      _shrink = true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   694
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   695
    return true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   696
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   697
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   698
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   699
volatile bool GSInserterThread::_shrink = false;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   700
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   701
class GSScannerThread : public CHTTestThread {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   702
public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   703
  GSScannerThread(uintptr_t start, uintptr_t stop, TestTable* cht, Semaphore* post) : CHTTestThread(start, stop, cht, post) {};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   704
  virtual ~GSScannerThread(){}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   705
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   706
  bool operator()(uintptr_t* val) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   707
    if (*val >= this->_start && *val <= this->_stop) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   708
      return false;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   709
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   710
    // continue scan
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   711
    return true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   712
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   713
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   714
  bool test_loop() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   715
    _cht->try_scan(this, *this);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   716
    os::naked_short_sleep(5);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   717
    return true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   718
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   719
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   720
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   721
class RunnerGSInserterThread : public CHTTestThread {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   722
public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   723
  uintptr_t _start;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   724
  uintptr_t _range;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   725
  Semaphore _done;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   726
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   727
  RunnerGSInserterThread(Semaphore* post) : CHTTestThread(0, 0, NULL, post) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   728
    _cht = new TestTable(START_SIZE, END_SIZE, 2);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   729
  };
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   730
  virtual ~RunnerGSInserterThread(){}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   731
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   732
  void premain() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   733
    volatile bool timeout = false;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   734
    _start = START;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   735
    _range = RANGE;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   736
    CHTTestThread* tt[GSTEST_THREAD_COUNT];
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   737
    tt[0] = new GSInserterThread(_start, _start + _range, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   738
    _start += _range + 1;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   739
    tt[1] = new GSInserterThread(_start, _start + _range, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   740
    _start += _range + 1;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   741
    tt[2] = new GSInserterThread(_start, _start + _range, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   742
    _start += _range + 1;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   743
    tt[3] = new GSInserterThread(_start, _start + _range, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   744
    tt[4] = new GSScannerThread(_start, _start + _range, _cht, &_done);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   745
    _start += _range + 1;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   746
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   747
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   748
    for (uintptr_t v = _start; v <= (_start + _range); v++ ) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   749
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   750
      EXPECT_TRUE(_cht->insert(this, tl, v)) << "Inserting an unique value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   751
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   752
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   753
    for (int i = 0; i < GSTEST_THREAD_COUNT; i++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   754
      tt[i]->doit();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   755
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   756
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   757
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   758
  bool test_loop() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   759
    for (uintptr_t v = _start; v <= (_start + _range); v++ ) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   760
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   761
      EXPECT_TRUE(_cht->get_copy(this, tl) == v) <<  "Getting an previously inserted value unsafe failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   762
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   763
    return true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   764
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   765
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   766
  void postmain() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   767
    GSInserterThread::_shrink = true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   768
    for (uintptr_t v = _start; v <= (_start + _range); v++ ) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   769
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   770
      EXPECT_TRUE(_cht->remove(this, tl)) << "Removing an existing value failed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   771
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   772
    for (int i = 0; i < GSTEST_THREAD_COUNT; i++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   773
      _done.wait();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   774
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   775
    EXPECT_TRUE(_cht->get_size_log2(this) == START_SIZE) << "Not at start size.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   776
    Count cnt;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   777
    _cht->do_scan(this, cnt);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   778
    EXPECT_TRUE(cnt._cnt == 0) << "Items still in table";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   779
    delete _cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   780
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   781
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   782
  struct Count {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   783
    Count() : _cnt(0) {}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   784
    size_t _cnt;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   785
    bool operator()(uintptr_t*) { _cnt++; return true; };
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   786
  };
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   787
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   788
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   789
TEST_VM(ConcurrentHashTable, concurrent_scan_grow_shrink) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   790
  GSInserterThread::_shrink = false;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   791
  mt_test_doer<RunnerGSInserterThread>();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   792
}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   793
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   794
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   795
//#############################################################################################
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   796
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   797
#define GI_BD_GI_BD_START_SIZE 13
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   798
#define GI_BD_END_SIZE 17
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   799
#define GI_BD_START (uintptr_t)0x1
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   800
#define GI_BD_RANGE (uintptr_t)0x3FFFF
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   801
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   802
#define GI_BD_TEST_THREAD_COUNT 4
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   803
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   804
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   805
class GI_BD_InserterThread: public CHTTestThread {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   806
public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   807
  static volatile bool _shrink;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   808
  uintptr_t _br;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   809
  GI_BD_InserterThread(uintptr_t start, uintptr_t stop, TestTable* cht, Semaphore* post, uintptr_t br)
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   810
    : CHTTestThread(start, stop, cht, post), _br(br) {};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   811
  virtual ~GI_BD_InserterThread(){}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   812
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   813
  bool keep_looping() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   814
    return !(_shrink && _cht->get_size_log2(this) == GI_BD_GI_BD_START_SIZE);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   815
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   816
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   817
  bool test_loop() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   818
    bool grow;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   819
    MyDel del(_br);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   820
    for (uintptr_t v = _start; v <= _stop; v++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   821
      ValVerify vv(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   822
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   823
      _cht->get_insert(this, tl, v, vv, &grow);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   824
      EXPECT_NE(vv.called_get, vv.called_insert) << "Non or both callbacks was called.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   825
      if (grow && !_shrink) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   826
        _cht->grow(this);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   827
      }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   828
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   829
    if (_shrink) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   830
      _cht->shrink(this);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   831
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   832
    _cht->try_bulk_delete(this, *this, del);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   833
    if (!_shrink && _cht->is_max_size_reached()) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   834
      _shrink = true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   835
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   836
    _cht->bulk_delete(this, *this, del);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   837
    return true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   838
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   839
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   840
  bool operator()(uintptr_t* val) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   841
    return (*val & _br) == 1;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   842
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   843
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   844
  struct MyDel {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   845
    MyDel(uintptr_t &br) : _br(br) {};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   846
    uintptr_t &_br;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   847
    void operator()(uintptr_t* val) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   848
      EXPECT_EQ((*val & _br), _br) << "Removing an item that should not have been removed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   849
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   850
  };
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   851
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   852
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   853
volatile bool GI_BD_InserterThread::_shrink = false;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   854
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   855
class RunnerGI_BD_InserterThread : public CHTTestThread {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   856
public:
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   857
  Semaphore _done;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   858
  uintptr_t _start;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   859
  uintptr_t _range;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   860
  RunnerGI_BD_InserterThread(Semaphore* post) : CHTTestThread(0, 0, NULL, post) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   861
    _cht = new TestTable(GI_BD_GI_BD_START_SIZE, GI_BD_END_SIZE, 2);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   862
  };
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   863
  virtual ~RunnerGI_BD_InserterThread(){}
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   864
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   865
  void premain() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   866
    _start = GI_BD_START;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   867
    _range = GI_BD_RANGE;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   868
    CHTTestThread* tt[GI_BD_TEST_THREAD_COUNT];
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   869
    tt[0] = new GI_BD_InserterThread(_start, _start + _range, _cht, &_done, (uintptr_t)0x1);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   870
    tt[1] = new GI_BD_InserterThread(_start, _start + _range, _cht, &_done, (uintptr_t)0x2);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   871
    tt[2] = new GI_BD_InserterThread(_start, _start + _range, _cht, &_done, (uintptr_t)0x4);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   872
    tt[3] = new GI_BD_InserterThread(_start, _start + _range, _cht, &_done, (uintptr_t)0x8);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   873
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   874
    for (uintptr_t v = _start; v <= (_start + _range); v++ ) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   875
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   876
      EXPECT_TRUE(_cht->insert(this, tl, v)) << "Inserting an unique value should work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   877
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   878
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   879
    for (int i =0; i < GI_BD_TEST_THREAD_COUNT; i++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   880
      tt[i]->doit();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   881
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   882
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   883
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   884
  bool test_loop() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   885
    for (uintptr_t v = _start; v <= (_start + _range); v++ ) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   886
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   887
      if (v & 0xF) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   888
        _cht->get_copy(this, tl);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   889
      } else {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   890
        EXPECT_EQ(_cht->get_copy(this, tl), v) << "Item ending with 0xX0 should never be removed.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   891
      }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   892
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   893
    return true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   894
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   895
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   896
  void postmain() {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   897
    GI_BD_InserterThread::_shrink = true;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   898
    for (uintptr_t v = _start; v <= (_start + _range); v++ ) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   899
      TestLookup tl(v);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   900
      if (v & 0xF) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   901
        _cht->remove(this, tl);
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   902
      } else {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   903
        EXPECT_TRUE(_cht->remove(this, tl)) << "Removing item ending with 0xX0 should always work.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   904
      }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   905
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   906
    for (int i = 0; i < GI_BD_TEST_THREAD_COUNT; i++) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   907
      _done.wait();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   908
    }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   909
    EXPECT_TRUE(_cht->get_size_log2(this) == GI_BD_GI_BD_START_SIZE) << "We have not shrunk back to start size.";
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   910
    delete _cht;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   911
  }
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   912
};
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   913
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   914
TEST_VM(ConcurrentHashTable, concurrent_get_insert_bulk_delete) {
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   915
  GI_BD_InserterThread::_shrink = false;
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   916
  mt_test_doer<RunnerGI_BD_InserterThread>();
8e4fcfb4cfe4 8195098: Low latency hashtable for read-mostly scenarios
rehn
parents:
diff changeset
   917
}