1 8 9 package com.sleepycat.je.tree; 10 11 import java.io.File ; 12 import java.io.IOException ; 13 14 import junit.framework.TestCase; 15 16 import com.sleepycat.bind.tuple.IntegerBinding; 17 import com.sleepycat.je.Cursor; 18 import com.sleepycat.je.Database; 19 import com.sleepycat.je.DatabaseConfig; 20 import com.sleepycat.je.DatabaseEntry; 21 import com.sleepycat.je.DatabaseException; 22 import com.sleepycat.je.DbInternal; 23 import com.sleepycat.je.Environment; 24 import com.sleepycat.je.EnvironmentConfig; 25 import com.sleepycat.je.LockMode; 26 import com.sleepycat.je.OperationStatus; 27 import com.sleepycat.je.util.TestUtils; 28 import com.sleepycat.je.utilint.TestHook; 29 30 98 99 public class SplitRace_SR11144Test extends TestCase { 100 private static final boolean DEBUG = false; 101 private File envHome; 102 private Environment env = null; 103 private Database db = null; 104 105 public SplitRace_SR11144Test() { 106 envHome = new File (System.getProperty(TestUtils.DEST_DIR)); 107 } 108 109 public void setUp() 110 throws IOException { 111 112 TestUtils.removeLogFiles("Setup", envHome, false); 113 } 114 115 public void tearDown() 116 throws Exception { 117 118 try { 119 120 if (env != null) { 121 env.close(); 122 } 123 } catch (DatabaseException e) { 124 125 } 126 env = null; TestUtils.removeLogFiles("TearDown", envHome, false); 128 } 129 130 public void testSplitRootRace() 131 throws Throwable { 132 133 134 initData(); 135 136 141 142 InsertThread a = new InsertThread(92, db); 143 InsertThread b = new InsertThread(202, db); 144 setWaiterHook(); 145 b.start(); 146 a.start(); 147 148 a.join(); 149 b.join(); 150 151 close(); 152 } 153 154 165 private void initData() { 166 try { 167 initEnvInternal(true); 168 169 173 int value = 0; 174 for (int i = 0; i < 23; i++) { 175 put(db, value); 176 value += 10; 177 } 178 179 180 put(db, 91); 181 put(db, 201); 182 183 if (DEBUG) { 184 dump(); 185 } 186 } catch (DatabaseException DBE) { 187 throw new RuntimeException (DBE); 188 } 189 } 190 191 private static void put(Database db, int value) 192 throws DatabaseException { 193 194 DatabaseEntry key = new DatabaseEntry(); 195 DatabaseEntry data = new DatabaseEntry(); 196 197 IntegerBinding.intToEntry(11, data); 198 IntegerBinding.intToEntry(value, key); 199 200 OperationStatus status = db.putNoOverwrite(null, key, data); 201 if (status != OperationStatus.SUCCESS) { 202 throw new RuntimeException ("status=" + status); 203 } 204 } 205 206 private void close() { 207 try { 208 db.close(); 209 env.close(); 210 } catch (DatabaseException DBE) { 211 throw new RuntimeException (DBE); 212 } 213 } 214 215 private void dump() { 216 try { 217 Cursor cursor = db.openCursor(null, null); 218 DatabaseEntry key = new DatabaseEntry(); 219 DatabaseEntry data = new DatabaseEntry(); 220 while (cursor.getNext(key, data, LockMode.DEFAULT) == 221 OperationStatus.SUCCESS) { 222 System.out.println("<rec key=\"" + 223 IntegerBinding.entryToInt(key) + 224 "\" data=\"" + 225 IntegerBinding.entryToInt(data) + 226 "\"/>"); 227 } 228 DbInternal.dbGetDatabaseImpl(db).getTree().dump(); 229 cursor.close(); 230 } catch (DatabaseException DBE) { 231 throw new RuntimeException (DBE); 232 } 233 } 234 235 private void initEnvInternal(boolean create) 236 throws DatabaseException { 237 238 EnvironmentConfig envConfig = TestUtils.initEnvConfig(); 239 envConfig.setTransactional(true); 240 envConfig.setAllowCreate(create); 241 envConfig.setConfigParam("je.nodeMaxEntries", "4"); 242 envConfig.setConfigParam("je.nodeDupTreeMaxEntries", "4"); 243 env = new Environment(envHome, envConfig); 244 245 DatabaseConfig dbConfig = new DatabaseConfig(); 246 dbConfig.setAllowCreate(create); 247 dbConfig.setTransactional(true); 248 dbConfig.setExclusiveCreate(create); 249 db = env.openDatabase(null, "foo", dbConfig); 250 } 251 252 private void setWaiterHook() { 253 TestHook hook = new WaiterHook(); 254 DbInternal.dbGetDatabaseImpl(db).getTree().setWaitHook(hook); 255 } 256 257 261 static class WaiterHook implements TestHook { 262 private int numArrived; 263 private Object block; 264 265 WaiterHook() { 266 numArrived = 0; 267 block = new Object (); 268 } 269 270 public void doHook() { 271 synchronized (block) { 272 if (numArrived == 0) { 273 numArrived = 1; 274 try { 275 block.wait(); 276 } catch (InterruptedException e) { 277 e.printStackTrace(); 278 } 279 } else if (numArrived == 1) { 280 numArrived = 2; 281 block.notify(); 282 } 283 } 284 } 285 286 public void doIOHook() 287 throws IOException { 288 289 } 290 291 public Object getHookValue() { 292 return null; 293 } 294 } 295 296 297 static class InsertThread extends Thread { 298 private int value; 299 private Database db; 300 301 InsertThread(int value, Database db) { 302 this.value = value; 303 this.db = db; 304 } 305 306 public void run() { 307 try { 308 put(db, value); 309 } catch (Exception e) { 310 e.printStackTrace(); 311 fail(e.getMessage()); 312 } 313 } 314 } 315 } 316 | Popular Tags |