00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #ifndef PPL_ppl_java_common_inlines_hh
00025 #define PPL_ppl_java_common_inlines_hh 1
00026
00027 #include <cassert>
00028
00029 namespace Parma_Polyhedra_Library {
00030
00031 namespace Interfaces {
00032
00033 namespace Java {
00034
00035 template <typename U, typename V>
00036 U
00037 jtype_to_unsigned(const V& value) {
00038 if (value < 0)
00039 throw std::invalid_argument("not an unsigned integer.");
00040
00041 if (sizeof(U) < sizeof(V)) {
00042 if (value > static_cast<V>(std::numeric_limits<U>::max()))
00043 throw std::invalid_argument("unsigned integer out of range.");
00044 }
00045
00046 return value;
00047 }
00048
00049 template <typename T>
00050 inline void
00051 set_ptr(JNIEnv* env, jobject ppl_object,
00052 const T* address, bool to_be_marked) {
00053 const T* ptr = (to_be_marked ? mark(address) : address);
00054 jlong pointer_value = reinterpret_cast<jlong>(ptr);
00055 assert(reinterpret_cast<const T*>(pointer_value) == ptr);
00056 env->SetLongField(ppl_object, cached_FMIDs.PPL_Object_ptr_ID, pointer_value);
00057 }
00058
00059 inline void*
00060 get_ptr(JNIEnv* env, jobject ppl_object) {
00061 jlong pointer_value
00062 = env->GetLongField(ppl_object, cached_FMIDs.PPL_Object_ptr_ID);
00063 void* ptr = reinterpret_cast<void*>(pointer_value);
00064 assert(reinterpret_cast<jlong>(ptr) == pointer_value);
00065 return unmark(ptr);
00066 }
00067
00068 inline bool
00069 is_java_marked(JNIEnv* env, jobject ppl_object) {
00070 jlong pointer_value
00071 = env->GetLongField(ppl_object, cached_FMIDs.PPL_Object_ptr_ID);
00072 const void* ptr = reinterpret_cast<const void*>(pointer_value);
00073 assert(reinterpret_cast<jlong>(ptr) == pointer_value);
00074 return marked(ptr);
00075 }
00076
00077 inline void
00078 set_coefficient(JNIEnv* env, jobject dst, jobject src) {
00079 jobject src_bi
00080 = env->GetObjectField(src, cached_FMIDs.Coefficient_value_ID);
00081 env->SetObjectField(dst, cached_FMIDs.Coefficient_value_ID, src_bi);
00082 }
00083
00084 inline void
00085 set_by_reference(JNIEnv* env, jobject by_ref_dst, jobject src) {
00086 env->SetObjectField(by_ref_dst,
00087 cached_FMIDs.By_Reference_obj_ID,
00088 src);
00089 }
00090
00091 inline jobject
00092 get_by_reference(JNIEnv* env, jobject by_reference) {
00093 return env->GetObjectField(by_reference, cached_FMIDs.By_Reference_obj_ID);
00094 }
00095
00096 template <typename R>
00097 jobject
00098 build_linear_expression(JNIEnv* env, const R& r) {
00099 jobject j_ret;
00100 PPL_DIRTY_TEMP_COEFFICIENT(coefficient);
00101 dimension_type varid = 0;
00102 dimension_type space_dimension = r.space_dimension();
00103 while (varid < space_dimension
00104 && (coefficient = r.coefficient(Variable(varid))) == 0)
00105 ++varid;
00106 if (varid >= space_dimension) {
00107 jobject j_coefficient_zero = build_java_coeff(env, Coefficient(0));
00108 j_ret = env->NewObject(cached_classes.Linear_Expression_Coefficient,
00109 cached_FMIDs.Linear_Expression_Coefficient_init_ID,
00110 j_coefficient_zero);
00111 CHECK_RESULT_THROW(env, j_ret);
00112 }
00113 else {
00114 jmethodID coeff_var_init_ID
00115 = cached_FMIDs.Linear_Expression_Times_init_from_coeff_var_ID;
00116 jobject j_coefficient = build_java_coeff(env, coefficient);
00117 jobject j_variable = build_java_variable(env, Variable(varid));
00118 jclass j_le_times_class = cached_classes.Linear_Expression_Times;
00119 jobject j_coeff_var = env->NewObject(j_le_times_class,
00120 coeff_var_init_ID,
00121 j_coefficient, j_variable);
00122 CHECK_EXCEPTION_THROW(env);
00123 j_ret = j_coeff_var;
00124 while (true) {
00125 ++varid;
00126 while (varid < space_dimension
00127 && (coefficient = r.coefficient(Variable(varid))) == 0)
00128 ++varid;
00129 if (varid >= space_dimension)
00130 break;
00131 else {
00132 j_coefficient = build_java_coeff(env, coefficient);
00133 j_variable = build_java_variable(env, Variable(varid));
00134 j_coeff_var = env->NewObject(j_le_times_class,
00135 coeff_var_init_ID,
00136 j_coefficient, j_variable);
00137 CHECK_EXCEPTION_THROW(env);
00138 j_ret = env->CallObjectMethod(j_ret,
00139 cached_FMIDs.Linear_Expression_sum_ID,
00140 j_coeff_var);
00141 CHECK_EXCEPTION_THROW(env);
00142 }
00143 }
00144 }
00145 return j_ret;
00146 }
00147
00148 inline Variable
00149 build_cxx_variable(JNIEnv* env, jobject j_var) {
00150 return Variable(env->GetIntField(j_var, cached_FMIDs.Variable_varid_ID));
00151 }
00152
00153 inline jobject
00154 build_java_variable(JNIEnv* env, const Variable& var) {
00155 jobject ret = env->NewObject(cached_classes.Variable,
00156 cached_FMIDs.Variable_init_ID,
00157 var.id());
00158 CHECK_RESULT_THROW(env, ret);
00159 return ret;
00160 }
00161
00162 inline Coefficient
00163 build_cxx_coeff(JNIEnv* env, jobject j_coeff) {
00164 jstring bi_string
00165 = (jstring) env->CallObjectMethod(j_coeff,
00166 cached_FMIDs.Coefficient_toString_ID);
00167 CHECK_EXCEPTION_THROW(env);
00168 const char *nativeString = env->GetStringUTFChars(bi_string, 0);
00169 CHECK_RESULT_THROW(env, nativeString);
00170 PPL_DIRTY_TEMP_COEFFICIENT(ppl_coeff);
00171 ppl_coeff = Coefficient(nativeString);
00172 env->ReleaseStringUTFChars(bi_string, nativeString);
00173 return ppl_coeff;
00174 }
00175
00176 inline jobject
00177 build_java_coeff(JNIEnv* env, const Coefficient& ppl_coeff) {
00178 std::ostringstream s;
00179 s << ppl_coeff;
00180 std::string str = s.str();
00181 jstring coeff_string = env->NewStringUTF(str.c_str());
00182 CHECK_RESULT_THROW(env, coeff_string);
00183 jobject ret = env->NewObject(cached_classes.Coefficient,
00184 cached_FMIDs.Coefficient_init_from_String_ID,
00185 coeff_string);
00186 CHECK_RESULT_THROW(env, ret);
00187 return ret;
00188 }
00189
00190 template <typename System, typename Elem_Builder>
00191 System
00192 build_cxx_system(JNIEnv* env, jobject j_iterable, Elem_Builder build_cxx_elem) {
00193
00194 jobject j_iter
00195 = env->CallObjectMethod(j_iterable, cached_FMIDs.System_iterator_ID);
00196 CHECK_EXCEPTION_THROW(env);
00197
00198 jmethodID has_next_mID = cached_FMIDs.System_Iterator_has_next_ID;
00199 jmethodID next_mID = cached_FMIDs.System_Iterator_next_ID;
00200
00201 System cxx_sys;
00202 jobject j_element;
00203 jboolean has_next_value = env->CallBooleanMethod(j_iter, has_next_mID);
00204 CHECK_EXCEPTION_ASSERT(env);
00205 while (has_next_value) {
00206 j_element = env->CallObjectMethod(j_iter, next_mID);
00207 CHECK_EXCEPTION_ASSERT(env);
00208 cxx_sys.insert(build_cxx_elem(env, j_element));
00209 has_next_value = env->CallBooleanMethod(j_iter, has_next_mID);
00210 CHECK_EXCEPTION_ASSERT(env);
00211 }
00212 return cxx_sys;
00213 }
00214
00215 inline Congruence_System
00216 build_cxx_congruence_system(JNIEnv* env, jobject j_iterable) {
00217 return
00218 build_cxx_system<Congruence_System>(env, j_iterable, build_cxx_congruence);
00219 }
00220
00221 inline Constraint_System
00222 build_cxx_constraint_system(JNIEnv* env, jobject j_iterable) {
00223 return
00224 build_cxx_system<Constraint_System>(env, j_iterable, build_cxx_constraint);
00225 }
00226
00227 inline Generator_System
00228 build_cxx_generator_system(JNIEnv* env, jobject j_iterable) {
00229 return
00230 build_cxx_system<Generator_System>(env, j_iterable, build_cxx_generator);
00231 }
00232
00233 inline Grid_Generator_System
00234 build_cxx_grid_generator_system(JNIEnv* env, jobject j_iterable) {
00235 return build_cxx_system<Grid_Generator_System> (env, j_iterable,
00236 build_cxx_grid_generator);
00237 }
00238
00239 }
00240
00241 }
00242
00243 }
00244
00245 #endif // !defined(PPL_ppl_java_common_inlines_hh)