1%module db_java 2 3%include "various.i" 4%include "typemaps.i" 5 6%include "java_util.i" 7%include "java_except.i" 8%include "java_typemaps.i" 9%include "java_stat.i" 10%include "java_callbacks.i" 11 12/* 13 * No finalize methods in general - most classes have "destructor" methods 14 * that applications must call explicitly. 15 */ 16%typemap(javafinalize) SWIGTYPE "" 17 18/* 19 * These are the exceptions - when there is no "close" method, we need to free 20 * the native part at finalization time. These are exactly the cases where C 21 * applications manage the memory for the handles. 22 */ 23%typemap(javafinalize) struct DbLsn, struct DbLock %{ 24 protected void finalize() { 25 try { 26 delete(); 27 } catch(Exception e) { 28 System.err.println("Exception during finalization: " + e); 29 e.printStackTrace(System.err); 30 } 31 } 32%} 33 34%typemap(javaimports) SWIGTYPE %{ 35import com.sleepycat.db.*; 36import java.util.Comparator; 37%} 38 39/* Class names */ 40%rename(LogSequenceNumber) DbLsn; 41 42/* Destructors */ 43%rename(close0) close; 44%rename(remove0) remove; 45%rename(rename0) rename; 46%rename(verify0) verify; 47%rename(abort0) abort; 48%rename(commit0) commit; 49%rename(discard0) discard; 50 51/* Special case methods */ 52%rename(set_tx_timestamp0) set_tx_timestamp; 53 54/* Extra code in the Java classes */ 55%typemap(javacode) struct DbEnv %{ 56 /* 57 * Internally, the JNI layer creates a global reference to each DbEnv, 58 * which can potentially be different to this. We keep a copy here so 59 * we can clean up after destructors. 60 */ 61 private long dbenv_ref; 62 public Environment wrapper; 63 64 private LogRecordHandler app_dispatch_handler; 65 private EventHandler event_notify_handler; 66 private FeedbackHandler env_feedback_handler; 67 private ErrorHandler error_handler; 68 private String errpfx; 69 private MessageHandler message_handler; 70 private PanicHandler panic_handler; 71 private ReplicationTransport rep_transport_handler; 72 private java.io.OutputStream error_stream; 73 private java.io.OutputStream message_stream; 74 private ThreadLocal errBuf; 75 76 public static class RepProcessMessage { 77 public int envid; 78 } 79 80 /* 81 * Called by the public DbEnv constructor and for private environments 82 * by the Db constructor. 83 */ 84 void initialize() { 85 dbenv_ref = db_java.initDbEnvRef0(this, this); 86 errBuf = new ThreadLocal(); 87 /* Start with System.err as the default error stream. */ 88 set_error_stream(System.err); 89 set_message_stream(System.out); 90 } 91 92 void cleanup() { 93 swigCPtr = 0; 94 db_java.deleteRef0(dbenv_ref); 95 dbenv_ref = 0L; 96 } 97 98 public synchronized void close(int flags) throws DatabaseException { 99 try { 100 close0(flags); 101 } finally { 102 cleanup(); 103 } 104 } 105 106 private final int handle_app_dispatch(DatabaseEntry dbt, 107 LogSequenceNumber lsn, 108 int recops) { 109 return app_dispatch_handler.handleLogRecord(wrapper, dbt, lsn, 110 RecoveryOperation.fromFlag(recops)); 111 } 112 113 public LogRecordHandler get_app_dispatch() { 114 return app_dispatch_handler; 115 } 116 117 private final void handle_panic_event_notify() { 118 event_notify_handler.handlePanicEvent(); 119 } 120 121 private final void handle_rep_client_event_notify() { 122 event_notify_handler.handleRepClientEvent(); 123 } 124 125 private final void handle_rep_elected_event_notify() { 126 event_notify_handler.handleRepElectedEvent(); 127 } 128 129 private final void handle_rep_master_event_notify() { 130 event_notify_handler.handleRepMasterEvent(); 131 } 132 133 private final void handle_rep_new_master_event_notify(int envid) { 134 event_notify_handler.handleRepNewMasterEvent(envid); 135 } 136 137 private final void handle_rep_perm_failed_event_notify() { 138 event_notify_handler.handleRepPermFailedEvent(); 139 } 140 141 private final void handle_rep_startup_done_event_notify() { 142 event_notify_handler.handleRepStartupDoneEvent(); 143 } 144 145 private final void handle_write_failed_event_notify(int errno) { 146 event_notify_handler.handleWriteFailedEvent(errno); 147 } 148 149 public EventHandler get_event_notify() { 150 return event_notify_handler; 151 } 152 153 private final void handle_env_feedback(int opcode, int percent) { 154 if (opcode == DbConstants.DB_RECOVER) 155 env_feedback_handler.recoveryFeedback(wrapper, percent); 156 /* No other environment feedback type supported. */ 157 } 158 159 public FeedbackHandler get_feedback() { 160 return env_feedback_handler; 161 } 162 163 public void set_errpfx(String errpfx) { 164 this.errpfx = errpfx; 165 } 166 167 public String get_errpfx() { 168 return errpfx; 169 } 170 171 private final void handle_error(String msg) { 172 com.sleepycat.util.ErrorBuffer ebuf = (com.sleepycat.util.ErrorBuffer)errBuf.get(); 173 if (ebuf == null) { 174 /* 175 * Populate the errBuf ThreadLocal on demand, since the 176 * callback can be made from different threads. 177 */ 178 ebuf = new com.sleepycat.util.ErrorBuffer(3); 179 errBuf.set(ebuf); 180 } 181 ebuf.append(msg); 182 error_handler.error(wrapper, this.errpfx, msg); 183 } 184 185 private final String get_err_msg(String orig_msg) { 186 com.sleepycat.util.ErrorBuffer ebuf = (com.sleepycat.util.ErrorBuffer)errBuf.get(); 187 String ret = null; 188 if (ebuf != null) { 189 ret = ebuf.get(); 190 ebuf.clear(); 191 } 192 if (ret != null && ret.length() > 0) 193 return orig_msg + ": " + ret; 194 return orig_msg; 195 } 196 197 public ErrorHandler get_errcall() { 198 return error_handler; 199 } 200 201 private final void handle_message(String msg) { 202 message_handler.message(wrapper, msg); 203 } 204 205 public MessageHandler get_msgcall() { 206 return message_handler; 207 } 208 209 private final void handle_panic(DatabaseException e) { 210 panic_handler.panic(wrapper, e); 211 } 212 213 public PanicHandler get_paniccall() { 214 return panic_handler; 215 } 216 217 private final int handle_rep_transport(DatabaseEntry control, 218 DatabaseEntry rec, 219 LogSequenceNumber lsn, 220 int envid, int flags) 221 throws DatabaseException { 222 return rep_transport_handler.send(wrapper, 223 control, rec, lsn, envid, 224 (flags & DbConstants.DB_REP_NOBUFFER) != 0, 225 (flags & DbConstants.DB_REP_PERMANENT) != 0, 226 (flags & DbConstants.DB_REP_ANYWHERE) != 0, 227 (flags & DbConstants.DB_REP_REREQUEST) != 0); 228 } 229 230 public void lock_vec(/*u_int32_t*/ int locker, int flags, 231 LockRequest[] list, int offset, int count) 232 throws DatabaseException { 233 db_javaJNI.DbEnv_lock_vec(swigCPtr, this, locker, flags, list, 234 offset, count); 235 } 236 237 public synchronized void remove(String db_home, int flags) 238 throws DatabaseException, java.io.FileNotFoundException { 239 try { 240 remove0(db_home, flags); 241 } finally { 242 cleanup(); 243 } 244 } 245 246 public void set_error_stream(java.io.OutputStream stream) { 247 error_stream = stream; 248 final java.io.PrintWriter pw = new java.io.PrintWriter(stream); 249 set_errcall(new ErrorHandler() { 250 public void error(Environment env, 251 String prefix, String buf) /* no exception */ { 252 if (prefix != null) 253 pw.print(prefix + ": "); 254 pw.println(buf); 255 pw.flush(); 256 } 257 }); 258 } 259 260 public java.io.OutputStream get_error_stream() { 261 return error_stream; 262 } 263 264 public void set_message_stream(java.io.OutputStream stream) { 265 message_stream = stream; 266 final java.io.PrintWriter pw = new java.io.PrintWriter(stream); 267 set_msgcall(new MessageHandler() { 268 public void message(Environment env, String msg) 269 /* no exception */ { 270 pw.println(msg); 271 pw.flush(); 272 } 273 }); 274 } 275 276 public java.io.OutputStream get_message_stream() { 277 return message_stream; 278 } 279 280 public void set_tx_timestamp(java.util.Date timestamp) { 281 set_tx_timestamp0(timestamp.getTime()/1000); 282 } 283%} 284 285%typemap(javacode) struct Db %{ 286 /* package */ static final int GIGABYTE = 1 << 30; 287 /* 288 * Internally, the JNI layer creates a global reference to each Db, 289 * which can potentially be different to this. We keep a copy here so 290 * we can clean up after destructors. 291 */ 292 private long db_ref; 293 private DbEnv dbenv; 294 private boolean private_dbenv; 295 296 public Database wrapper; 297 private RecordNumberAppender append_recno_handler; 298 private Comparator bt_compare_handler; 299 private BtreePrefixCalculator bt_prefix_handler; 300 private Comparator dup_compare_handler; 301 private FeedbackHandler db_feedback_handler; 302 private Comparator h_compare_handler; 303 private Hasher h_hash_handler; 304 private SecondaryKeyCreator seckey_create_handler; 305 private SecondaryMultiKeyCreator secmultikey_create_handler; 306 private ForeignKeyNullifier foreignkey_nullify_handler; 307 private ForeignMultiKeyNullifier foreignmultikey_nullify_handler; 308 309 /* Called by the Db constructor */ 310 private void initialize(DbEnv dbenv) { 311 if (dbenv == null) { 312 private_dbenv = true; 313 dbenv = db_java.getDbEnv0(this); 314 dbenv.initialize(); 315 } 316 this.dbenv = dbenv; 317 db_ref = db_java.initDbRef0(this, this); 318 } 319 320 private void cleanup() { 321 swigCPtr = 0; 322 db_java.deleteRef0(db_ref); 323 db_ref = 0L; 324 if (private_dbenv) 325 dbenv.cleanup(); 326 dbenv = null; 327 } 328 329 public boolean getPrivateDbEnv() { 330 return private_dbenv; 331 } 332 333 public synchronized void close(int flags) throws DatabaseException { 334 try { 335 close0(flags); 336 } finally { 337 cleanup(); 338 } 339 } 340 341 public DbEnv get_env() throws DatabaseException { 342 return dbenv; 343 } 344 345 private final void handle_append_recno(DatabaseEntry data, int recno) 346 throws DatabaseException { 347 append_recno_handler.appendRecordNumber(wrapper, data, recno); 348 } 349 350 public RecordNumberAppender get_append_recno() { 351 return append_recno_handler; 352 } 353 354 private final int handle_bt_compare(byte[] arr1, byte[] arr2) { 355 return bt_compare_handler.compare(arr1, arr2); 356 } 357 358 public Comparator get_bt_compare() { 359 return bt_compare_handler; 360 } 361 362 private final int handle_bt_prefix(DatabaseEntry dbt1, 363 DatabaseEntry dbt2) { 364 return bt_prefix_handler.prefix(wrapper, dbt1, dbt2); 365 } 366 367 public BtreePrefixCalculator get_bt_prefix() { 368 return bt_prefix_handler; 369 } 370 371 private final void handle_db_feedback(int opcode, int percent) { 372 if (opcode == DbConstants.DB_UPGRADE) 373 db_feedback_handler.upgradeFeedback(wrapper, percent); 374 else if (opcode == DbConstants.DB_VERIFY) 375 db_feedback_handler.upgradeFeedback(wrapper, percent); 376 /* No other database feedback types known. */ 377 } 378 379 public FeedbackHandler get_feedback() { 380 return db_feedback_handler; 381 } 382 383 private final int handle_h_compare(byte[] arr1, byte[] arr2) { 384 return h_compare_handler.compare(arr1, arr2); 385 } 386 387 public Comparator get_h_compare() { 388 return h_compare_handler; 389 } 390 391 private final int handle_dup_compare(byte[] arr1, byte[] arr2) { 392 return dup_compare_handler.compare(arr1, arr2); 393 } 394 395 public Comparator get_dup_compare() { 396 return dup_compare_handler; 397 } 398 399 private final int handle_h_hash(byte[] data, int len) { 400 return h_hash_handler.hash(wrapper, data, len); 401 } 402 403 public Hasher get_h_hash() { 404 return h_hash_handler; 405 } 406 407 private final boolean handle_foreignkey_nullify( 408 DatabaseEntry key, 409 DatabaseEntry data, 410 DatabaseEntry seckey) 411 throws DatabaseException { 412 if (foreignmultikey_nullify_handler != null) 413 return foreignmultikey_nullify_handler.nullifyForeignKey( 414 (SecondaryDatabase)wrapper, key, data, seckey); 415 else 416 return foreignkey_nullify_handler.nullifyForeignKey( 417 (SecondaryDatabase)wrapper, data); 418 } 419 420 private final DatabaseEntry[] handle_seckey_create( 421 DatabaseEntry key, 422 DatabaseEntry data) 423 throws DatabaseException { 424 425 if (secmultikey_create_handler != null) { 426 java.util.HashSet keySet = new java.util.HashSet(); 427 secmultikey_create_handler.createSecondaryKeys( 428 (SecondaryDatabase)wrapper, key, data, keySet); 429 if (!keySet.isEmpty()) 430 return (DatabaseEntry[])keySet.toArray( 431 new DatabaseEntry[keySet.size()]); 432 } else { 433 DatabaseEntry result = new DatabaseEntry(); 434 if (seckey_create_handler.createSecondaryKey( 435 (SecondaryDatabase)wrapper, key, data, result)) { 436 DatabaseEntry[] results = { result }; 437 return results; 438 } 439 } 440 441 return null; 442 } 443 444 public SecondaryKeyCreator get_seckey_create() { 445 return seckey_create_handler; 446 } 447 448 public SecondaryMultiKeyCreator get_secmultikey_create() { 449 return secmultikey_create_handler; 450 } 451 452 public void set_secmultikey_create( 453 SecondaryMultiKeyCreator secmultikey_create_handler) { 454 this.secmultikey_create_handler = secmultikey_create_handler; 455 } 456 457 public void set_foreignmultikey_nullifier(ForeignMultiKeyNullifier nullify){ 458 this.foreignmultikey_nullify_handler = nullify; 459 } 460 461 public synchronized void remove(String file, String database, int flags) 462 throws DatabaseException, java.io.FileNotFoundException { 463 try { 464 remove0(file, database, flags); 465 } finally { 466 cleanup(); 467 } 468 } 469 470 public synchronized void rename(String file, String database, 471 String newname, int flags) 472 throws DatabaseException, java.io.FileNotFoundException { 473 try { 474 rename0(file, database, newname, flags); 475 } finally { 476 cleanup(); 477 } 478 } 479 480 public synchronized boolean verify(String file, String database, 481 java.io.OutputStream outfile, int flags) 482 throws DatabaseException, java.io.FileNotFoundException { 483 try { 484 return verify0(file, database, outfile, flags); 485 } finally { 486 cleanup(); 487 } 488 } 489 490 public ErrorHandler get_errcall() { 491 return dbenv.get_errcall(); 492 } 493 494 public void set_errcall(ErrorHandler db_errcall_fcn) { 495 dbenv.set_errcall(db_errcall_fcn); 496 } 497 498 public java.io.OutputStream get_error_stream() { 499 return dbenv.get_error_stream(); 500 } 501 502 public void set_error_stream(java.io.OutputStream stream) { 503 dbenv.set_error_stream(stream); 504 } 505 506 public void set_errpfx(String errpfx) { 507 dbenv.set_errpfx(errpfx); 508 } 509 510 public String get_errpfx() { 511 return dbenv.get_errpfx(); 512 } 513 514 public java.io.OutputStream get_message_stream() { 515 return dbenv.get_message_stream(); 516 } 517 518 public void set_message_stream(java.io.OutputStream stream) { 519 dbenv.set_message_stream(stream); 520 } 521 522 public MessageHandler get_msgcall() { 523 return dbenv.get_msgcall(); 524 } 525 526 public void set_msgcall(MessageHandler db_msgcall_fcn) { 527 dbenv.set_msgcall(db_msgcall_fcn); 528 } 529 530 public void set_paniccall(PanicHandler db_panic_fcn) 531 throws DatabaseException { 532 dbenv.set_paniccall(db_panic_fcn); 533 } 534 535 public PanicHandler get_paniccall() { 536 return dbenv.get_paniccall(); 537 } 538%} 539 540%typemap(javacode) struct Dbc %{ 541 public synchronized void close() throws DatabaseException { 542 try { 543 close0(); 544 } finally { 545 swigCPtr = 0; 546 } 547 } 548%} 549 550%typemap(javacode) struct DbLock %{ 551 public Lock wrapper; 552%} 553 554%typemap(javacode) struct DbLogc %{ 555 public synchronized void close(int flags) throws DatabaseException { 556 try { 557 close0(flags); 558 } finally { 559 swigCPtr = 0; 560 } 561 } 562%} 563 564%typemap(javacode) struct DbSequence %{ 565 public Sequence wrapper; 566 567 public synchronized void close(int flags) throws DatabaseException { 568 try { 569 close0(flags); 570 } finally { 571 swigCPtr = 0; 572 } 573 } 574 575 public synchronized void remove(DbTxn txn, int flags) 576 throws DatabaseException { 577 try { 578 remove0(txn, flags); 579 } finally { 580 swigCPtr = 0; 581 } 582 } 583%} 584 585%typemap(javacode) struct DbTxn %{ 586 public void abort() throws DatabaseException { 587 try { 588 abort0(); 589 } finally { 590 swigCPtr = 0; 591 } 592 } 593 594 public void commit(int flags) throws DatabaseException { 595 try { 596 commit0(flags); 597 } finally { 598 swigCPtr = 0; 599 } 600 } 601 602 public void discard(int flags) throws DatabaseException { 603 try { 604 discard0(flags); 605 } finally { 606 swigCPtr = 0; 607 } 608 } 609 610 /* 611 * We override Object.equals because it is possible for the Java API to 612 * create multiple DbTxns that reference the same underlying object. 613 * This can happen for example during DbEnv.txn_recover(). 614 */ 615 public boolean equals(Object obj) 616 { 617 if (this == obj) 618 return true; 619 620 if (obj != null && (obj instanceof DbTxn)) { 621 DbTxn that = (DbTxn)obj; 622 return (this.swigCPtr == that.swigCPtr); 623 } 624 return false; 625 } 626 627 /* 628 * We must override Object.hashCode whenever we override 629 * Object.equals() to enforce the maxim that equal objects have the 630 * same hashcode. 631 */ 632 public int hashCode() 633 { 634 return ((int)swigCPtr ^ (int)(swigCPtr >> 32)); 635 } 636%} 637 638%native(initDbEnvRef0) jlong initDbEnvRef0(DB_ENV *self, void *handle); 639%native(initDbRef0) jlong initDbRef0(DB *self, void *handle); 640%native(deleteRef0) void deleteRef0(jlong ref); 641%native(getDbEnv0) DB_ENV *getDbEnv0(DB *self); 642 643%{ 644SWIGEXPORT jlong JNICALL 645Java_com_sleepycat_db_internal_db_1javaJNI_initDbEnvRef0( 646 JNIEnv *jenv, jclass jcls, jlong jarg1, jobject jarg1_, jobject jarg2) { 647 DB_ENV *self = *(DB_ENV **)(void *)&jarg1; 648 jlong ret; 649 COMPQUIET(jcls, NULL); 650 COMPQUIET(jarg1_, NULL); 651 652 DB_ENV_INTERNAL(self) = (void *)(*jenv)->NewGlobalRef(jenv, jarg2); 653 *(jobject *)(void *)&ret = (jobject)DB_ENV_INTERNAL(self); 654 return (ret); 655} 656 657SWIGEXPORT jlong JNICALL 658Java_com_sleepycat_db_internal_db_1javaJNI_initDbRef0( 659 JNIEnv *jenv, jclass jcls, jlong jarg1, jobject jarg1_, jobject jarg2) { 660 DB *self = *(DB **)(void *)&jarg1; 661 jlong ret; 662 COMPQUIET(jcls, NULL); 663 COMPQUIET(jarg1_, NULL); 664 665 DB_INTERNAL(self) = (void *)(*jenv)->NewGlobalRef(jenv, jarg2); 666 *(jobject *)(void *)&ret = (jobject)DB_INTERNAL(self); 667 return (ret); 668} 669 670SWIGEXPORT void JNICALL 671Java_com_sleepycat_db_internal_db_1javaJNI_deleteRef0( 672 JNIEnv *jenv, jclass jcls, jlong jarg1) { 673 jobject jref = *(jobject *)(void *)&jarg1; 674 COMPQUIET(jcls, NULL); 675 676 if (jref != 0L) 677 (*jenv)->DeleteGlobalRef(jenv, jref); 678} 679 680SWIGEXPORT jlong JNICALL 681Java_com_sleepycat_db_internal_db_1javaJNI_getDbEnv0( 682 JNIEnv *jenv, jclass jcls, jlong jarg1, jobject jarg1_) { 683 DB *self = *(DB **)(void *)&jarg1; 684 jlong ret; 685 686 COMPQUIET(jenv, NULL); 687 COMPQUIET(jcls, NULL); 688 COMPQUIET(jarg1_, NULL); 689 690 *(DB_ENV **)(void *)&ret = self->dbenv; 691 return (ret); 692} 693 694SWIGEXPORT jboolean JNICALL 695Java_com_sleepycat_db_internal_DbUtil_is_1big_1endian( 696 JNIEnv *jenv, jclass clazz) 697{ 698 COMPQUIET(jenv, NULL); 699 COMPQUIET(clazz, NULL); 700 701 return (__db_isbigendian() ? JNI_TRUE : JNI_FALSE); 702} 703%} 704