1 /* 2 * Copyright (C) 2006-2008 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #undef LOG_TAG 18 #define LOG_TAG "Cursor" 19 20 #include <jni.h> 21 #include <JNIHelp.h> 22 #include <android_runtime/AndroidRuntime.h> 23 24 #include <sqlite3.h> 25 26 #include <utils/Log.h> 27 28 #include <stdio.h> 29 #include <string.h> 30 #include <unistd.h> 31 32 #include "sqlite3_exception.h" 33 34 35 namespace android { 36 37 static jfieldID gHandleField; 38 static jfieldID gStatementField; 39 40 41 #define GET_STATEMENT(env, object) \ 42 (sqlite3_stmt *)env->GetIntField(object, gStatementField) 43 #define GET_HANDLE(env, object) \ 44 (sqlite3 *)env->GetIntField(object, gHandleField) 45 46 static void native_compile(JNIEnv* env, jobject object, jstring sqlString) 47 { 48 char buf[65]; 49 strcpy(buf, "android_database_SQLiteProgram->native_compile() not implemented"); 50 throw_sqlite3_exception(env, GET_HANDLE(env, object), buf); 51 return; 52 } 53 54 static void native_bind_null(JNIEnv* env, jobject object, 55 jint index) 56 { 57 int err; 58 sqlite3_stmt * statement = GET_STATEMENT(env, object); 59 60 err = sqlite3_bind_null(statement, index); 61 if (err != SQLITE_OK) { 62 char buf[32]; 63 sprintf(buf, "handle %p", statement); 64 throw_sqlite3_exception(env, GET_HANDLE(env, object), buf); 65 return; 66 } 67 } 68 69 static void native_bind_long(JNIEnv* env, jobject object, 70 jint index, jlong value) 71 { 72 int err; 73 sqlite3_stmt * statement = GET_STATEMENT(env, object); 74 75 err = sqlite3_bind_int64(statement, index, value); 76 if (err != SQLITE_OK) { 77 char buf[32]; 78 sprintf(buf, "handle %p", statement); 79 throw_sqlite3_exception(env, GET_HANDLE(env, object), buf); 80 return; 81 } 82 } 83 84 static void native_bind_double(JNIEnv* env, jobject object, 85 jint index, jdouble value) 86 { 87 int err; 88 sqlite3_stmt * statement = GET_STATEMENT(env, object); 89 90 err = sqlite3_bind_double(statement, index, value); 91 if (err != SQLITE_OK) { 92 char buf[32]; 93 sprintf(buf, "handle %p", statement); 94 throw_sqlite3_exception(env, GET_HANDLE(env, object), buf); 95 return; 96 } 97 } 98 99 static void native_bind_string(JNIEnv* env, jobject object, 100 jint index, jstring sqlString) 101 { 102 int err; 103 jchar const * sql; 104 jsize sqlLen; 105 sqlite3_stmt * statement= GET_STATEMENT(env, object); 106 107 sql = env->GetStringChars(sqlString, NULL); 108 sqlLen = env->GetStringLength(sqlString); 109 err = sqlite3_bind_text16(statement, index, sql, sqlLen * 2, SQLITE_TRANSIENT); 110 env->ReleaseStringChars(sqlString, sql); 111 if (err != SQLITE_OK) { 112 char buf[32]; 113 sprintf(buf, "handle %p", statement); 114 throw_sqlite3_exception(env, GET_HANDLE(env, object), buf); 115 return; 116 } 117 } 118 119 static void native_bind_blob(JNIEnv* env, jobject object, 120 jint index, jbyteArray value) 121 { 122 int err; 123 jchar const * sql; 124 jsize sqlLen; 125 sqlite3_stmt * statement= GET_STATEMENT(env, object); 126 127 jint len = env->GetArrayLength(value); 128 jbyte * bytes = env->GetByteArrayElements(value, NULL); 129 130 err = sqlite3_bind_blob(statement, index, bytes, len, SQLITE_TRANSIENT); 131 env->ReleaseByteArrayElements(value, bytes, JNI_ABORT); 132 133 if (err != SQLITE_OK) { 134 char buf[32]; 135 sprintf(buf, "statement %p", statement); 136 throw_sqlite3_exception(env, GET_HANDLE(env, object), buf); 137 return; 138 } 139 } 140 141 static void native_clear_bindings(JNIEnv* env, jobject object) 142 { 143 int err; 144 sqlite3_stmt * statement = GET_STATEMENT(env, object); 145 146 err = sqlite3_clear_bindings(statement); 147 if (err != SQLITE_OK) { 148 throw_sqlite3_exception(env, GET_HANDLE(env, object)); 149 return; 150 } 151 } 152 153 static void native_finalize(JNIEnv* env, jobject object) 154 { 155 char buf[66]; 156 strcpy(buf, "android_database_SQLiteProgram->native_finalize() not implemented"); 157 throw_sqlite3_exception(env, GET_HANDLE(env, object), buf); 158 return; 159 } 160 161 162 static JNINativeMethod sMethods[] = 163 { 164 /* name, signature, funcPtr */ 165 {"native_bind_null", "(I)V", (void *)native_bind_null}, 166 {"native_bind_long", "(IJ)V", (void *)native_bind_long}, 167 {"native_bind_double", "(ID)V", (void *)native_bind_double}, 168 {"native_bind_string", "(ILjava/lang/String;)V", (void *)native_bind_string}, 169 {"native_bind_blob", "(I[B)V", (void *)native_bind_blob}, 170 {"native_clear_bindings", "()V", (void *)native_clear_bindings}, 171 }; 172 173 int register_android_database_SQLiteProgram(JNIEnv * env) 174 { 175 jclass clazz; 176 177 clazz = env->FindClass("android/database/sqlite/SQLiteProgram"); 178 if (clazz == NULL) { 179 LOGE("Can't find android/database/sqlite/SQLiteProgram"); 180 return -1; 181 } 182 183 gHandleField = env->GetFieldID(clazz, "nHandle", "I"); 184 gStatementField = env->GetFieldID(clazz, "nStatement", "I"); 185 186 if (gHandleField == NULL || gStatementField == NULL) { 187 LOGE("Error locating fields"); 188 return -1; 189 } 190 191 return AndroidRuntime::registerNativeMethods(env, 192 "android/database/sqlite/SQLiteProgram", sMethods, NELEM(sMethods)); 193 } 194 195 } // namespace android 196