]> git.proxmox.com Git - ceph.git/blob - ceph/src/rocksdb/java/rocksjni/ttl.cc
update sources to ceph Nautilus 14.2.1
[ceph.git] / ceph / src / rocksdb / java / rocksjni / ttl.cc
1 // Copyright (c) 2011-present, Facebook, Inc. All rights reserved.
2 // This source code is licensed under both the GPLv2 (found in the
3 // COPYING file in the root directory) and Apache 2.0 License
4 // (found in the LICENSE.Apache file in the root directory).
5 //
6 // This file implements the "bridge" between Java and C++ and enables
7 // calling c++ rocksdb::TtlDB methods.
8 // from Java side.
9
10 #include <jni.h>
11 #include <stdio.h>
12 #include <stdlib.h>
13 #include <memory>
14 #include <string>
15 #include <vector>
16
17 #include "include/org_rocksdb_TtlDB.h"
18 #include "rocksdb/utilities/db_ttl.h"
19 #include "rocksjni/portal.h"
20
21 /*
22 * Class: org_rocksdb_TtlDB
23 * Method: open
24 * Signature: (JLjava/lang/String;IZ)J
25 */
26 jlong Java_org_rocksdb_TtlDB_open(JNIEnv* env, jclass /*jcls*/,
27 jlong joptions_handle, jstring jdb_path,
28 jint jttl, jboolean jread_only) {
29 const char* db_path = env->GetStringUTFChars(jdb_path, nullptr);
30 if (db_path == nullptr) {
31 // exception thrown: OutOfMemoryError
32 return 0;
33 }
34
35 auto* opt = reinterpret_cast<rocksdb::Options*>(joptions_handle);
36 rocksdb::DBWithTTL* db = nullptr;
37 rocksdb::Status s =
38 rocksdb::DBWithTTL::Open(*opt, db_path, &db, jttl, jread_only);
39 env->ReleaseStringUTFChars(jdb_path, db_path);
40
41 // as TTLDB extends RocksDB on the java side, we can reuse
42 // the RocksDB portal here.
43 if (s.ok()) {
44 return reinterpret_cast<jlong>(db);
45 } else {
46 rocksdb::RocksDBExceptionJni::ThrowNew(env, s);
47 return 0;
48 }
49 }
50
51 /*
52 * Class: org_rocksdb_TtlDB
53 * Method: openCF
54 * Signature: (JLjava/lang/String;[[B[J[IZ)[J
55 */
56 jlongArray Java_org_rocksdb_TtlDB_openCF(JNIEnv* env, jclass /*jcls*/,
57 jlong jopt_handle, jstring jdb_path,
58 jobjectArray jcolumn_names,
59 jlongArray jcolumn_options,
60 jintArray jttls, jboolean jread_only) {
61 const char* db_path = env->GetStringUTFChars(jdb_path, nullptr);
62 if (db_path == nullptr) {
63 // exception thrown: OutOfMemoryError
64 return 0;
65 }
66
67 const jsize len_cols = env->GetArrayLength(jcolumn_names);
68 jlong* jco = env->GetLongArrayElements(jcolumn_options, nullptr);
69 if (jco == nullptr) {
70 // exception thrown: OutOfMemoryError
71 env->ReleaseStringUTFChars(jdb_path, db_path);
72 return nullptr;
73 }
74
75 std::vector<rocksdb::ColumnFamilyDescriptor> column_families;
76 jboolean has_exception = JNI_FALSE;
77 rocksdb::JniUtil::byteStrings<std::string>(
78 env, jcolumn_names,
79 [](const char* str_data, const size_t str_len) {
80 return std::string(str_data, str_len);
81 },
82 [&jco, &column_families](size_t idx, std::string cf_name) {
83 rocksdb::ColumnFamilyOptions* cf_options =
84 reinterpret_cast<rocksdb::ColumnFamilyOptions*>(jco[idx]);
85 column_families.push_back(
86 rocksdb::ColumnFamilyDescriptor(cf_name, *cf_options));
87 },
88 &has_exception);
89
90 env->ReleaseLongArrayElements(jcolumn_options, jco, JNI_ABORT);
91
92 if (has_exception == JNI_TRUE) {
93 // exception occurred
94 env->ReleaseStringUTFChars(jdb_path, db_path);
95 return nullptr;
96 }
97
98 std::vector<int32_t> ttl_values;
99 jint* jttlv = env->GetIntArrayElements(jttls, nullptr);
100 if (jttlv == nullptr) {
101 // exception thrown: OutOfMemoryError
102 env->ReleaseStringUTFChars(jdb_path, db_path);
103 return nullptr;
104 }
105 const jsize len_ttls = env->GetArrayLength(jttls);
106 for (jsize i = 0; i < len_ttls; i++) {
107 ttl_values.push_back(jttlv[i]);
108 }
109 env->ReleaseIntArrayElements(jttls, jttlv, JNI_ABORT);
110
111 auto* opt = reinterpret_cast<rocksdb::DBOptions*>(jopt_handle);
112 std::vector<rocksdb::ColumnFamilyHandle*> handles;
113 rocksdb::DBWithTTL* db = nullptr;
114 rocksdb::Status s = rocksdb::DBWithTTL::Open(
115 *opt, db_path, column_families, &handles, &db, ttl_values, jread_only);
116
117 // we have now finished with db_path
118 env->ReleaseStringUTFChars(jdb_path, db_path);
119
120 // check if open operation was successful
121 if (s.ok()) {
122 const jsize resultsLen = 1 + len_cols; // db handle + column family handles
123 std::unique_ptr<jlong[]> results =
124 std::unique_ptr<jlong[]>(new jlong[resultsLen]);
125 results[0] = reinterpret_cast<jlong>(db);
126 for (int i = 1; i <= len_cols; i++) {
127 results[i] = reinterpret_cast<jlong>(handles[i - 1]);
128 }
129
130 jlongArray jresults = env->NewLongArray(resultsLen);
131 if (jresults == nullptr) {
132 // exception thrown: OutOfMemoryError
133 return nullptr;
134 }
135
136 env->SetLongArrayRegion(jresults, 0, resultsLen, results.get());
137 if (env->ExceptionCheck()) {
138 // exception thrown: ArrayIndexOutOfBoundsException
139 env->DeleteLocalRef(jresults);
140 return nullptr;
141 }
142
143 return jresults;
144 } else {
145 rocksdb::RocksDBExceptionJni::ThrowNew(env, s);
146 return NULL;
147 }
148 }
149
150 /*
151 * Class: org_rocksdb_TtlDB
152 * Method: createColumnFamilyWithTtl
153 * Signature: (JLorg/rocksdb/ColumnFamilyDescriptor;[BJI)J;
154 */
155 jlong Java_org_rocksdb_TtlDB_createColumnFamilyWithTtl(
156 JNIEnv* env, jobject /*jobj*/, jlong jdb_handle, jbyteArray jcolumn_name,
157 jlong jcolumn_options, jint jttl) {
158 jbyte* cfname = env->GetByteArrayElements(jcolumn_name, nullptr);
159 if (cfname == nullptr) {
160 // exception thrown: OutOfMemoryError
161 return 0;
162 }
163 const jsize len = env->GetArrayLength(jcolumn_name);
164
165 auto* cfOptions =
166 reinterpret_cast<rocksdb::ColumnFamilyOptions*>(jcolumn_options);
167
168 auto* db_handle = reinterpret_cast<rocksdb::DBWithTTL*>(jdb_handle);
169 rocksdb::ColumnFamilyHandle* handle;
170 rocksdb::Status s = db_handle->CreateColumnFamilyWithTtl(
171 *cfOptions, std::string(reinterpret_cast<char*>(cfname), len), &handle,
172 jttl);
173
174 env->ReleaseByteArrayElements(jcolumn_name, cfname, 0);
175
176 if (s.ok()) {
177 return reinterpret_cast<jlong>(handle);
178 }
179 rocksdb::RocksDBExceptionJni::ThrowNew(env, s);
180 return 0;
181 }