jni_simple/lib.rs
1//! # jni-simple
2//! This crate contains a simple dumb handwritten rust wrapper around the JNI (Java Native Interface) API.
3//! It does absolutely no magic around the JNI Calls and lets you just use it as you would in C.
4//!
5//! In addition to JNI, this crate also provides a similar simplistic wrapper for the JVMTI (Java VM Tool Interface) API.
6//! The JVMTI Api can be used to write, for example, a Java Agent (like a Java debugger) in Rust or perform similar deep instrumentation with the JVM.
7//!
8//! If you are looking to start a jvm from rust then the entrypoints in this create are
9//! `init_dynamic_link`, `load_jvm_from_library`, `JNI_CreateJavaVM` and `JNI_GetCreatedJavaVMs`.
10//!
11//! If you are looking to write a jni library in rust then the types `JNIEnv` and jclass, etc.
12//! should be sufficient.
13//!
14#![no_std]
15#![allow(non_snake_case)]
16#![allow(non_camel_case_types)]
17#![deny(clippy::correctness)]
18#![deny(
19 clippy::perf,
20 clippy::complexity,
21 clippy::style,
22 clippy::nursery,
23 clippy::pedantic,
24 clippy::clone_on_ref_ptr,
25 clippy::decimal_literal_representation,
26 clippy::float_cmp_const,
27 clippy::missing_docs_in_private_items,
28 clippy::multiple_inherent_impl,
29 clippy::unwrap_used,
30 clippy::cargo_common_metadata,
31 clippy::used_underscore_binding
32)]
33#![allow(clippy::cognitive_complexity)]
34#![allow(clippy::inline_always)]
35//#![allow(clippy::trivially_copy_pass_by_ref)]
36
37/// This module contains the abi wrapper for jboolean using `core::ffi::c_uchar`
38mod jbool;
39/// This module contains all functions that are relevant for dynamic linking of the jvm.
40mod linking;
41
42pub use linking::{JNI_CreateJavaVM, JNI_CreateJavaVM_with_string_args, JNI_GetCreatedJavaVMs, JNI_GetCreatedJavaVMs_first, init_dynamic_link, is_jvm_loaded};
43
44#[cfg(feature = "loadjvm")]
45pub use linking::{LoadFromLibraryError, load_jvm_from_library};
46
47#[cfg(all(feature = "loadjvm", feature = "std"))]
48pub use linking::{LoadFromJavaHomeError, LoadFromJavaHomeFolderError, load_jvm_from_java_home, load_jvm_from_java_home_folder};
49
50extern crate alloc;
51#[cfg(feature = "std")]
52extern crate std;
53
54use alloc::borrow::Cow;
55use alloc::ffi::CString;
56use alloc::string::String;
57use alloc::string::ToString;
58use alloc::vec;
59use alloc::vec::Vec;
60
61use crate::private::{SealedAsJNILinkage, SealedEnvVTable, SealedJBooleanInputLayout, SealedJBooleanMutPtr};
62use alloc::boxed::Box;
63use core::cmp::Ordering;
64use core::ffi::{CStr, c_char, c_int, c_uchar, c_void};
65use core::fmt::{Debug, Display, Formatter};
66use core::hash::{Hash, Hasher};
67use core::ptr::null;
68use core::ptr::null_mut;
69use core::sync::atomic::Ordering::SeqCst;
70use sync_ptr::{FromMutPtr, SyncFnPtr, SyncMutPtr, sync_fn_ptr, sync_fn_ptr_opt};
71
72pub use crate::jbool::jboolean;
73pub const JNI_TRUE: jboolean = jboolean::TRUE;
74pub const JNI_FALSE: jboolean = jboolean::FALSE;
75
76///
77/// Trait for all types that can be used as a mutable boolean pointer for jni.
78/// JVM commonly uses this for functions that have an c-style output parameter via a pointer.
79///
80/// Implemented by
81/// - `&mut jboolean`
82/// - `* mut jboolean`
83/// - `&mut bool`
84/// - `* mut bool`
85/// - `()` -> "null pointer"
86///
87pub trait JBooleanMutPtr: SealedJBooleanMutPtr {}
88
89/// Trait for all types that have a ABI that is compatible for
90/// passing a jboolean from rust to java.
91///
92/// Implemented by:
93/// - `core::ffi::c_uchar`
94/// - `bool`
95/// - `jboolean`
96pub trait JBooleanInputLayout: SealedJBooleanInputLayout {}
97
98pub const JNI_OK: jint = 0;
99
100pub const JNI_COMMIT: jint = 1;
101
102pub const JNI_ABORT: jint = 2;
103pub const JNI_ERR: jint = -1;
104pub const JNI_EDETACHED: jint = -2;
105pub const JNI_EVERSION: jint = -3;
106pub const JNI_ENOMEM: jint = -4;
107pub const JNI_EEXIST: jint = -5;
108pub const JNI_EINVAL: jint = -6;
109pub const JVMTI_VERSION_1: jint = 0x3001_0000;
110pub const JVMTI_VERSION_1_0: jint = 0x3001_0000;
111pub const JVMTI_VERSION_1_1: jint = 0x3001_0100;
112pub const JVMTI_VERSION_1_2: jint = 0x3001_0200;
113
114pub const JVMTI_VERSION_9: jint = 0x3009_0000;
115pub const JVMTI_VERSION_11: jint = 0x300B_0000;
116pub const JVMTI_VERSION_19: jint = 0x3013_0000;
117pub const JVMTI_VERSION_21: jint = 0x3015_0000;
118
119pub const JVMTI_VERSION_25: jint = 0x3019_0000;
120
121pub const JNI_VERSION_1_1: jint = 0x0001_0001;
122pub const JNI_VERSION_1_2: jint = 0x0001_0002;
123pub const JNI_VERSION_1_4: jint = 0x0001_0004;
124pub const JNI_VERSION_1_6: jint = 0x0001_0006;
125pub const JNI_VERSION_1_8: jint = 0x0001_0008;
126pub const JNI_VERSION_9: jint = 0x0009_0000;
127pub const JNI_VERSION_10: jint = 0x000a_0000;
128pub const JNI_VERSION_19: jint = 0x0013_0000;
129pub const JNI_VERSION_20: jint = 0x0014_0000;
130pub const JNI_VERSION_21: jint = 0x0015_0000;
131
132pub const JNI_VERSION_24: jint = 0x0018_0000;
133
134//https://docs.oracle.com/en/java/javase/17/docs/api/constant-values.html#java.lang.reflect.Modifier.FINAL
135
136/// JVM modifier constant that represents the "final" keyword.
137pub const REFLECT_MODIFIER_FINAL: jint = 16;
138
139/// JVM modifier constant that represents the "interface" keyword.
140pub const REFLECT_MODIFIER_INTERFACE: jint = 512;
141
142/// JVM modifier constant that represents the "native" keyword.
143pub const REFLECT_MODIFIER_NATIVE: jint = 256;
144
145/// JVM modifier constant that represents the "private" keyword.
146pub const REFLECT_MODIFIER_PRIVATE: jint = 2;
147
148/// JVM modifier constant that represents the "protected" keyword.
149pub const REFLECT_MODIFIER_PROTECTED: jint = 4;
150
151/// JVM modifier constant that represents the "public" keyword.
152pub const REFLECT_MODIFIER_PUBLIC: jint = 1;
153
154/// JVM modifier constant that represents the "static" keyword.
155pub const REFLECT_MODIFIER_STATIC: jint = 8;
156
157/// JVM modifier constant that represents the "strictfp" keyword.
158pub const REFLECT_MODIFIER_STRICT: jint = 2048;
159
160/// JVM modifier constant that represents the "synchronized" keyword.
161pub const REFLECT_MODIFIER_SYNCHRONIZED: jint = 32;
162
163/// JVM modifier constant that represents the "transient" keyword.
164pub const REFLECT_MODIFIER_TRANSIENT: jint = 128;
165
166/// JVM modifier constant that represents the "volatile" keyword.
167pub const REFLECT_MODIFIER_VOLATILE: jint = 64;
168
169pub type jlong = i64;
170
171pub type jlocation = jlong;
172
173pub type jint = i32;
174pub type jsize = jint;
175pub type jshort = i16;
176pub type jchar = u16;
177pub type jbyte = i8;
178
179pub type jfloat = core::ffi::c_float;
180
181pub type jdouble = core::ffi::c_double;
182
183pub type jclass = *mut c_void;
184
185pub type jobject = *mut c_void;
186
187pub type jstring = jobject;
188
189pub type jarray = jobject;
190
191pub type jobjectArray = jarray;
192
193pub type jbooleanArray = jarray;
194
195pub type jbyteArray = jarray;
196
197pub type jcharArray = jarray;
198
199pub type jshortArray = jarray;
200
201pub type jintArray = jarray;
202
203pub type jlongArray = jarray;
204
205pub type jfloatArray = jarray;
206
207pub type jdoubleArray = jarray;
208
209#[repr(C)]
210#[derive(Debug, Ord, Eq, PartialOrd, PartialEq, Hash, Clone, Copy)]
211pub enum jobjectRefType {
212 JNIInvalidRefType = 0,
213 JNILocalRefType = 1,
214 JNIGlobalRefType = 2,
215 JNIWeakGlobalRefType = 3,
216}
217
218/// Rust enum that mirrors jvmtiError, however it has a different repr to `c_int` causing it to be incompatible outside of rust code.
219///
220/// It is mainly useful to use in rusts match statements.
221///
222/// This enum can be transformed from the repr(C) jvmtiError or transformed into it via the From/Into traits.
223#[derive(Debug, Eq, Clone, Copy)]
224pub enum JvmtiError {
225 NONE,
226 INVALID_THREAD,
227 INVALID_THREAD_GROUP,
228 INVALID_PRIORITY,
229 THREAD_NOT_SUSPENDED,
230 THREAD_SUSPENDED,
231 THREAD_NOT_ALIVE,
232 INVALID_OBJECT,
233 INVALID_CLASS,
234 CLASS_NOT_PREPARED,
235 INVALID_METHODID,
236 INVALID_LOCATION,
237 INVALID_FIELDID,
238 INVALID_MODULE,
239 NO_MORE_FRAMES,
240 OPAQUE_FRAME,
241 TYPE_MISMATCH,
242 INVALID_SLOT,
243 DUPLICATE,
244 NOT_FOUND,
245 INVALID_MONITOR,
246 NOT_MONITOR_OWNER,
247 INTERRUPT,
248 INVALID_CLASS_FORMAT,
249 CIRCULAR_CLASS_DEFINITION,
250 FAILS_VERIFICATION,
251 UNSUPPORTED_REDEFINITION_METHOD_ADDED,
252 UNSUPPORTED_REDEFINITION_SCHEMA_CHANGED,
253 INVALID_TYPESTATE,
254 UNSUPPORTED_REDEFINITION_HIERARCHY_CHANGED,
255 UNSUPPORTED_REDEFINITION_METHOD_DELETED,
256 UNSUPPORTED_VERSION,
257 NAMES_DONT_MATCH,
258 UNSUPPORTED_REDEFINITION_CLASS_MODIFIERS_CHANGED,
259 UNSUPPORTED_REDEFINITION_METHOD_MODIFIERS_CHANGED,
260 UNSUPPORTED_REDEFINITION_CLASS_ATTRIBUTE_CHANGED,
261 UNSUPPORTED_OPERATION,
262 UNMODIFIABLE_CLASS,
263 UNMODIFIABLE_MODULE,
264 NOT_AVAILABLE,
265 MUST_POSSESS_CAPABILITY,
266 NULL_POINTER,
267 ABSENT_INFORMATION,
268 INVALID_EVENT_TYPE,
269 ILLEGAL_ARGUMENT,
270 NATIVE_METHOD,
271 CLASS_LOADER_UNSUPPORTED,
272 OUT_OF_MEMORY,
273 ACCESS_DENIED,
274 WRONG_PHASE,
275 INTERNAL,
276 UNATTACHED_THREAD,
277 INVALID_ENVIRONMENT,
278 OTHER(c_int), //TODO seal this c_int
279}
280
281impl Display for JvmtiError {
282 fn fmt(&self, f: &mut Formatter<'_>) -> core::fmt::Result {
283 //Unwind the other case and fold it into known codes.
284 let me: c_int = (*self).into();
285 let reform = Self::from(me);
286 //Debug fmt it.
287 Debug::fmt(&reform, f)
288 }
289}
290
291//we have to implement this because the OTHER case may shadow an actual error code.
292impl PartialEq for JvmtiError {
293 fn eq(&self, other: &Self) -> bool {
294 let me: c_int = (*self).into();
295 let other: c_int = (*other).into();
296 me == other
297 }
298}
299
300//we have to implement this because the OTHER case may shadow an actual error code.
301impl Ord for JvmtiError {
302 fn cmp(&self, other: &Self) -> Ordering {
303 let me: c_int = (*self).into();
304 let other: c_int = (*other).into();
305 c_int::cmp(&me, &other)
306 }
307}
308
309impl PartialOrd for JvmtiError {
310 fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
311 Some(self.cmp(other))
312 }
313}
314
315//we have to implement this because the OTHER case may shadow an actual error code.
316impl Hash for JvmtiError {
317 fn hash<H: Hasher>(&self, state: &mut H) {
318 let me: c_int = (*self).into();
319 state.write_i64(i64::from(me));
320 }
321}
322
323impl From<c_int> for JvmtiError {
324 fn from(value: c_int) -> Self {
325 Self::from_raw(value)
326 }
327}
328
329impl From<&JvmtiError> for c_int {
330 fn from(value: &JvmtiError) -> Self {
331 (*value).into()
332 }
333}
334
335impl From<JvmtiError> for c_int {
336 fn from(value: JvmtiError) -> Self {
337 JvmtiError::into_raw(value)
338 }
339}
340
341impl JvmtiError {
342 /// Const implementation of `From<c_int>`
343 #[must_use]
344 pub const fn from_raw(raw: c_int) -> Self {
345 match raw {
346 0 => Self::NONE,
347 10 => Self::INVALID_THREAD,
348 11 => Self::INVALID_THREAD_GROUP,
349 12 => Self::INVALID_PRIORITY,
350 13 => Self::THREAD_NOT_SUSPENDED,
351 14 => Self::THREAD_SUSPENDED,
352 15 => Self::THREAD_NOT_ALIVE,
353 20 => Self::INVALID_OBJECT,
354 21 => Self::INVALID_CLASS,
355 22 => Self::CLASS_NOT_PREPARED,
356 23 => Self::INVALID_METHODID,
357 24 => Self::INVALID_LOCATION,
358 25 => Self::INVALID_FIELDID,
359 26 => Self::INVALID_MODULE,
360 31 => Self::NO_MORE_FRAMES,
361 32 => Self::OPAQUE_FRAME,
362 34 => Self::TYPE_MISMATCH,
363 35 => Self::INVALID_SLOT,
364 40 => Self::DUPLICATE,
365 41 => Self::NOT_FOUND,
366 50 => Self::INVALID_MONITOR,
367 51 => Self::NOT_MONITOR_OWNER,
368 52 => Self::INTERRUPT,
369 60 => Self::INVALID_CLASS_FORMAT,
370 61 => Self::CIRCULAR_CLASS_DEFINITION,
371 62 => Self::FAILS_VERIFICATION,
372 63 => Self::UNSUPPORTED_REDEFINITION_METHOD_ADDED,
373 64 => Self::UNSUPPORTED_REDEFINITION_SCHEMA_CHANGED,
374 65 => Self::INVALID_TYPESTATE,
375 66 => Self::UNSUPPORTED_REDEFINITION_HIERARCHY_CHANGED,
376 67 => Self::UNSUPPORTED_REDEFINITION_METHOD_DELETED,
377 68 => Self::UNSUPPORTED_VERSION,
378 69 => Self::NAMES_DONT_MATCH,
379 70 => Self::UNSUPPORTED_REDEFINITION_CLASS_MODIFIERS_CHANGED,
380 71 => Self::UNSUPPORTED_REDEFINITION_METHOD_MODIFIERS_CHANGED,
381 72 => Self::UNSUPPORTED_REDEFINITION_CLASS_ATTRIBUTE_CHANGED,
382 73 => Self::UNSUPPORTED_OPERATION,
383 79 => Self::UNMODIFIABLE_CLASS,
384 80 => Self::UNMODIFIABLE_MODULE,
385 98 => Self::NOT_AVAILABLE,
386 99 => Self::MUST_POSSESS_CAPABILITY,
387 100 => Self::NULL_POINTER,
388 101 => Self::ABSENT_INFORMATION,
389 102 => Self::INVALID_EVENT_TYPE,
390 103 => Self::ILLEGAL_ARGUMENT,
391 104 => Self::NATIVE_METHOD,
392 106 => Self::CLASS_LOADER_UNSUPPORTED,
393 110 => Self::OUT_OF_MEMORY,
394 111 => Self::ACCESS_DENIED,
395 112 => Self::WRONG_PHASE,
396 113 => Self::INTERNAL,
397 115 => Self::UNATTACHED_THREAD,
398 116 => Self::INVALID_ENVIRONMENT,
399 other => Self::OTHER(other),
400 }
401 }
402
403 /// Const implementation of `Into<c_int>`
404 #[must_use]
405 pub const fn into_raw(self) -> c_int {
406 match self {
407 Self::NONE => 0,
408 Self::INVALID_THREAD => 10,
409 Self::INVALID_THREAD_GROUP => 11,
410 Self::INVALID_PRIORITY => 12,
411 Self::THREAD_NOT_SUSPENDED => 13,
412 Self::THREAD_SUSPENDED => 14,
413 Self::THREAD_NOT_ALIVE => 15,
414 Self::INVALID_OBJECT => 20,
415 Self::INVALID_CLASS => 21,
416 Self::CLASS_NOT_PREPARED => 22,
417 Self::INVALID_METHODID => 23,
418 Self::INVALID_LOCATION => 24,
419 Self::INVALID_FIELDID => 25,
420 Self::INVALID_MODULE => 26,
421 Self::NO_MORE_FRAMES => 31,
422 Self::OPAQUE_FRAME => 32,
423 Self::TYPE_MISMATCH => 34,
424 Self::INVALID_SLOT => 35,
425 Self::DUPLICATE => 40,
426 Self::NOT_FOUND => 41,
427 Self::INVALID_MONITOR => 50,
428 Self::NOT_MONITOR_OWNER => 51,
429 Self::INTERRUPT => 52,
430 Self::INVALID_CLASS_FORMAT => 60,
431 Self::CIRCULAR_CLASS_DEFINITION => 61,
432 Self::FAILS_VERIFICATION => 62,
433 Self::UNSUPPORTED_REDEFINITION_METHOD_ADDED => 63,
434 Self::UNSUPPORTED_REDEFINITION_SCHEMA_CHANGED => 64,
435 Self::INVALID_TYPESTATE => 65,
436 Self::UNSUPPORTED_REDEFINITION_HIERARCHY_CHANGED => 66,
437 Self::UNSUPPORTED_REDEFINITION_METHOD_DELETED => 67,
438 Self::UNSUPPORTED_VERSION => 68,
439 Self::NAMES_DONT_MATCH => 69,
440 Self::UNSUPPORTED_REDEFINITION_CLASS_MODIFIERS_CHANGED => 70,
441 Self::UNSUPPORTED_REDEFINITION_METHOD_MODIFIERS_CHANGED => 71,
442 Self::UNSUPPORTED_REDEFINITION_CLASS_ATTRIBUTE_CHANGED => 72,
443 Self::UNSUPPORTED_OPERATION => 73,
444 Self::UNMODIFIABLE_CLASS => 79,
445 Self::UNMODIFIABLE_MODULE => 80,
446 Self::NOT_AVAILABLE => 98,
447 Self::MUST_POSSESS_CAPABILITY => 99,
448 Self::NULL_POINTER => 100,
449 Self::ABSENT_INFORMATION => 101,
450 Self::INVALID_EVENT_TYPE => 102,
451 Self::ILLEGAL_ARGUMENT => 103,
452 Self::NATIVE_METHOD => 104,
453 Self::CLASS_LOADER_UNSUPPORTED => 106,
454 Self::OUT_OF_MEMORY => 110,
455 Self::ACCESS_DENIED => 111,
456 Self::WRONG_PHASE => 112,
457 Self::INTERNAL => 113,
458 Self::UNATTACHED_THREAD => 115,
459 Self::INVALID_ENVIRONMENT => 116,
460 Self::OTHER(value) => value,
461 }
462 }
463
464 /// Returns true if this `JvmtiError` refers to `JVMTI_ERROR_NONE`
465 #[must_use]
466 pub const fn is_ok(&self) -> bool {
467 matches!(self, Self::NONE)
468 }
469
470 /// Returns true if this `JvmtiError` does not refer to `JVMTI_ERROR_NONE`
471 #[must_use]
472 pub const fn is_err(&self) -> bool {
473 !self.is_ok()
474 }
475
476 /// Returns `Ok(())` if self is `JVMTI_ERROR_NONE` otherwise returns `Err(self)`
477 ///
478 /// # Errors
479 /// if self is not `JVMTI_ERROR_NONE`
480 pub const fn into_result(self) -> Result<(), Self> {
481 if self.is_ok() {
482 return Ok(());
483 }
484
485 Err(self)
486 }
487}
488
489//We cannot turn this into an enum because the JVM may with a reasonable likelihood decide to add new codes in the future.
490//If we enum this and the VM returned a code we don't know it would instantly be UB.
491#[repr(transparent)]
492#[derive(Debug, Ord, Eq, PartialOrd, PartialEq, Hash, Clone, Copy)]
493#[must_use]
494pub struct jvmtiError(pub c_int);
495
496impl Display for jvmtiError {
497 fn fmt(&self, f: &mut Formatter<'_>) -> core::fmt::Result {
498 let display_var = JvmtiError::from(self.0);
499 Display::fmt(&display_var, f)
500 }
501}
502
503impl From<c_int> for jvmtiError {
504 fn from(value: c_int) -> Self {
505 Self(value)
506 }
507}
508
509impl From<jvmtiError> for c_int {
510 fn from(value: jvmtiError) -> Self {
511 value.0
512 }
513}
514
515impl From<&jvmtiError> for c_int {
516 fn from(value: &jvmtiError) -> Self {
517 value.0
518 }
519}
520
521impl From<JvmtiError> for jvmtiError {
522 fn from(value: JvmtiError) -> Self {
523 let me: c_int = value.into();
524 me.into()
525 }
526}
527
528impl From<jvmtiError> for JvmtiError {
529 fn from(value: jvmtiError) -> Self {
530 let me: c_int = value.into();
531 me.into()
532 }
533}
534
535impl jvmtiError {
536 #[must_use]
537 pub const fn is_ok(self) -> bool {
538 self.0 == JVMTI_ERROR_NONE.0
539 }
540
541 #[must_use]
542 pub const fn is_err(self) -> bool {
543 self.0 != JVMTI_ERROR_NONE.0
544 }
545
546 /// This function transforms the jvmtiError into a Result if the jvmtiError is not `JVMTI_ERROR_NONE`.
547 /// Its useful if you want to use the "if let" pattern.
548 ///
549 /// # Errors
550 /// if jvmtiError is not equal to `JVMTI_ERROR_NONE`
551 ///
552 /// # Example
553 /// ```rust
554 /// use jni_simple::{jint, JVMTIEnv, JVMTI_VERSION_21};
555 ///
556 /// fn check_version21(env: JVMTIEnv) {
557 /// unsafe {
558 /// let mut version: jint = 0;
559 /// if let Err(err) = env.GetVersionNumber(&mut version).into_result() {
560 /// //Handle failed jvmti call
561 /// //You can also match on err here if you want.
562 /// panic!("GetVersionNumber call failed with err={err}")
563 /// }
564 ///
565 /// //Handle successful jvmti call
566 /// if version != JVMTI_VERSION_21 {
567 /// panic!("JVMTI Version is not 21");
568 /// }
569 /// }
570 /// }
571 ///
572 /// ```
573 ///
574 pub const fn into_result(self) -> Result<(), JvmtiError> {
575 if self.is_ok() {
576 return Ok(());
577 }
578
579 Err(JvmtiError::from_raw(self.0))
580 }
581
582 /// This function will return if self is `JVMTI_ERROR_NONE` otherwise
583 /// it will panic with the given message as well as the value of self.
584 ///
585 /// This method will attempt to resolve self to a known constant and print the name
586 /// of the constant in the panic message if at all possible. If self is not a known
587 /// constant the numeric value of self will be contained in the panic message.
588 ///
589 /// # Panics
590 /// if self is not `JVMTI_ERROR_NONE`
591 ///
592 pub fn expect(self, msg: &str) {
593 self.into_result().expect(msg);
594 }
595
596 /// This function transforms the jvmtiError into a rust enum that you can easily match on.
597 ///
598 /// # Example
599 /// ```rust
600 /// use jni_simple::{jint, JVMTIEnv, JvmtiError, JVMTI_VERSION_21};
601 ///
602 /// fn check_version21(env: JVMTIEnv) {
603 /// unsafe {
604 /// let mut version: jint = 0;
605 /// match env.GetVersionNumber(&mut version).into_enum() {
606 /// JvmtiError::NONE => {
607 /// //Handle successful jvmti call
608 /// if version != JVMTI_VERSION_21 {
609 /// panic!("JVMTI Version is not 21");
610 /// }
611 /// }
612 /// err => {
613 /// panic!("GetVersionNumber call failed with err={err}")
614 /// }
615 /// }
616 /// }
617 /// }
618 ///
619 /// ```
620 ///
621 #[must_use]
622 pub const fn into_enum(self) -> JvmtiError {
623 JvmtiError::from_raw(self.0)
624 }
625
626 /// This function transforms the jvmtiError back into its raw magic number from the jvm.
627 /// This is useful if you deal with undocumented errors from customized jvm's.
628 ///
629 /// # Example
630 /// ```rust
631 /// use std::ffi::c_int;
632 /// use jni_simple::{jint, JVMTIEnv, JvmtiError, JVMTI_VERSION_21};
633 ///
634 /// fn check_version21(env: JVMTIEnv) {
635 /// unsafe {
636 /// let mut version: jint = 0;
637 /// let raw_err : c_int = env.GetVersionNumber(&mut version).into_raw();
638 /// match raw_err {
639 /// 0 => {
640 /// //Handle successful jvmti call
641 /// if version != JVMTI_VERSION_21 {
642 /// panic!("JVMTI Version is not 21");
643 /// }
644 /// }
645 /// err => {
646 /// panic!("GetVersionNumber call failed with magic number err={err}")
647 /// }
648 /// }
649 /// }
650 /// }
651 ///
652 /// ```
653 ///
654 #[must_use]
655 pub const fn into_raw(self) -> c_int {
656 self.0
657 }
658}
659
660pub const JVMTI_ERROR_NONE: jvmtiError = jvmtiError(0);
661pub const JVMTI_ERROR_INVALID_THREAD: jvmtiError = jvmtiError(10);
662pub const JVMTI_ERROR_INVALID_THREAD_GROUP: jvmtiError = jvmtiError(11);
663pub const JVMTI_ERROR_INVALID_PRIORITY: jvmtiError = jvmtiError(12);
664pub const JVMTI_ERROR_THREAD_NOT_SUSPENDED: jvmtiError = jvmtiError(13);
665pub const JVMTI_ERROR_THREAD_SUSPENDED: jvmtiError = jvmtiError(14);
666pub const JVMTI_ERROR_THREAD_NOT_ALIVE: jvmtiError = jvmtiError(15);
667pub const JVMTI_ERROR_INVALID_OBJECT: jvmtiError = jvmtiError(20);
668pub const JVMTI_ERROR_INVALID_CLASS: jvmtiError = jvmtiError(21);
669pub const JVMTI_ERROR_CLASS_NOT_PREPARED: jvmtiError = jvmtiError(22);
670pub const JVMTI_ERROR_INVALID_METHODID: jvmtiError = jvmtiError(23);
671pub const JVMTI_ERROR_INVALID_LOCATION: jvmtiError = jvmtiError(24);
672pub const JVMTI_ERROR_INVALID_FIELDID: jvmtiError = jvmtiError(25);
673pub const JVMTI_ERROR_INVALID_MODULE: jvmtiError = jvmtiError(26);
674pub const JVMTI_ERROR_NO_MORE_FRAMES: jvmtiError = jvmtiError(31);
675pub const JVMTI_ERROR_OPAQUE_FRAME: jvmtiError = jvmtiError(32);
676pub const JVMTI_ERROR_TYPE_MISMATCH: jvmtiError = jvmtiError(34);
677pub const JVMTI_ERROR_INVALID_SLOT: jvmtiError = jvmtiError(35);
678pub const JVMTI_ERROR_DUPLICATE: jvmtiError = jvmtiError(40);
679pub const JVMTI_ERROR_NOT_FOUND: jvmtiError = jvmtiError(41);
680pub const JVMTI_ERROR_INVALID_MONITOR: jvmtiError = jvmtiError(50);
681pub const JVMTI_ERROR_NOT_MONITOR_OWNER: jvmtiError = jvmtiError(51);
682pub const JVMTI_ERROR_INTERRUPT: jvmtiError = jvmtiError(52);
683pub const JVMTI_ERROR_INVALID_CLASS_FORMAT: jvmtiError = jvmtiError(60);
684pub const JVMTI_ERROR_CIRCULAR_CLASS_DEFINITION: jvmtiError = jvmtiError(61);
685pub const JVMTI_ERROR_FAILS_VERIFICATION: jvmtiError = jvmtiError(62);
686pub const JVMTI_ERROR_UNSUPPORTED_REDEFINITION_METHOD_ADDED: jvmtiError = jvmtiError(63);
687pub const JVMTI_ERROR_UNSUPPORTED_REDEFINITION_SCHEMA_CHANGED: jvmtiError = jvmtiError(64);
688pub const JVMTI_ERROR_INVALID_TYPESTATE: jvmtiError = jvmtiError(65);
689pub const JVMTI_ERROR_UNSUPPORTED_REDEFINITION_HIERARCHY_CHANGED: jvmtiError = jvmtiError(66);
690pub const JVMTI_ERROR_UNSUPPORTED_REDEFINITION_METHOD_DELETED: jvmtiError = jvmtiError(67);
691pub const JVMTI_ERROR_UNSUPPORTED_VERSION: jvmtiError = jvmtiError(68);
692pub const JVMTI_ERROR_NAMES_DONT_MATCH: jvmtiError = jvmtiError(69);
693pub const JVMTI_ERROR_UNSUPPORTED_REDEFINITION_CLASS_MODIFIERS_CHANGED: jvmtiError = jvmtiError(70);
694pub const JVMTI_ERROR_UNSUPPORTED_REDEFINITION_METHOD_MODIFIERS_CHANGED: jvmtiError = jvmtiError(71);
695pub const JVMTI_ERROR_UNSUPPORTED_REDEFINITION_CLASS_ATTRIBUTE_CHANGED: jvmtiError = jvmtiError(72);
696pub const JVMTI_ERROR_UNSUPPORTED_OPERATION: jvmtiError = jvmtiError(73);
697pub const JVMTI_ERROR_UNMODIFIABLE_CLASS: jvmtiError = jvmtiError(79);
698pub const JVMTI_ERROR_UNMODIFIABLE_MODULE: jvmtiError = jvmtiError(80);
699pub const JVMTI_ERROR_NOT_AVAILABLE: jvmtiError = jvmtiError(98);
700pub const JVMTI_ERROR_MUST_POSSESS_CAPABILITY: jvmtiError = jvmtiError(99);
701pub const JVMTI_ERROR_NULL_POINTER: jvmtiError = jvmtiError(100);
702pub const JVMTI_ERROR_ABSENT_INFORMATION: jvmtiError = jvmtiError(101);
703pub const JVMTI_ERROR_INVALID_EVENT_TYPE: jvmtiError = jvmtiError(102);
704pub const JVMTI_ERROR_ILLEGAL_ARGUMENT: jvmtiError = jvmtiError(103);
705pub const JVMTI_ERROR_NATIVE_METHOD: jvmtiError = jvmtiError(104);
706pub const JVMTI_ERROR_CLASS_LOADER_UNSUPPORTED: jvmtiError = jvmtiError(106);
707pub const JVMTI_ERROR_OUT_OF_MEMORY: jvmtiError = jvmtiError(110);
708pub const JVMTI_ERROR_ACCESS_DENIED: jvmtiError = jvmtiError(111);
709pub const JVMTI_ERROR_WRONG_PHASE: jvmtiError = jvmtiError(112);
710pub const JVMTI_ERROR_INTERNAL: jvmtiError = jvmtiError(113);
711pub const JVMTI_ERROR_UNATTACHED_THREAD: jvmtiError = jvmtiError(115);
712pub const JVMTI_ERROR_INVALID_ENVIRONMENT: jvmtiError = jvmtiError(116);
713pub const JVMTI_ERROR_MAX: jvmtiError = jvmtiError(116);
714
715/////////////////////////////////////////////////////////////////////
716///Thread is alive. Zero if thread is new (not started) or terminated.
717pub const JVMTI_THREAD_STATE_ALIVE: jint = 0x0001;
718
719/// Thread has completed execution.
720pub const JVMTI_THREAD_STATE_TERMINATED: jint = 0x0002;
721
722/// Thread is runnable.
723pub const JVMTI_THREAD_STATE_RUNNABLE: jint = 0x0004;
724
725/// Thread is waiting to enter a synchronized block/method or, after an `Object.wait()`, waiting to re-enter a synchronized block/method.
726pub const JVMTI_THREAD_STATE_BLOCKED_ON_MONITOR_ENTER: jint = 0x0400;
727
728/// Thread is waiting.
729pub const JVMTI_THREAD_STATE_WAITING: jint = 0x0080;
730
731/// Thread is waiting without a timeout. For example, `Object.wait()`.
732pub const JVMTI_THREAD_STATE_WAITING_INDEFINITELY: jint = 0x0010;
733
734/// Thread is waiting with a maximum time to wait specified. For example, Object.wait(long).
735pub const JVMTI_THREAD_STATE_WAITING_WITH_TIMEOUT: jint = 0x0020;
736
737/// Thread is sleeping -- Thread.sleep.
738pub const JVMTI_THREAD_STATE_SLEEPING: jint = 0x0040;
739
740/// Thread is waiting on an object monitor -- Object.wait.
741pub const JVMTI_THREAD_STATE_IN_OBJECT_WAIT: jint = 0x0100;
742
743/// Thread is parked, for example: LockSupport.park, LockSupport.parkUtil and LockSupport.parkNanos. A virtual thread that is sleeping, in Thread.sleep, may have this state flag set instead of `JVMTI_THREAD_STATE_SLEEPING`.
744pub const JVMTI_THREAD_STATE_PARKED: jint = 0x0200;
745
746/// Thread is suspended by a suspend function (such as `SuspendThread`). If this bit is set, the other bits refer to the thread state before suspension.
747pub const JVMTI_THREAD_STATE_SUSPENDED: jint = 0x0010_0000;
748
749/// Thread has been interrupted.
750pub const JVMTI_THREAD_STATE_INTERRUPTED: jint = 0x0020_0000;
751
752/// Thread is in native code--that is, a native method is running which has not called back into the VM or Java programming language code.
753///
754/// This flag is not set when running VM compiled Java programming language code nor is it set when running VM code or VM support code.
755///
756/// Native VM interface functions, such as JNI and JVM TI functions, may be implemented as VM code.
757pub const JVMTI_THREAD_STATE_IN_NATIVE: jint = 0x0040_0000;
758
759/// Defined by VM vendor.
760pub const JVMTI_THREAD_STATE_VENDOR_1: jint = 0x1000_0000;
761
762/// Defined by VM vendor.
763pub const JVMTI_THREAD_STATE_VENDOR_2: jint = 0x2000_0000;
764
765/// Defined by VM vendor.
766pub const JVMTI_THREAD_STATE_VENDOR_3: jint = 0x4000_0000;
767
768/// Mod for private trait seals that should be hidden.
769mod private {
770 use crate::{jboolean, jrawMonitorID};
771 use core::ffi::{c_char, c_void};
772
773 /// Trait seal for `AsJrawMonitorID`
774 pub trait SealedAsJrawMonitorID {
775 /// Gets the underlying `jrawMonitorID`
776 fn jraw_monitor_id(self) -> jrawMonitorID;
777 }
778
779 /// Trait seal for `JrawMonitorIDReceiver`
780 pub trait SealedReceiveJrawMonitorID {
781 /// Can the arg produce a pointer that can be directly passed to jvmti?
782 fn is_direct() -> bool;
783
784 /// Get the raw pointer to pass directly to jvmti.
785 fn direct_arg(self) -> *mut jrawMonitorID;
786
787 /// Store the newly created `jrawMonitorID`
788 fn receive(self, monitor: jrawMonitorID);
789 }
790
791 ///Trait seal for `AsJNILinkage`
792 pub trait SealedAsJNILinkage {
793 /// Returns the jni linkage index.
794 fn linkage(self) -> usize;
795 }
796
797 /// Trait seal for `JBooleanMutPtr`
798 pub trait SealedJBooleanMutPtr {
799 /// Call the closure with a *mut jboolean pointer that is valid for at least the duration of the call.
800 fn use_jboolean_mut<R>(self, func: impl FnOnce(*mut jboolean) -> R) -> R;
801 }
802
803 /// Trait seal for `JBooleanInputLayout`
804 pub trait SealedJBooleanInputLayout {}
805
806 /// Trait seal for `JType`
807 pub trait SealedJType {}
808
809 /// Trait Seal for `UseCString`
810 pub trait SealedUseCString {
811 /// Transform the string into a zero terminated string if necessary and calls the closure with it.
812 /// The pointer passed into the closure only stays valid until the closure returns.
813 /// The string is guaranteed to be 0 terminated!
814 /// The string is not guaranteed to be valid utf-8, but it can generally be assumed to be utf-8!
815 ///
816 /// # Undefined Behavior
817 /// If called on a raw pointer type that is not in fact 0 terminated.
818 /// Yes I am aware that is should make this fn unsafe because of this.
819 /// I choose not to do so because it doesnt apply for 90% of the implementations of this trait.
820 ///
821 /// # Panics
822 /// panics if asserts feature is enabled and the implementation is capable of detecting that the string is not utf-8.
823 /// This check is only relevant for types that do not do conversion to utf-8 by default (such as `OsString` and friends)
824 ///
825 fn use_as_const_c_char<X>(self, param: impl FnOnce(*const c_char) -> X) -> X;
826 }
827
828 #[test]
829 #[cfg(feature = "std")]
830 pub fn testSealedUseCString() {
831 use std::ffi::{CStr, OsString};
832
833 unsafe {
834 assert!([].use_as_const_c_char(|ptr| CStr::from_ptr(ptr).to_bytes().is_empty()));
835 assert!([0u8].use_as_const_c_char(|ptr| CStr::from_ptr(ptr).to_bytes().is_empty()));
836 assert!("".use_as_const_c_char(|ptr| CStr::from_ptr(ptr).to_bytes().is_empty()));
837 assert!("abc".use_as_const_c_char(|ptr| CStr::from_ptr(ptr).to_bytes() == [b'a', b'b', b'c']));
838 assert!([b'a', b'b', 0, b'c'].use_as_const_c_char(|ptr| CStr::from_ptr(ptr).to_bytes() == [b'a', b'b']));
839 assert!("abc\0".use_as_const_c_char(|ptr| CStr::from_ptr(ptr).to_bytes() == [b'a', b'b', b'c']));
840 assert!(OsString::from("abc").use_as_const_c_char(|ptr| CStr::from_ptr(ptr).to_bytes() == [b'a', b'b', b'c']));
841
842 #[cfg(feature = "asserts")]
843 {
844 let r = std::panic::catch_unwind(|| [0b1011_1111, b'A', b'B'].as_slice().use_as_const_c_char(|_| std::process::abort()));
845 assert!(r.is_err());
846 }
847 }
848 }
849
850 /// Sealed trait for the Env Vtable receiver so we can check if the receiver is correct if asssertions are correct.
851 pub trait SealedEnvVTable: From<*mut c_void> {
852 /// can this receiver get the JNI function table?
853 fn can_jni() -> bool;
854
855 /// can this receiver get the JVMTI function table?
856 fn can_jvmti() -> bool;
857 }
858
859 impl SealedEnvVTable for *mut c_void {
860 fn can_jni() -> bool {
861 true
862 }
863
864 fn can_jvmti() -> bool {
865 true
866 }
867 }
868}
869
870pub type jweak = jobject;
871
872pub type jthrowable = jobject;
873
874pub type jthread = jobject;
875
876pub type jthreadGroup = jobject;
877
878pub type jmethodID = jobject;
879pub type jfieldID = jobject;
880
881///
882/// Marker trait for all types that are valid to use to make variadic JNI Up-calls with.
883///
884pub trait JType: private::SealedJType + Into<jtype> + Clone + Copy {
885 ///
886 /// Returns a single character that equals the type's JNI signature.
887 ///
888 /// Boolean -> Z
889 /// Byte -> B
890 /// Short -> S
891 /// Char -> C
892 /// Int -> I
893 /// Long -> J
894 /// Float -> F
895 /// Double -> D
896 /// any java.lang.Object -> L
897 ///
898 ///
899 fn jtype_id() -> char;
900}
901impl private::SealedJType for jobject {}
902impl JType for jobject {
903 #[inline(always)]
904 fn jtype_id() -> char {
905 'L'
906 }
907}
908impl private::SealedJType for jboolean {}
909impl JType for jboolean {
910 #[inline(always)]
911 fn jtype_id() -> char {
912 'Z'
913 }
914}
915impl private::SealedJType for jbyte {}
916impl JType for jbyte {
917 #[inline(always)]
918 fn jtype_id() -> char {
919 'B'
920 }
921}
922impl private::SealedJType for jshort {}
923impl JType for jshort {
924 #[inline(always)]
925 fn jtype_id() -> char {
926 'S'
927 }
928}
929impl private::SealedJType for jchar {}
930impl JType for jchar {
931 #[inline(always)]
932 fn jtype_id() -> char {
933 'C'
934 }
935}
936impl private::SealedJType for jint {}
937impl JType for jint {
938 #[inline(always)]
939 fn jtype_id() -> char {
940 'I'
941 }
942}
943impl private::SealedJType for jlong {}
944impl JType for jlong {
945 #[inline(always)]
946 fn jtype_id() -> char {
947 'J'
948 }
949}
950impl private::SealedJType for jfloat {}
951impl JType for jfloat {
952 #[inline(always)]
953 fn jtype_id() -> char {
954 'F'
955 }
956}
957impl private::SealedJType for jdouble {}
958impl JType for jdouble {
959 #[inline(always)]
960 fn jtype_id() -> char {
961 'D'
962 }
963}
964
965#[repr(C)]
966#[derive(Clone, Copy)]
967#[allow(clippy::missing_docs_in_private_items)]
968pub union jtype {
969 long: jlong,
970 int: jint,
971 short: jshort,
972 char: jchar,
973 byte: jbyte,
974 boolean: jboolean,
975 float: jfloat,
976 double: jdouble,
977 object: jobject,
978 class: jclass,
979 throwable: jthrowable,
980}
981
982pub type jvalue = jtype;
983
984pub type jrawMonitorID = *mut jrawMonitorIDType;
985
986pub type jrawMonitorIDType = c_void;
987
988pub trait AsJrawMonitorID: private::SealedAsJrawMonitorID {}
989
990pub trait ReceiveJrawMonitorID: private::SealedReceiveJrawMonitorID {}
991
992impl private::SealedAsJrawMonitorID for jrawMonitorID {
993 fn jraw_monitor_id(self) -> jrawMonitorID {
994 self
995 }
996}
997impl AsJrawMonitorID for jrawMonitorID {}
998
999impl private::SealedAsJrawMonitorID for &core::sync::atomic::AtomicPtr<jrawMonitorIDType> {
1000 fn jraw_monitor_id(self) -> jrawMonitorID {
1001 self.load(SeqCst)
1002 }
1003}
1004impl AsJrawMonitorID for &core::sync::atomic::AtomicPtr<jrawMonitorIDType> {}
1005
1006impl private::SealedReceiveJrawMonitorID for &mut jrawMonitorID {
1007 fn is_direct() -> bool {
1008 false
1009 }
1010
1011 fn direct_arg(self) -> *mut jrawMonitorID {
1012 unreachable!()
1013 }
1014 fn receive(self, monitor: jrawMonitorID) {
1015 *self = monitor;
1016 }
1017}
1018
1019impl ReceiveJrawMonitorID for &mut jrawMonitorID {}
1020
1021impl private::SealedReceiveJrawMonitorID for &core::sync::atomic::AtomicPtr<jrawMonitorIDType> {
1022 fn is_direct() -> bool {
1023 false
1024 }
1025
1026 fn direct_arg(self) -> *mut jrawMonitorID {
1027 unreachable!()
1028 }
1029
1030 fn receive(self, monitor: jrawMonitorID) {
1031 self.store(monitor, SeqCst);
1032 }
1033}
1034
1035impl ReceiveJrawMonitorID for &core::sync::atomic::AtomicPtr<jrawMonitorIDType> {}
1036
1037impl private::SealedReceiveJrawMonitorID for *mut jrawMonitorID {
1038 fn is_direct() -> bool {
1039 true
1040 }
1041
1042 fn direct_arg(self) -> *mut jrawMonitorID {
1043 self
1044 }
1045
1046 fn receive(self, _monitor: jrawMonitorID) {
1047 unreachable!()
1048 }
1049}
1050
1051impl ReceiveJrawMonitorID for *mut jrawMonitorID {}
1052
1053///
1054/// This macro is usefull for constructing jtype arrays.
1055/// This is often needed when making upcalls into the jvm with many arguments using the 'A' type functions:
1056/// * CallStatic(TYPE)MethodA
1057/// * `CallStaticVoidMethodA`
1058/// * `CallStaticIntMethodA`
1059/// * ...
1060/// * Call(TYPE)MethodA
1061/// * `CallVoidMethodA`
1062/// * ...
1063/// * `NewObjectA`
1064///
1065/// # Example
1066/// ```rust
1067/// use jni_simple::{*};
1068///
1069/// unsafe fn test(env: JNIEnv, class: jclass) {
1070/// //public static void methodWith5Params(int a, int b, long c, long d, boolean e) {}
1071/// let meth = env.GetStaticMethodID(class, "methodWith5Params", "(IIJJZ)V");
1072/// if meth.is_null() {
1073/// unimplemented!("handle method not found");
1074/// }
1075/// // methodWith5Params(16, 32, 12, 13, false);
1076/// env.CallStaticVoidMethodA(class, meth, jtypes!(16i32, 64i32, 12i64, 13i64, false).as_ptr());
1077/// }
1078/// ```
1079///
1080#[macro_export]
1081macro_rules! jtypes {
1082 ( $($x:expr),* ) => {
1083 {
1084 [ $(jtype::from($x)),* ]
1085 }
1086 };
1087}
1088
1089impl Debug for jtype {
1090 fn fmt(&self, f: &mut Formatter<'_>) -> core::fmt::Result {
1091 //Call jtype::debug if more information is desired.
1092 f.write_str("jtype")
1093 }
1094}
1095
1096impl jtype {
1097 ///
1098 /// Helper function to "create" a jtype with a null jobject.
1099 ///
1100 /// This function is guaranteed to fully initialize all unused bits of the union to 0.
1101 ///
1102 #[inline(always)]
1103 #[must_use]
1104 pub const fn null() -> Self {
1105 #[cfg(target_pointer_width = "32")]
1106 {
1107 let mut jt = jtype { long: 0 };
1108 jt.object = null_mut();
1109 jt
1110 }
1111 #[cfg(target_pointer_width = "64")]
1112 {
1113 jtype { object: null_mut() }
1114 }
1115 }
1116
1117 /// read this jtype as jlong
1118 /// # Safety
1119 /// only safe if jtype was a jlong.
1120 #[inline(always)]
1121 #[must_use]
1122 pub const unsafe fn long(&self) -> jlong {
1123 unsafe { self.long }
1124 }
1125
1126 /// read this jtype as jint
1127 /// # Safety
1128 /// only safe if jtype was a jint.
1129 #[inline(always)]
1130 #[must_use]
1131 pub const unsafe fn int(&self) -> jint {
1132 unsafe { self.int }
1133 }
1134
1135 /// read this jtype as jshort
1136 /// # Safety
1137 /// only safe if jtype was a jshort.
1138 #[inline(always)]
1139 #[must_use]
1140 pub const unsafe fn short(&self) -> jshort {
1141 unsafe { self.short }
1142 }
1143
1144 /// read this jtype as jchar
1145 /// # Safety
1146 /// only safe if jtype was a jchar.
1147 #[inline(always)]
1148 #[must_use]
1149 pub const unsafe fn char(&self) -> jchar {
1150 unsafe { self.char }
1151 }
1152
1153 /// read this jtype as jbyte
1154 /// # Safety
1155 /// only safe if jtype was a jbyte.
1156 #[inline(always)]
1157 #[must_use]
1158 pub const unsafe fn byte(&self) -> jbyte {
1159 unsafe { self.byte }
1160 }
1161
1162 /// read this jtype as jboolean
1163 /// # Safety
1164 /// only safe if jtype was a jboolean.
1165 #[inline(always)]
1166 #[must_use]
1167 pub const unsafe fn boolean(&self) -> jboolean {
1168 unsafe { self.boolean }
1169 }
1170
1171 /// read this jtype as jboolean
1172 /// # Safety
1173 /// only safe if jtype was a jboolean.
1174 #[inline(always)]
1175 #[must_use]
1176 pub const unsafe fn bool(&self) -> bool {
1177 unsafe { self.boolean.as_bool() }
1178 }
1179
1180 /// read this jtype as jfloat
1181 /// # Safety
1182 /// only safe if jtype was a jfloat.
1183 #[inline(always)]
1184 #[must_use]
1185 pub const unsafe fn float(&self) -> jfloat {
1186 unsafe { self.float }
1187 }
1188
1189 /// read this jtype as jdouble
1190 /// # Safety
1191 /// only safe if jtype was a jdouble.
1192 #[inline(always)]
1193 #[must_use]
1194 pub const unsafe fn double(&self) -> jdouble {
1195 unsafe { self.double }
1196 }
1197
1198 /// read this jtype as jobject
1199 /// # Safety
1200 /// only safe if jtype was a jobject.
1201 #[inline(always)]
1202 #[must_use]
1203 pub const unsafe fn object(&self) -> jobject {
1204 unsafe { self.object }
1205 }
1206
1207 /// read this jtype as jclass
1208 /// # Safety
1209 /// only safe if jtype was a jclass.
1210 #[inline(always)]
1211 #[must_use]
1212 pub const unsafe fn class(&self) -> jclass {
1213 unsafe { self.class }
1214 }
1215
1216 /// read this jtype as jthrowable
1217 /// # Safety
1218 /// only safe if jtype was a jthrowable.
1219 #[inline(always)]
1220 #[must_use]
1221 pub const unsafe fn throwable(&self) -> jthrowable {
1222 unsafe { self.throwable }
1223 }
1224
1225 /// Sets the jtype to a value, this is always safe.
1226 ///
1227 /// This function is guaranteed to set all bits
1228 /// of the union that are not used by the type T to 0.
1229 #[inline(always)]
1230 pub fn set<T: Into<Self>>(&mut self, value: T) {
1231 *self = value.into();
1232 }
1233
1234 /// Returns a helper struct which implements debug and reads the actual values from the jtype.
1235 ///
1236 /// This function should be avoided in productive code.
1237 ///
1238 /// # Safety
1239 /// This is always safe for all jtype values constructed in rust regardless of the union variant.
1240 ///
1241 /// This is only safe for jtype values constructed by the jvm if they were 'jdouble, jlong or on 64-bit jvm's jobject/jthrowable/jclass'.
1242 /// All the other jtype variants may cause reading of uninitialized memory
1243 /// when the `Debug::fmt` is invoked. It depends entirely on the jvm implementation
1244 /// if this is the case or not.
1245 ///
1246 /// It is impossible to get a pointer to a jtype value constructed by the jvm without using JVMTI.
1247 /// If you only use JNI then this function should always be safe since no JNI function as of java 25
1248 /// returns a jtype. Its only used as a input parameter.
1249 ///
1250 ///
1251 /// # Example
1252 /// ```rust
1253 /// use jni_simple::*;
1254 ///
1255 /// fn some_func() {
1256 /// let x : jlong = 4;
1257 /// let jt = jtype::from(x);
1258 ///
1259 /// //Safe but opaque
1260 /// assert_eq!("jtype", format!("{jt:?}").as_str());
1261 ///
1262 /// // Safe in this case because `jt` was initialized in rust and is jlong.
1263 /// assert!(format!("{:?}", unsafe { jt.debug() }).as_str().contains("long=0x4"));
1264 /// }
1265 /// ```
1266 ///
1267 #[inline(always)]
1268 #[must_use]
1269 pub const unsafe fn debug(&self) -> JTypeDebug<'_> {
1270 JTypeDebug(self)
1271 }
1272}
1273
1274impl From<jlong> for jtype {
1275 fn from(value: jlong) -> Self {
1276 jtype { long: value }
1277 }
1278}
1279
1280impl From<jobject> for jtype {
1281 #[cfg(target_pointer_width = "64")]
1282 fn from(value: jobject) -> Self {
1283 jtype { object: value }
1284 }
1285
1286 #[cfg(target_pointer_width = "32")]
1287 fn from(value: jobject) -> Self {
1288 let mut jt = jtype { long: 0 };
1289 jt.object = value;
1290 jt
1291 }
1292}
1293impl From<jint> for jtype {
1294 fn from(value: jint) -> Self {
1295 let mut jt = jtype { long: 0 };
1296 jt.int = value;
1297 jt
1298 }
1299}
1300
1301impl From<jshort> for jtype {
1302 fn from(value: jshort) -> Self {
1303 let mut jt = jtype { long: 0 };
1304 jt.short = value;
1305 jt
1306 }
1307}
1308
1309impl From<jbyte> for jtype {
1310 fn from(value: jbyte) -> Self {
1311 let mut jt = jtype { long: 0 };
1312 jt.byte = value;
1313 jt
1314 }
1315}
1316
1317impl From<jchar> for jtype {
1318 fn from(value: jchar) -> Self {
1319 let mut jt = jtype { long: 0 };
1320 jt.char = value;
1321 jt
1322 }
1323}
1324
1325impl From<jfloat> for jtype {
1326 fn from(value: jfloat) -> Self {
1327 let mut jt = jtype { long: 0 };
1328 jt.float = value;
1329 jt
1330 }
1331}
1332
1333impl From<jdouble> for jtype {
1334 fn from(value: jdouble) -> Self {
1335 jtype { double: value }
1336 }
1337}
1338impl From<jboolean> for jtype {
1339 fn from(value: jboolean) -> Self {
1340 let mut jt = jtype { long: 0 };
1341 jt.boolean = value;
1342 jt
1343 }
1344}
1345
1346impl From<bool> for jtype {
1347 fn from(value: bool) -> Self {
1348 let mut jt = jtype { long: 0 };
1349 jt.boolean = jboolean::from(value);
1350 jt
1351 }
1352}
1353
1354/// Debug helper struct that ensures that the caller understands the safety of printing/debugging the jtype.
1355/// Its impossible to construct this type without unsafe code.
1356#[repr(transparent)]
1357pub struct JTypeDebug<'a>(&'a jtype);
1358
1359impl Debug for JTypeDebug<'_> {
1360 #[inline(never)]
1361 fn fmt(&self, f: &mut Formatter<'_>) -> core::fmt::Result {
1362 // Safety:
1363 // This is safe for any jtype's we created in rust as we always fully initalize the jtype.
1364 // This is not safe for jtype pointers passed to us from jvmti as the jvm does not need to guarantee that it points
1365 // to an initialized allocation of 8 bytes. Its perfectly valid for the jvm to give us a pointer to a jbyte and cast it to jtype.
1366 // We would then read 8 bytes here, reading beyond the bytes. We mitigate this to some degree by using read_unaligned but we still might segfault here.
1367 unsafe {
1368 let long = core::ptr::read_unaligned(core::ptr::from_ref::<jlong>(&self.0.long));
1369 let int = core::ptr::read_unaligned(core::ptr::from_ref::<jint>(&self.0.int));
1370 let short = core::ptr::read_unaligned(core::ptr::from_ref::<jshort>(&self.0.short));
1371 let byte = core::ptr::read_unaligned(core::ptr::from_ref::<jbyte>(&self.0.byte));
1372 let float = core::ptr::read_unaligned(core::ptr::from_ref::<jfloat>(&self.0.float));
1373 let double = core::ptr::read_unaligned(core::ptr::from_ref::<jdouble>(&self.0.double));
1374
1375 f.write_fmt(format_args!(
1376 "jtype union[long=0x{long:x} int=0x{int:x} short=0x{short:x} byte=0x{byte:x} float={float:e} double={double:e}]"
1377 ))
1378 }
1379 }
1380}
1381
1382#[repr(C)]
1383#[derive(Debug, Copy, Clone)]
1384pub struct JNINativeMethod {
1385 /// Name of the native method
1386 name: *const c_char,
1387 /// JNI Signature of the native method
1388 signature: *const c_char,
1389 /// raw Function pointer that should be called when the native method is called.
1390 fnPtr: *const c_void,
1391}
1392
1393/// The invocation interface pointer
1394type JNIInvPtr = SyncMutPtr<*mut *mut c_void>;
1395
1396#[repr(transparent)]
1397#[derive(Debug, Clone, Copy)]
1398pub struct JavaVM {
1399 /// The vtable of the `JavaVM` object.
1400 vtable: JNIInvPtr,
1401}
1402
1403#[repr(C)]
1404#[derive(Debug, Copy, Clone)]
1405pub struct JavaVMAttachArgs {
1406 /// Jni version
1407 version: jint,
1408 /// Thread name as a C-Linke string
1409 name: *const c_char,
1410 /// `ThreadGroup` reference. This can be null
1411 group: jobject,
1412}
1413
1414#[repr(C)]
1415#[derive(Debug, Clone, Copy)]
1416pub struct JavaVMOption {
1417 /// this field contains the string option as a C-like string.
1418 optionString: *mut c_char,
1419 /// This field is reserved and should be set to null
1420 extraInfo: *mut c_void,
1421}
1422
1423impl JavaVMOption {
1424 pub const fn new(option_string: *mut c_char, extra_info: *mut c_void) -> Self {
1425 Self {
1426 optionString: option_string,
1427 extraInfo: extra_info,
1428 }
1429 }
1430
1431 #[must_use]
1432 pub const fn optionString(&self) -> *mut c_char {
1433 self.optionString
1434 }
1435
1436 #[must_use]
1437 pub const fn extraInfo(&self) -> *mut c_void {
1438 self.extraInfo
1439 }
1440}
1441
1442#[repr(C)]
1443#[derive(Debug, Clone, Copy)]
1444pub struct JavaVMInitArgs {
1445 /// The JNI version
1446 version: i32,
1447 /// amount of options
1448 nOptions: i32,
1449 /// options
1450 options: *mut JavaVMOption,
1451 /// flat to indicate if the jvm should ignore unrecognized options instead of returning an error 1 = yes, 0 = no
1452 ignoreUnrecognized: u8,
1453}
1454
1455impl JavaVMInitArgs {
1456 pub const fn new(version: i32, n_options: i32, options: *mut JavaVMOption, ignore_unrecognized: u8) -> Self {
1457 Self {
1458 version,
1459 nOptions: n_options,
1460 options,
1461 ignoreUnrecognized: ignore_unrecognized,
1462 }
1463 }
1464
1465 #[must_use]
1466 pub const fn version(&self) -> i32 {
1467 self.version
1468 }
1469
1470 #[must_use]
1471 pub const fn nOptions(&self) -> i32 {
1472 self.nOptions
1473 }
1474
1475 #[must_use]
1476 pub const fn options(&self) -> *mut JavaVMOption {
1477 self.options
1478 }
1479
1480 #[must_use]
1481 pub const fn ignoreUnrecognized(&self) -> u8 {
1482 self.ignoreUnrecognized
1483 }
1484}
1485
1486#[derive(Debug, Copy, Clone)]
1487#[repr(C)]
1488pub struct jvmtiThreadInfo {
1489 pub name: *const c_char,
1490 pub priority: jint,
1491 pub is_daemon: jboolean,
1492 pub thread_group: jthreadGroup,
1493 pub context_class_loader: jobject,
1494}
1495
1496impl Default for jvmtiThreadInfo {
1497 fn default() -> Self {
1498 Self {
1499 name: null(),
1500 priority: 0,
1501 is_daemon: jboolean::from(false),
1502 thread_group: null_mut(),
1503 context_class_loader: null_mut(),
1504 }
1505 }
1506}
1507
1508#[derive(Debug, Copy, Clone)]
1509#[repr(C)]
1510pub struct jvmtiThreadGroupInfo {
1511 pub parent: jthreadGroup,
1512 pub name: *const c_char,
1513 pub max_priority: jint,
1514 pub is_daemon: jboolean,
1515}
1516
1517#[derive(Debug, Copy, Clone)]
1518#[repr(C)]
1519pub struct jvmtiMonitorStackDepthInfo {
1520 pub monitor: jobject,
1521 pub stack_depth: jint,
1522}
1523
1524pub type jvmtiEventReserved = extern "system" fn();
1525pub type jvmtiEventBreakpoint = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, method: jmethodID, location: jlocation);
1526
1527pub type jvmtiEventClassFileLoadHook = extern "system" fn(
1528 jvmti_env: JVMTIEnv,
1529 jni_env: JNIEnv,
1530 class_being_redefined: jclass,
1531 loader: jobject,
1532 name: *const c_char,
1533 protection_domain: jobject,
1534 class_data_len: jint,
1535 class_data: *const c_uchar,
1536 new_class_data_len: *mut jint,
1537 new_class_data: *mut *mut c_uchar,
1538);
1539
1540pub type jvmtiEventClassLoad = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, klass: jclass);
1541
1542pub type jvmtiEventClassPrepare = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, klass: jclass);
1543
1544#[derive(Debug)]
1545#[repr(C)]
1546pub struct jvmtiAddrLocationMap {
1547 pub start_address: *const c_void,
1548 pub location: jlocation,
1549}
1550pub type jvmtiEventCompiledMethodLoad = extern "system" fn(
1551 jvmti_env: JVMTIEnv,
1552 method: jmethodID,
1553 code_size: jint,
1554 code_addr: *const c_void,
1555 map_length: jint,
1556 map: *const jvmtiAddrLocationMap,
1557 compile_info: *const c_void,
1558);
1559
1560pub type jvmtiEventCompiledMethodUnload = extern "system" fn(jvmti_env: JVMTIEnv, method: jmethodID, code_addr: *const c_void);
1561
1562pub type jvmtiEventDataDumpRequest = extern "system" fn(jvmti_env: JVMTIEnv);
1563
1564pub type jvmtiEventDynamicCodeGenerated = extern "system" fn(jvmti_env: JVMTIEnv, name: *const c_char, address: *const c_void, length: jint);
1565
1566pub type jvmtiEventException = extern "system" fn(
1567 jvmti_env: JVMTIEnv,
1568 jni_env: JNIEnv,
1569 thread: jthread,
1570 method: jmethodID,
1571 location: jlocation,
1572 exception: jobject,
1573 catch_method: jmethodID,
1574 catch_location: jlocation,
1575);
1576
1577pub type jvmtiEventExceptionCatch = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, method: jmethodID, location: jlocation, exception: jobject);
1578
1579pub type jvmtiEventFieldAccess =
1580 extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, method: jmethodID, location: jlocation, field_klass: jclass, object: jobject, field: jfieldID);
1581
1582pub type jvmtiEventFieldModification = extern "system" fn(
1583 jvmti_env: JVMTIEnv,
1584 jni_env: JNIEnv,
1585 thread: jthread,
1586 method: jmethodID,
1587 location: jlocation,
1588 field_klass: jclass,
1589 object: jobject,
1590 field: jfieldID,
1591 signature_type: c_char,
1592 new_value: jvalue,
1593);
1594
1595pub type jvmtiEventFramePop = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, method: jmethodID, was_popped_by_exception: jboolean);
1596
1597pub type jvmtiEventGarbageCollectionFinish = extern "system" fn(jvmti_env: JVMTIEnv);
1598
1599pub type jvmtiEventGarbageCollectionStart = extern "system" fn(jvmti_env: JVMTIEnv);
1600
1601pub type jvmtiEventMethodEntry = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, method: jmethodID);
1602
1603pub type jvmtiEventMethodExit =
1604 extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, method: jmethodID, was_popped_by_exception: jboolean, return_value: jvalue);
1605
1606pub type jvmtiEventMonitorContendedEnter = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, object: jobject);
1607
1608pub type jvmtiEventMonitorContendedEntered = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, object: jobject);
1609
1610pub type jvmtiEventMonitorWait = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, object: jobject, timeout: jlong);
1611
1612pub type jvmtiEventMonitorWaited = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, object: jobject, timed_out: jboolean);
1613
1614pub type jvmtiEventNativeMethodBind =
1615 extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, method: jmethodID, address: *mut c_void, new_address_ptr: *mut *mut c_void);
1616
1617pub type jvmtiEventObjectFree = extern "system" fn(jvmti_env: JVMTIEnv, tag: jlong);
1618
1619pub type jvmtiEventResourceExhausted = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, flags: jint, reserved: *const c_void, description: *const c_char);
1620
1621pub type jvmtiEventSampledObjectAlloc = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, object: jobject, object_klass: jclass, size: jlong);
1622
1623pub type jvmtiEventSingleStep = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, method: jmethodID, location: jlocation);
1624
1625pub type jvmtiEventThreadEnd = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread);
1626
1627pub type jvmtiEventThreadStart = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread);
1628
1629pub type jvmtiEventVirtualThreadEnd = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, virtual_thread: jthread);
1630
1631pub type jvmtiEventVirtualThreadStart = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, virtual_thread: jthread);
1632
1633pub type jvmtiEventVMDeath = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv);
1634
1635pub type jvmtiEventVMInit = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread);
1636
1637pub type jvmtiEventVMObjectAlloc = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv, thread: jthread, object: jobject, object_klass: jclass, size: jlong);
1638
1639pub type jvmtiEventVMStart = extern "system" fn(jvmti_env: JVMTIEnv, jni_env: JNIEnv);
1640
1641#[derive(Debug, Clone, Default)]
1642#[repr(C)]
1643#[allow(clippy::missing_docs_in_private_items)] //TODO later
1644pub struct jvmtiEventCallbacks {
1645 VMInit: SyncFnPtr<jvmtiEventVMInit>,
1646 VMDeath: SyncFnPtr<jvmtiEventVMDeath>,
1647 ThreadStart: SyncFnPtr<jvmtiEventThreadStart>,
1648 ThreadEnd: SyncFnPtr<jvmtiEventThreadEnd>,
1649 ClassFileLoadHook: SyncFnPtr<jvmtiEventClassFileLoadHook>,
1650 ClassLoad: SyncFnPtr<jvmtiEventClassLoad>,
1651 ClassPrepare: SyncFnPtr<jvmtiEventClassPrepare>,
1652 VMStart: SyncFnPtr<jvmtiEventVMStart>,
1653 Exception: SyncFnPtr<jvmtiEventException>,
1654 ExceptionCatch: SyncFnPtr<jvmtiEventExceptionCatch>,
1655 SingleStep: SyncFnPtr<jvmtiEventSingleStep>,
1656 FramePop: SyncFnPtr<jvmtiEventFramePop>,
1657 Breakpoint: SyncFnPtr<jvmtiEventBreakpoint>,
1658 FieldAccess: SyncFnPtr<jvmtiEventFieldAccess>,
1659 FieldModification: SyncFnPtr<jvmtiEventFieldModification>,
1660 MethodEntry: SyncFnPtr<jvmtiEventMethodEntry>,
1661 MethodExit: SyncFnPtr<jvmtiEventMethodExit>,
1662 NativeMethodBind: SyncFnPtr<jvmtiEventNativeMethodBind>,
1663 CompiledMethodLoad: SyncFnPtr<jvmtiEventCompiledMethodLoad>,
1664 CompiledMethodUnload: SyncFnPtr<jvmtiEventCompiledMethodUnload>,
1665 DynamicCodeGenerated: SyncFnPtr<jvmtiEventDynamicCodeGenerated>,
1666 DataDumpRequest: SyncFnPtr<jvmtiEventDataDumpRequest>,
1667 reserved72: SyncFnPtr<jvmtiEventReserved>,
1668 MonitorWait: SyncFnPtr<jvmtiEventMonitorWait>,
1669 MonitorWaited: SyncFnPtr<jvmtiEventMonitorWaited>,
1670 MonitorContendedEnter: SyncFnPtr<jvmtiEventMonitorContendedEnter>,
1671 MonitorContendedEntered: SyncFnPtr<jvmtiEventMonitorContendedEntered>,
1672 reserved77: SyncFnPtr<jvmtiEventReserved>,
1673 reserved78: SyncFnPtr<jvmtiEventReserved>,
1674 reserved79: SyncFnPtr<jvmtiEventReserved>,
1675 ResourceExhausted: SyncFnPtr<jvmtiEventResourceExhausted>,
1676 GarbageCollectionStart: SyncFnPtr<jvmtiEventGarbageCollectionStart>,
1677 GarbageCollectionFinish: SyncFnPtr<jvmtiEventGarbageCollectionFinish>,
1678 ObjectFree: SyncFnPtr<jvmtiEventObjectFree>,
1679 VMObjectAlloc: SyncFnPtr<jvmtiEventVMObjectAlloc>,
1680 reserved85: SyncFnPtr<jvmtiEventReserved>,
1681 SampledObjectAlloc: SyncFnPtr<jvmtiEventSampledObjectAlloc>,
1682 VirtualThreadStart: SyncFnPtr<jvmtiEventVirtualThreadStart>,
1683 VirtualThreadEnd: SyncFnPtr<jvmtiEventVirtualThreadEnd>,
1684}
1685
1686/// private helper macro to generate getters/setters for some ffi structs.
1687macro_rules! sync_ptr_setter {
1688 ($field:ident, $setter:ident, $with:ident, $typ:ty) => {
1689 /// Gets the function pointer value.
1690 ///
1691 /// # Returns
1692 /// None if the function pointer is null.
1693 #[must_use]
1694 pub const fn $field(&self) -> Option<$typ> {
1695 self.$field.inner()
1696 }
1697
1698 /// Sets the function pointer value.
1699 /// Pass None to set the function pointer value to null.
1700 pub const fn $setter(&mut self, function: Option<$typ>) {
1701 self.$field = sync_fn_ptr_opt!($typ, function);
1702 }
1703
1704 /// Sets the function pointer value.
1705 ///
1706 /// # Returns
1707 /// Self to allow for using the builder pattern.
1708 #[must_use]
1709 pub const fn $with(mut self, function: $typ) -> Self {
1710 self.$field = sync_fn_ptr!($typ, function);
1711 self
1712 }
1713 };
1714}
1715impl jvmtiEventCallbacks {
1716 /// Creates new jvmtiEventCallbacks with all callback function pointers set to null.
1717 #[must_use]
1718 pub const fn new() -> Self {
1719 Self {
1720 VMInit: SyncFnPtr::null(),
1721 VMDeath: SyncFnPtr::null(),
1722 ThreadStart: SyncFnPtr::null(),
1723 ThreadEnd: SyncFnPtr::null(),
1724 ClassFileLoadHook: SyncFnPtr::null(),
1725 ClassLoad: SyncFnPtr::null(),
1726 ClassPrepare: SyncFnPtr::null(),
1727 VMStart: SyncFnPtr::null(),
1728 Exception: SyncFnPtr::null(),
1729 ExceptionCatch: SyncFnPtr::null(),
1730 SingleStep: SyncFnPtr::null(),
1731 FramePop: SyncFnPtr::null(),
1732 Breakpoint: SyncFnPtr::null(),
1733 FieldAccess: SyncFnPtr::null(),
1734 FieldModification: SyncFnPtr::null(),
1735 MethodEntry: SyncFnPtr::null(),
1736 MethodExit: SyncFnPtr::null(),
1737 NativeMethodBind: SyncFnPtr::null(),
1738 CompiledMethodLoad: SyncFnPtr::null(),
1739 CompiledMethodUnload: SyncFnPtr::null(),
1740 DynamicCodeGenerated: SyncFnPtr::null(),
1741 DataDumpRequest: SyncFnPtr::null(),
1742 reserved72: SyncFnPtr::null(),
1743 MonitorWait: SyncFnPtr::null(),
1744 MonitorWaited: SyncFnPtr::null(),
1745 MonitorContendedEnter: SyncFnPtr::null(),
1746 MonitorContendedEntered: SyncFnPtr::null(),
1747 reserved77: SyncFnPtr::null(),
1748 reserved78: SyncFnPtr::null(),
1749 reserved79: SyncFnPtr::null(),
1750 ResourceExhausted: SyncFnPtr::null(),
1751 GarbageCollectionStart: SyncFnPtr::null(),
1752 GarbageCollectionFinish: SyncFnPtr::null(),
1753 ObjectFree: SyncFnPtr::null(),
1754 VMObjectAlloc: SyncFnPtr::null(),
1755 reserved85: SyncFnPtr::null(),
1756 SampledObjectAlloc: SyncFnPtr::null(),
1757 VirtualThreadStart: SyncFnPtr::null(),
1758 VirtualThreadEnd: SyncFnPtr::null(),
1759 }
1760 }
1761
1762 sync_ptr_setter!(VMInit, set_VMInit, with_VMInit, jvmtiEventVMInit);
1763 sync_ptr_setter!(VMDeath, set_VMDeath, with_VMDeath, jvmtiEventVMDeath);
1764 sync_ptr_setter!(ThreadStart, set_ThreadStart, with_ThreadStart, jvmtiEventThreadStart);
1765 sync_ptr_setter!(ThreadEnd, set_ThreadEnd, with_ThreadEnd, jvmtiEventThreadEnd);
1766 sync_ptr_setter!(ClassFileLoadHook, set_ClassFileLoadHook, with_ClassFileLoadHook, jvmtiEventClassFileLoadHook);
1767 sync_ptr_setter!(ClassLoad, set_ClassLoad, with_ClassLoad, jvmtiEventClassLoad);
1768 sync_ptr_setter!(ClassPrepare, set_ClassPrepare, with_ClassPrepare, jvmtiEventClassPrepare);
1769 sync_ptr_setter!(VMStart, set_VMStart, with_VMStart, jvmtiEventVMStart);
1770 sync_ptr_setter!(Exception, set_Exception, with_Exception, jvmtiEventException);
1771 sync_ptr_setter!(ExceptionCatch, set_ExceptionCatch, with_ExceptionCatch, jvmtiEventExceptionCatch);
1772 sync_ptr_setter!(SingleStep, set_SingleStep, with_SingleStep, jvmtiEventSingleStep);
1773 sync_ptr_setter!(FramePop, set_FramePop, with_FramePop, jvmtiEventFramePop);
1774 sync_ptr_setter!(Breakpoint, set_Breakpoint, with_Breakpoint, jvmtiEventBreakpoint);
1775 sync_ptr_setter!(FieldAccess, set_FieldAccess, with_FieldAccess, jvmtiEventFieldAccess);
1776 sync_ptr_setter!(FieldModification, set_FieldModification, with_FieldModification, jvmtiEventFieldModification);
1777 sync_ptr_setter!(MethodEntry, set_MethodEntry, with_MethodEntry, jvmtiEventMethodEntry);
1778 sync_ptr_setter!(MethodExit, set_MethodExit, with_MethodExit, jvmtiEventMethodExit);
1779 sync_ptr_setter!(NativeMethodBind, set_NativeMethodBind, with_NativeMethodBind, jvmtiEventNativeMethodBind);
1780 sync_ptr_setter!(CompiledMethodLoad, set_CompiledMethodLoad, with_CompiledMethodLoad, jvmtiEventCompiledMethodLoad);
1781 sync_ptr_setter!(CompiledMethodUnload, set_CompiledMethodUnload, with_CompiledMethodUnload, jvmtiEventCompiledMethodUnload);
1782 sync_ptr_setter!(DynamicCodeGenerated, set_DynamicCodeGenerated, with_DynamicCodeGenerated, jvmtiEventDynamicCodeGenerated);
1783 sync_ptr_setter!(DataDumpRequest, set_DataDumpRequest, with_DataDumpRequest, jvmtiEventDataDumpRequest);
1784 sync_ptr_setter!(reserved72, set_reserved72, with_reserved72, jvmtiEventReserved);
1785 sync_ptr_setter!(MonitorWait, set_MonitorWait, with_MonitorWait, jvmtiEventMonitorWait);
1786 sync_ptr_setter!(MonitorWaited, set_MonitorWaited, with_MonitorWaited, jvmtiEventMonitorWaited);
1787 sync_ptr_setter!(
1788 MonitorContendedEnter,
1789 set_MonitorContendedEnter,
1790 with_MonitorContendedEnter,
1791 jvmtiEventMonitorContendedEnter
1792 );
1793 sync_ptr_setter!(
1794 MonitorContendedEntered,
1795 set_MonitorContendedEntered,
1796 with_MonitorContendedEntered,
1797 jvmtiEventMonitorContendedEntered
1798 );
1799 sync_ptr_setter!(reserved77, set_reserved77, with_reserved77, jvmtiEventReserved);
1800 sync_ptr_setter!(reserved78, set_reserved78, with_reserved78, jvmtiEventReserved);
1801 sync_ptr_setter!(reserved79, set_reserved79, with_reserved79, jvmtiEventReserved);
1802 sync_ptr_setter!(ResourceExhausted, set_ResourceExhausted, with_ResourceExhausted, jvmtiEventResourceExhausted);
1803 sync_ptr_setter!(
1804 GarbageCollectionStart,
1805 set_GarbageCollectionStart,
1806 with_GarbageCollectionStart,
1807 jvmtiEventGarbageCollectionStart
1808 );
1809 sync_ptr_setter!(
1810 GarbageCollectionFinish,
1811 set_GarbageCollectionFinish,
1812 with_GarbageCollectionFinish,
1813 jvmtiEventGarbageCollectionFinish
1814 );
1815 sync_ptr_setter!(ObjectFree, set_ObjectFree, with_ObjectFree, jvmtiEventObjectFree);
1816 sync_ptr_setter!(VMObjectAlloc, set_VMObjectAlloc, with_VMObjectAlloc, jvmtiEventVMObjectAlloc);
1817 sync_ptr_setter!(reserved85, set_reserved85, with_reserved85, jvmtiEventReserved);
1818 sync_ptr_setter!(SampledObjectAlloc, set_SampledObjectAlloc, with_SampledObjectAlloc, jvmtiEventSampledObjectAlloc);
1819 sync_ptr_setter!(VirtualThreadStart, set_VirtualThreadStart, with_VirtualThreadStart, jvmtiEventVirtualThreadStart);
1820 sync_ptr_setter!(VirtualThreadEnd, set_VirtualThreadEnd, with_VirtualThreadEnd, jvmtiEventVirtualThreadEnd);
1821}
1822
1823#[repr(C)]
1824#[derive(Debug, Copy, Clone, Default)]
1825pub enum jvmtiEventMode {
1826 #[default]
1827 JVMTI_ENABLE = 1,
1828 JVMTI_DISABLE = 0,
1829}
1830
1831#[repr(C)]
1832#[derive(Debug, Copy, Clone, Default)]
1833pub enum jvmtiEvent {
1834 #[default]
1835 JVMTI_EVENT_VM_DEATH = 51,
1836 JVMTI_EVENT_THREAD_START = 52,
1837 JVMTI_EVENT_THREAD_END = 53,
1838 JVMTI_EVENT_CLASS_FILE_LOAD_HOOK = 54,
1839 JVMTI_EVENT_CLASS_LOAD = 55,
1840 JVMTI_EVENT_CLASS_PREPARE = 56,
1841 JVMTI_EVENT_VM_START = 57,
1842 JVMTI_EVENT_EXCEPTION = 58,
1843 JVMTI_EVENT_EXCEPTION_CATCH = 59,
1844 JVMTI_EVENT_SINGLE_STEP = 60,
1845 JVMTI_EVENT_FRAME_POP = 61,
1846 JVMTI_EVENT_BREAKPOINT = 62,
1847 JVMTI_EVENT_FIELD_ACCESS = 63,
1848 JVMTI_EVENT_FIELD_MODIFICATION = 64,
1849 JVMTI_EVENT_METHOD_ENTRY = 65,
1850 JVMTI_EVENT_METHOD_EXIT = 66,
1851 JVMTI_EVENT_NATIVE_METHOD_BIND = 67,
1852 JVMTI_EVENT_COMPILED_METHOD_LOAD = 68,
1853 JVMTI_EVENT_COMPILED_METHOD_UNLOAD = 69,
1854 JVMTI_EVENT_DYNAMIC_CODE_GENERATED = 70,
1855 JVMTI_EVENT_DATA_DUMP_REQUEST = 71,
1856 JVMTI_EVENT_MONITOR_WAIT = 73,
1857 JVMTI_EVENT_MONITOR_WAITED = 74,
1858 JVMTI_EVENT_MONITOR_CONTENDED_ENTER = 75,
1859 JVMTI_EVENT_MONITOR_CONTENDED_ENTERED = 76,
1860 JVMTI_EVENT_RESOURCE_EXHAUSTED = 80,
1861 JVMTI_EVENT_GARBAGE_COLLECTION_START = 81,
1862 JVMTI_EVENT_GARBAGE_COLLECTION_FINISH = 82,
1863 JVMTI_EVENT_OBJECT_FREE = 83,
1864 JVMTI_EVENT_VM_OBJECT_ALLOC = 84,
1865 JVMTI_EVENT_SAMPLED_OBJECT_ALLOC = 86,
1866 JVMTI_EVENT_VIRTUAL_THREAD_START = 87,
1867 JVMTI_EVENT_VIRTUAL_THREAD_END = 88,
1868}
1869
1870pub type jvmtiExtensionFunction = Option<extern "C" fn(jvmti_env: JVMTIEnv, ...)>;
1871
1872pub type jvmtiExtensionEvent = Option<extern "C" fn(jvmti_env: JVMTIEnv, ...)>;
1873
1874//We cant enum this as the jvm returning an unknown value to us would be ub.
1875pub type jvmtiParamKind = c_int;
1876
1877/// Ingoing argument - foo.
1878pub const JVMTI_KIND_IN: c_int = 91;
1879
1880/// Ingoing pointer argument - const foo*.
1881pub const JVMTI_KIND_IN_PTR: c_int = 92;
1882
1883/// Ingoing array argument - const foo*.
1884pub const JVMTI_KIND_IN_BUF: c_int = 93;
1885
1886/// Outgoing allocated array argument - foo**. Free with Deallocate.
1887pub const JVMTI_KIND_ALLOC_BUF: c_int = 94;
1888
1889/// Outgoing allocated array of allocated arrays argument - foo***. Free with Deallocate.
1890pub const JVMTI_KIND_ALLOC_ALLOC_BUF: c_int = 95;
1891
1892/// Outgoing argument - foo*.
1893pub const JVMTI_KIND_OUT: c_int = 96;
1894
1895/// Outgoing array argument (pre-allocated by agent) - foo*. Do not Deallocate.
1896pub const JVMTI_KIND_OUT_BUF: c_int = 97;
1897
1898//We cant enum this as the jvm returning an unknown value to us would be ub.
1899pub type jvmtiParamTypes = c_int;
1900
1901/// Java programming language primitive type - byte. JNI type jbyte.
1902pub const JVMTI_TYPE_JBYTE: c_int = 101;
1903
1904/// Java programming language primitive type - char. JNI type jchar.
1905pub const JVMTI_TYPE_JCHAR: c_int = 102;
1906
1907/// Java programming language primitive type - short. JNI type jshort.
1908pub const JVMTI_TYPE_JSHORT: c_int = 103;
1909
1910/// Java programming language primitive type - int. JNI type jint.
1911pub const JVMTI_TYPE_JINT: c_int = 104;
1912
1913/// Java programming language primitive type - long. JNI type jlong.
1914pub const JVMTI_TYPE_JLONG: c_int = 105;
1915
1916/// Java programming language primitive type - float. JNI type jfloat.
1917pub const JVMTI_TYPE_JFLOAT: c_int = 106;
1918
1919/// Java programming language primitive type - double. JNI type jdouble.
1920pub const JVMTI_TYPE_JDOUBLE: c_int = 107;
1921
1922/// Java programming language primitive type - boolean. JNI type jboolean.
1923pub const JVMTI_TYPE_JBOOLEAN: c_int = 108;
1924
1925/// Java programming language object type - java.lang.Object. JNI type jobject. Returned values are JNI local references and must be managed.
1926pub const JVMTI_TYPE_JOBJECT: c_int = 109;
1927
1928/// Java programming language object type - java.lang.Thread. JVM TI type jthread. Returned values are JNI local references and must be managed.
1929pub const JVMTI_TYPE_JTHREAD: c_int = 110;
1930
1931/// Java programming language object type - java.lang.Class. JNI type jclass. Returned values are JNI local references and must be managed.
1932pub const JVMTI_TYPE_JCLASS: c_int = 111;
1933
1934/// Union of all Java programming language primitive and object types - JNI type jvalue. Returned values which represent object types are JNI local references and must be managed.
1935pub const JVMTI_TYPE_JVALUE: c_int = 112;
1936
1937/// Java programming language field identifier - JNI type jfieldID.
1938pub const JVMTI_TYPE_JFIELDID: c_int = 113;
1939
1940/// Java programming language method identifier - JNI type jmethodID.
1941pub const JVMTI_TYPE_JMETHODID: c_int = 114;
1942
1943/// C programming language type - char.
1944pub const JVMTI_TYPE_CCHAR: c_int = 115;
1945
1946/// C programming language type - void.
1947pub const JVMTI_TYPE_CVOID: c_int = 116;
1948
1949/// JNI environment - `JNIEnv`. Should be used with the correct jvmtiParamKind to make it a pointer type.
1950pub const JVMTI_TYPE_JNIENV: c_int = 117;
1951
1952pub type jvmtiTimerKind = c_int;
1953
1954pub const JVMTI_TIMER_USER_CPU: jvmtiTimerKind = 30;
1955
1956pub const JVMTI_TIMER_TOTAL_CPU: jvmtiTimerKind = 31;
1957
1958pub const JVMTI_TIMER_ELAPSED: jvmtiTimerKind = 32;
1959#[repr(C)]
1960#[derive(Debug, Copy, Clone, Default, PartialEq, Eq)]
1961pub struct jvmtiTimerInfo {
1962 pub max_value: jlong,
1963 pub may_skip_forward: jboolean,
1964 pub may_skip_backward: jboolean,
1965 pub kind: jvmtiTimerKind,
1966 pub reserved1: jlong,
1967 pub reserved2: jlong,
1968}
1969
1970#[repr(C)]
1971#[derive(Debug, Copy, Clone)]
1972pub struct jvmtiParamInfo {
1973 pub name: *mut c_char,
1974 pub kind: jvmtiParamKind,
1975 pub base_type: jvmtiParamTypes,
1976 pub null_ok: jboolean,
1977}
1978#[repr(C)]
1979#[derive(Debug, Copy, Clone)]
1980pub struct jvmtiExtensionFunctionInfo {
1981 pub func: jvmtiExtensionFunction,
1982 pub id: *mut c_char,
1983 pub short_description: *mut c_char,
1984 pub param_count: jint,
1985 pub params: *mut jvmtiParamInfo,
1986 pub error_count: jint,
1987 pub errors: *mut jvmtiError,
1988}
1989
1990impl Default for jvmtiExtensionFunctionInfo {
1991 fn default() -> Self {
1992 Self {
1993 func: None,
1994 id: null_mut(),
1995 short_description: null_mut(),
1996 param_count: 0,
1997 params: null_mut(),
1998 error_count: 0,
1999 errors: null_mut(),
2000 }
2001 }
2002}
2003
2004#[repr(C)]
2005#[derive(Debug, Copy, Clone)]
2006pub struct jvmtiExtensionEventInfo {
2007 pub extension_event_index: jint,
2008 pub id: *mut c_char,
2009 pub short_description: *mut c_char,
2010 pub param_count: jint,
2011 pub params: *mut jvmtiParamInfo,
2012}
2013
2014impl Default for jvmtiExtensionEventInfo {
2015 fn default() -> Self {
2016 Self {
2017 extension_event_index: 0,
2018 id: null_mut(),
2019 short_description: null_mut(),
2020 param_count: 0,
2021 params: null_mut(),
2022 }
2023 }
2024}
2025
2026pub type jvmtiPhase = c_int;
2027pub const JVMTI_PHASE_ONLOAD: jvmtiPhase = 1;
2028pub const JVMTI_PHASE_PRIMORDIAL: jvmtiPhase = 2;
2029pub const JVMTI_PHASE_START: jvmtiPhase = 6;
2030pub const JVMTI_PHASE_LIVE: jvmtiPhase = 4;
2031pub const JVMTI_PHASE_DEAD: jvmtiPhase = 8;
2032
2033#[repr(C)]
2034#[derive(Debug, Copy, Clone)]
2035pub enum jvmtiVerboseFlag {
2036 JVMTI_VERBOSE_OTHER = 0,
2037 JVMTI_VERBOSE_GC = 1,
2038 JVMTI_VERBOSE_CLASS = 2,
2039 JVMTI_VERBOSE_JNI = 4,
2040}
2041
2042pub type jvmtiJlocationFormat = c_int;
2043
2044/// jlocation values represent virtual machine bytecode indices--that is, offsets into the virtual machine code for a method.
2045pub const JVMTI_JLOCATION_JVMBCI: jvmtiJlocationFormat = 1;
2046
2047/// jlocation values represent native machine program counter values.
2048pub const JVMTI_JLOCATION_MACHINEPC: jvmtiJlocationFormat = 2;
2049
2050/// jlocation values have some other representation.
2051pub const JVMTI_JLOCATION_OTHER: jvmtiJlocationFormat = 0;
2052
2053#[repr(transparent)]
2054#[derive(Debug, Default, Copy, Clone, Eq, PartialEq)]
2055pub struct jvmtiCapabilities(u128);
2056
2057/// Dumped from c program `bitfield_gen` in this repo.
2058#[expect(clippy::missing_docs_in_private_items)]
2059#[cfg(target_endian = "little")]
2060mod jvmti_cap_offsets {
2061 pub const OFFSET_CAN_TAG_OBJECTS: usize = 0x0001;
2062 pub const OFFSET_CAN_GENERATE_FIELD_MODIFICATION_EVENTS: usize = 0x0002;
2063 pub const OFFSET_CAN_GENERATE_FIELD_ACCESS_EVENTS: usize = 0x0004;
2064 pub const OFFSET_CAN_GET_BYTECODES: usize = 0x0008;
2065 pub const OFFSET_CAN_GET_SYNTHETIC_ATTRIBUTE: usize = 0x0010;
2066 pub const OFFSET_CAN_GET_OWNED_MONITOR_INFO: usize = 0x0020;
2067 pub const OFFSET_CAN_GET_CURRENT_CONTENDED_MONITOR: usize = 0x0040;
2068 pub const OFFSET_CAN_GET_MONITOR_INFO: usize = 0x0080;
2069 pub const OFFSET_CAN_POP_FRAME: usize = 0x0101;
2070 pub const OFFSET_CAN_REDEFINE_CLASSES: usize = 0x0102;
2071 pub const OFFSET_CAN_SIGNAL_THREAD: usize = 0x0104;
2072 pub const OFFSET_CAN_GET_SOURCE_FILE_NAME: usize = 0x0108;
2073 pub const OFFSET_CAN_GET_LINE_NUMBERS: usize = 0x0110;
2074 pub const OFFSET_CAN_GET_SOURCE_DEBUG_EXTENSION: usize = 0x0120;
2075 pub const OFFSET_CAN_ACCESS_LOCAL_VARIABLES: usize = 0x0140;
2076 pub const OFFSET_CAN_MAINTAIN_ORIGINAL_METHOD_ORDER: usize = 0x0180;
2077 pub const OFFSET_CAN_GENERATE_SINGLE_STEP_EVENTS: usize = 0x0201;
2078 pub const OFFSET_CAN_GENERATE_EXCEPTION_EVENTS: usize = 0x0202;
2079 pub const OFFSET_CAN_GENERATE_FRAME_POP_EVENTS: usize = 0x0204;
2080 pub const OFFSET_CAN_GENERATE_BREAKPOINT_EVENTS: usize = 0x0208;
2081 pub const OFFSET_CAN_SUSPEND: usize = 0x0210;
2082 pub const OFFSET_CAN_REDEFINE_ANY_CLASS: usize = 0x0220;
2083 pub const OFFSET_CAN_GET_CURRENT_THREAD_CPU_TIME: usize = 0x0240;
2084 pub const OFFSET_CAN_GET_THREAD_CPU_TIME: usize = 0x0280;
2085 pub const OFFSET_CAN_GENERATE_METHOD_ENTRY_EVENTS: usize = 0x0301;
2086 pub const OFFSET_CAN_GENERATE_METHOD_EXIT_EVENTS: usize = 0x0302;
2087 pub const OFFSET_CAN_GENERATE_ALL_CLASS_HOOK_EVENTS: usize = 0x0304;
2088 pub const OFFSET_CAN_GENERATE_COMPILED_METHOD_LOAD_EVENTS: usize = 0x0308;
2089 pub const OFFSET_CAN_GENERATE_MONITOR_EVENTS: usize = 0x0310;
2090 pub const OFFSET_CAN_GENERATE_VM_OBJECT_ALLOC_EVENTS: usize = 0x0320;
2091 pub const OFFSET_CAN_GENERATE_NATIVE_METHOD_BIND_EVENTS: usize = 0x0340;
2092 pub const OFFSET_CAN_GENERATE_GARBAGE_COLLECTION_EVENTS: usize = 0x0380;
2093 pub const OFFSET_CAN_GENERATE_OBJECT_FREE_EVENTS: usize = 0x0401;
2094 pub const OFFSET_CAN_FORCE_EARLY_RETURN: usize = 0x0402;
2095 pub const OFFSET_CAN_GET_OWNED_MONITOR_STACK_DEPTH_INFO: usize = 0x0404;
2096 pub const OFFSET_CAN_GET_CONSTANT_POOL: usize = 0x0408;
2097 pub const OFFSET_CAN_SET_NATIVE_METHOD_PREFIX: usize = 0x0410;
2098 pub const OFFSET_CAN_RETRANSFORM_CLASSES: usize = 0x0420;
2099 pub const OFFSET_CAN_RETRANSFORM_ANY_CLASS: usize = 0x0440;
2100 pub const OFFSET_CAN_GENERATE_RESOURCE_EXHAUSTION_HEAP_EVENTS: usize = 0x0480;
2101 pub const OFFSET_CAN_GENERATE_RESOURCE_EXHAUSTION_THREAD_EVENETS: usize = 0x0501;
2102 pub const OFFSET_CAN_GENERATE_EARLY_VMSTART: usize = 0x0502;
2103 pub const OFFSET_CAN_GENERATE_EARLY_CLASS_HOOK_EVENTS: usize = 0x0504;
2104 pub const OFFSET_CAN_GENERATE_SAMPLED_OBJECT_ALLOC_EVENTS: usize = 0x0508;
2105 pub const OFFSET_CAN_SUPPORT_VIRTUAL_THREADS: usize = 0x0510;
2106}
2107
2108#[expect(clippy::missing_docs_in_private_items)]
2109#[cfg(target_endian = "big")]
2110mod jvmti_cap_offsets {
2111 pub const OFFSET_CAN_TAG_OBJECTS: usize = 0x0080;
2112 pub const OFFSET_CAN_GENERATE_FIELD_MODIFICATION_EVENTS: usize = 0x0040;
2113 pub const OFFSET_CAN_GENERATE_FIELD_ACCESS_EVENTS: usize = 0x0020;
2114 pub const OFFSET_CAN_GET_BYTECODES: usize = 0x0010;
2115 pub const OFFSET_CAN_GET_SYNTHETIC_ATTRIBUTE: usize = 0x0008;
2116 pub const OFFSET_CAN_GET_OWNED_MONITOR_INFO: usize = 0x0004;
2117 pub const OFFSET_CAN_GET_CURRENT_CONTENDED_MONITOR: usize = 0x0002;
2118 pub const OFFSET_CAN_GET_MONITOR_INFO: usize = 0x0001;
2119 pub const OFFSET_CAN_POP_FRAME: usize = 0x0180;
2120 pub const OFFSET_CAN_REDEFINE_CLASSES: usize = 0x0140;
2121 pub const OFFSET_CAN_SIGNAL_THREAD: usize = 0x0120;
2122 pub const OFFSET_CAN_GET_SOURCE_FILE_NAME: usize = 0x0110;
2123 pub const OFFSET_CAN_GET_LINE_NUMBERS: usize = 0x0108;
2124 pub const OFFSET_CAN_GET_SOURCE_DEBUG_EXTENSION: usize = 0x0104;
2125 pub const OFFSET_CAN_ACCESS_LOCAL_VARIABLES: usize = 0x0102;
2126 pub const OFFSET_CAN_MAINTAIN_ORIGINAL_METHOD_ORDER: usize = 0x0101;
2127 pub const OFFSET_CAN_GENERATE_SINGLE_STEP_EVENTS: usize = 0x0280;
2128 pub const OFFSET_CAN_GENERATE_EXCEPTION_EVENTS: usize = 0x0240;
2129 pub const OFFSET_CAN_GENERATE_FRAME_POP_EVENTS: usize = 0x0220;
2130 pub const OFFSET_CAN_GENERATE_BREAKPOINT_EVENTS: usize = 0x0210;
2131 pub const OFFSET_CAN_SUSPEND: usize = 0x0208;
2132 pub const OFFSET_CAN_REDEFINE_ANY_CLASS: usize = 0x0204;
2133 pub const OFFSET_CAN_GET_CURRENT_THREAD_CPU_TIME: usize = 0x0202;
2134 pub const OFFSET_CAN_GET_THREAD_CPU_TIME: usize = 0x0201;
2135 pub const OFFSET_CAN_GENERATE_METHOD_ENTRY_EVENTS: usize = 0x0380;
2136 pub const OFFSET_CAN_GENERATE_METHOD_EXIT_EVENTS: usize = 0x0340;
2137 pub const OFFSET_CAN_GENERATE_ALL_CLASS_HOOK_EVENTS: usize = 0x0320;
2138 pub const OFFSET_CAN_GENERATE_COMPILED_METHOD_LOAD_EVENTS: usize = 0x0310;
2139 pub const OFFSET_CAN_GENERATE_MONITOR_EVENTS: usize = 0x0308;
2140 pub const OFFSET_CAN_GENERATE_VM_OBJECT_ALLOC_EVENTS: usize = 0x0304;
2141 pub const OFFSET_CAN_GENERATE_NATIVE_METHOD_BIND_EVENTS: usize = 0x0302;
2142 pub const OFFSET_CAN_GENERATE_GARBAGE_COLLECTION_EVENTS: usize = 0x0301;
2143 pub const OFFSET_CAN_GENERATE_OBJECT_FREE_EVENTS: usize = 0x0480;
2144 pub const OFFSET_CAN_FORCE_EARLY_RETURN: usize = 0x0440;
2145 pub const OFFSET_CAN_GET_OWNED_MONITOR_STACK_DEPTH_INFO: usize = 0x0420;
2146 pub const OFFSET_CAN_GET_CONSTANT_POOL: usize = 0x0410;
2147 pub const OFFSET_CAN_SET_NATIVE_METHOD_PREFIX: usize = 0x0408;
2148 pub const OFFSET_CAN_RETRANSFORM_CLASSES: usize = 0x0404;
2149 pub const OFFSET_CAN_RETRANSFORM_ANY_CLASS: usize = 0x0402;
2150 pub const OFFSET_CAN_GENERATE_RESOURCE_EXHAUSTION_HEAP_EVENTS: usize = 0x0401;
2151 pub const OFFSET_CAN_GENERATE_RESOURCE_EXHAUSTION_THREAD_EVENETS: usize = 0x0580;
2152 pub const OFFSET_CAN_GENERATE_EARLY_VMSTART: usize = 0x0540;
2153 pub const OFFSET_CAN_GENERATE_EARLY_CLASS_HOOK_EVENTS: usize = 0x0520;
2154 pub const OFFSET_CAN_GENERATE_SAMPLED_OBJECT_ALLOC_EVENTS: usize = 0x0510;
2155 pub const OFFSET_CAN_SUPPORT_VIRTUAL_THREADS: usize = 0x0508;
2156}
2157
2158#[expect(clippy::wildcard_imports)]
2159use crate::jvmti_cap_offsets::*;
2160
2161/// This macro generates an setter and getter for a field that is stored in the C jvmtiCapabilities bitfield struct
2162/// In rust we store the bitfield in a u128.
2163macro_rules! jvmtiCapField {
2164 ($getter:ident, $setter:ident, $constant:expr) => {
2165 #[must_use]
2166 pub const fn $getter(&self) -> bool {
2167 self.get($constant)
2168 }
2169
2170 pub const fn $setter(&mut self, value: bool) {
2171 self.set($constant, value);
2172 }
2173 };
2174}
2175
2176impl jvmtiCapabilities {
2177 /// Copies the raw data into the given slice.
2178 /// # Panics
2179 /// if the target slice does not have the same length as `size()` returns
2180 #[inline(always)]
2181 pub const fn copy_to_slice(&self, target: &mut [u8]) {
2182 target.copy_from_slice(self.0.to_ne_bytes().as_slice());
2183 }
2184
2185 /// Copies the raw data from the given slice into this structure.
2186 /// # Panics
2187 /// if the target slice does not have the same length as `size()` returns
2188 #[inline(always)]
2189 pub const fn copy_from_slice(&mut self, data: &[u8]) {
2190 let mut raw = [0u8; 16];
2191 raw.copy_from_slice(data);
2192 self.0 = u128::from_ne_bytes(raw);
2193 }
2194
2195 ///Returns the amount of bytes needed to access the raw data in this struct.
2196 #[inline(always)]
2197 #[must_use]
2198 pub const fn size() -> usize {
2199 16
2200 }
2201
2202 /// C compatible bitfield setter, translates the offset constant into a slice index and bitmask.
2203 #[expect(clippy::cast_possible_truncation)]
2204 const fn set(&mut self, offset: usize, value: bool) {
2205 let idx = offset >> 8;
2206 let mask = (offset & 0xFF) as u8;
2207 let mut raw = self.0.to_ne_bytes();
2208 if value {
2209 raw[idx] |= mask;
2210 } else {
2211 raw[idx] &= !mask;
2212 }
2213 self.0 = u128::from_ne_bytes(raw);
2214 }
2215
2216 /// C compatible bitfield getter, translates the offset constant into a slice index and bitmask.
2217 #[must_use]
2218 #[expect(clippy::cast_possible_truncation)]
2219 const fn get(&self, offset: usize) -> bool {
2220 let idx = offset >> 8;
2221 let mask = (offset & 0xFF) as u8;
2222 let raw = self.0.to_ne_bytes();
2223 raw[idx] & mask != 0
2224 }
2225
2226 jvmtiCapField!(can_tag_objects, set_can_tag_objects, OFFSET_CAN_TAG_OBJECTS);
2227 jvmtiCapField!(
2228 can_generate_field_modification_events,
2229 set_can_generate_field_modification_events,
2230 OFFSET_CAN_GENERATE_FIELD_MODIFICATION_EVENTS
2231 );
2232 jvmtiCapField!(
2233 can_generate_field_access_events,
2234 set_can_generate_field_access_events,
2235 OFFSET_CAN_GENERATE_FIELD_ACCESS_EVENTS
2236 );
2237 jvmtiCapField!(can_get_bytecodes, set_can_get_bytecodes, OFFSET_CAN_GET_BYTECODES);
2238 jvmtiCapField!(can_get_synthetic_attribute, set_can_get_synthetic_attribute, OFFSET_CAN_GET_SYNTHETIC_ATTRIBUTE);
2239 jvmtiCapField!(can_get_owned_monitor_info, set_can_get_owned_monitor_info, OFFSET_CAN_GET_OWNED_MONITOR_INFO);
2240 jvmtiCapField!(
2241 can_get_current_contended_monitor,
2242 set_can_get_current_contended_monitor,
2243 OFFSET_CAN_GET_CURRENT_CONTENDED_MONITOR
2244 );
2245 jvmtiCapField!(can_get_monitor_info, set_can_get_monitor_info, OFFSET_CAN_GET_MONITOR_INFO);
2246 jvmtiCapField!(can_pop_frame, set_can_pop_frame, OFFSET_CAN_POP_FRAME);
2247 jvmtiCapField!(can_redefine_classes, set_can_redefine_classes, OFFSET_CAN_REDEFINE_CLASSES);
2248 jvmtiCapField!(can_signal_thread, set_can_signal_thread, OFFSET_CAN_SIGNAL_THREAD);
2249 jvmtiCapField!(can_get_source_file_name, set_can_get_source_file_name, OFFSET_CAN_GET_SOURCE_FILE_NAME);
2250 jvmtiCapField!(can_get_line_numbers, set_can_get_line_numbers, OFFSET_CAN_GET_LINE_NUMBERS);
2251 jvmtiCapField!(can_get_source_debug_extension, set_can_get_source_debug_extension, OFFSET_CAN_GET_SOURCE_DEBUG_EXTENSION);
2252 jvmtiCapField!(can_access_local_variables, set_can_access_local_variables, OFFSET_CAN_ACCESS_LOCAL_VARIABLES);
2253 jvmtiCapField!(
2254 can_maintain_original_method_order,
2255 set_can_maintain_original_method_order,
2256 OFFSET_CAN_MAINTAIN_ORIGINAL_METHOD_ORDER
2257 );
2258 jvmtiCapField!(can_generate_single_step_events, set_generate_single_step_events, OFFSET_CAN_GENERATE_SINGLE_STEP_EVENTS);
2259 jvmtiCapField!(can_generate_exception_events, set_can_generate_exception_events, OFFSET_CAN_GENERATE_EXCEPTION_EVENTS);
2260 jvmtiCapField!(can_generate_frame_pop_events, set_can_generate_frame_pop_events, OFFSET_CAN_GENERATE_FRAME_POP_EVENTS);
2261 jvmtiCapField!(can_generate_breakpoint_events, set_can_generate_breakpoint_events, OFFSET_CAN_GENERATE_BREAKPOINT_EVENTS);
2262 jvmtiCapField!(can_suspend, set_can_suspend, OFFSET_CAN_SUSPEND);
2263 jvmtiCapField!(can_redefine_any_class, set_can_redefine_any_class, OFFSET_CAN_REDEFINE_ANY_CLASS);
2264 jvmtiCapField!(can_get_current_thread_cpu_time, set_can_get_current_thread_cpu_time, OFFSET_CAN_GET_CURRENT_THREAD_CPU_TIME);
2265 jvmtiCapField!(can_get_thread_cpu_time, set_can_get_thread_cpu_time, OFFSET_CAN_GET_THREAD_CPU_TIME);
2266 jvmtiCapField!(
2267 can_generate_method_entry_events,
2268 set_can_generate_method_entry_events,
2269 OFFSET_CAN_GENERATE_METHOD_ENTRY_EVENTS
2270 );
2271 jvmtiCapField!(can_generate_method_exit_events, set_can_generate_method_exit_events, OFFSET_CAN_GENERATE_METHOD_EXIT_EVENTS);
2272 jvmtiCapField!(
2273 can_generate_all_class_hook_events,
2274 set_can_generate_all_class_hook_events,
2275 OFFSET_CAN_GENERATE_ALL_CLASS_HOOK_EVENTS
2276 );
2277 jvmtiCapField!(
2278 can_generate_compiled_method_load_events,
2279 set_can_generate_compiled_method_load_events,
2280 OFFSET_CAN_GENERATE_COMPILED_METHOD_LOAD_EVENTS
2281 );
2282 jvmtiCapField!(can_generate_monitor_events, set_can_generate_monitor_events, OFFSET_CAN_GENERATE_MONITOR_EVENTS);
2283 jvmtiCapField!(
2284 can_generate_vm_object_alloc_events,
2285 set_can_generate_vm_object_alloc_events,
2286 OFFSET_CAN_GENERATE_VM_OBJECT_ALLOC_EVENTS
2287 );
2288 jvmtiCapField!(
2289 can_generate_native_method_bind_events,
2290 set_can_generate_native_method_bind_events,
2291 OFFSET_CAN_GENERATE_NATIVE_METHOD_BIND_EVENTS
2292 );
2293 jvmtiCapField!(
2294 can_generate_garbage_collection_events,
2295 set_can_generate_garbage_collection_events,
2296 OFFSET_CAN_GENERATE_GARBAGE_COLLECTION_EVENTS
2297 );
2298 jvmtiCapField!(can_generate_object_free_events, set_can_generate_object_free_events, OFFSET_CAN_GENERATE_OBJECT_FREE_EVENTS);
2299 jvmtiCapField!(can_force_early_return, set_can_force_early_return, OFFSET_CAN_FORCE_EARLY_RETURN);
2300 jvmtiCapField!(
2301 can_get_owned_monitor_stack_depth_info,
2302 set_can_get_owned_monitor_stack_depth_info,
2303 OFFSET_CAN_GET_OWNED_MONITOR_STACK_DEPTH_INFO
2304 );
2305 jvmtiCapField!(can_get_constant_pool, set_can_get_constant_pool, OFFSET_CAN_GET_CONSTANT_POOL);
2306 jvmtiCapField!(can_set_native_method_prefix, set_can_set_native_method_prefix, OFFSET_CAN_SET_NATIVE_METHOD_PREFIX);
2307 jvmtiCapField!(can_retransform_classes, set_can_retransform_classes, OFFSET_CAN_RETRANSFORM_CLASSES);
2308 jvmtiCapField!(can_retransform_any_class, set_can_retransform_any_class, OFFSET_CAN_RETRANSFORM_ANY_CLASS);
2309 jvmtiCapField!(
2310 can_generate_resource_exhaustion_heap_events,
2311 set_can_generate_resource_exhaustion_heap_events,
2312 OFFSET_CAN_GENERATE_RESOURCE_EXHAUSTION_HEAP_EVENTS
2313 );
2314 jvmtiCapField!(
2315 can_generate_resource_exhaustion_threads_events,
2316 set_can_generate_resource_exhaustion_threads_events,
2317 OFFSET_CAN_GENERATE_RESOURCE_EXHAUSTION_THREAD_EVENETS
2318 );
2319 jvmtiCapField!(can_generate_early_vmstart, set_can_generate_early_vmstart, OFFSET_CAN_GENERATE_EARLY_VMSTART);
2320 jvmtiCapField!(
2321 can_generate_early_class_hook_events,
2322 set_can_generate_early_class_hook_events,
2323 OFFSET_CAN_GENERATE_EARLY_CLASS_HOOK_EVENTS
2324 );
2325 jvmtiCapField!(
2326 can_generate_sampled_object_alloc_events,
2327 set_can_generate_sampled_object_alloc_events,
2328 OFFSET_CAN_GENERATE_SAMPLED_OBJECT_ALLOC_EVENTS
2329 );
2330 jvmtiCapField!(can_support_virtual_threads, set_can_support_virtual_threads, OFFSET_CAN_SUPPORT_VIRTUAL_THREADS);
2331}
2332
2333impl Display for jvmtiCapabilities {
2334 fn fmt(&self, f: &mut Formatter<'_>) -> core::fmt::Result {
2335 f.write_fmt(format_args!(
2336 "jvmtiCapabilities {{
2337 can_tag_objects: {}
2338 can_generate_field_modification_events: {}
2339 can_generate_field_access_events: {}
2340 can_get_bytecodes: {}
2341 can_get_synthetic_attribute: {}
2342 can_get_owned_monitor_info: {}
2343 can_get_current_contended_monitor: {}
2344 can_get_monitor_info: {}
2345 can_pop_frame: {}
2346 can_redefine_classes: {}
2347 can_signal_thread: {}
2348 can_get_source_file_name: {}
2349 can_get_line_numbers: {}
2350 can_get_source_debug_extension: {}
2351 can_access_local_variables: {}
2352 can_maintain_original_method_order: {}
2353 can_generate_single_step_events: {}
2354 can_generate_exception_events: {}
2355 can_generate_frame_pop_events: {}
2356 can_generate_breakpoint_events: {}
2357 can_suspend: {}
2358 can_redefine_any_class: {}
2359 can_get_current_thread_cpu_time: {}
2360 can_get_thread_cpu_time: {}
2361 can_generate_method_entry_events: {}
2362 can_generate_method_exit_events: {}
2363 can_generate_all_class_hook_events: {}
2364 can_generate_compiled_method_load_events: {}
2365 can_generate_monitor_events: {}
2366 can_generate_vm_object_alloc_events: {}
2367 can_generate_native_method_bind_events: {}
2368 can_generate_garbage_collection_events: {}
2369 can_generate_object_free_events: {}
2370 can_force_early_return: {}
2371 can_get_owned_monitor_stack_depth_info: {}
2372 can_get_constant_pool: {}
2373 can_set_native_method_prefix: {}
2374 can_retransform_classes: {}
2375 can_retransform_any_class: {}
2376 can_generate_resource_exhaustion_heap_events: {}
2377 can_generate_resource_exhaustion_threads_events: {}
2378 can_generate_early_vmstart: {}
2379 can_generate_early_class_hook_events: {}
2380 can_generate_sampled_object_alloc_events: {}
2381 can_support_virtual_threads: {}
2382}}",
2383 self.can_tag_objects(),
2384 self.can_generate_field_modification_events(),
2385 self.can_generate_field_access_events(),
2386 self.can_get_bytecodes(),
2387 self.can_get_synthetic_attribute(),
2388 self.can_get_owned_monitor_info(),
2389 self.can_get_current_contended_monitor(),
2390 self.can_get_monitor_info(),
2391 self.can_pop_frame(),
2392 self.can_redefine_classes(),
2393 self.can_signal_thread(),
2394 self.can_get_source_file_name(),
2395 self.can_get_line_numbers(),
2396 self.can_get_source_debug_extension(),
2397 self.can_access_local_variables(),
2398 self.can_maintain_original_method_order(),
2399 self.can_generate_single_step_events(),
2400 self.can_generate_exception_events(),
2401 self.can_generate_frame_pop_events(),
2402 self.can_generate_breakpoint_events(),
2403 self.can_suspend(),
2404 self.can_redefine_any_class(),
2405 self.can_get_current_thread_cpu_time(),
2406 self.can_get_thread_cpu_time(),
2407 self.can_generate_method_entry_events(),
2408 self.can_generate_method_exit_events(),
2409 self.can_generate_all_class_hook_events(),
2410 self.can_generate_compiled_method_load_events(),
2411 self.can_generate_monitor_events(),
2412 self.can_generate_vm_object_alloc_events(),
2413 self.can_generate_native_method_bind_events(),
2414 self.can_generate_garbage_collection_events(),
2415 self.can_generate_object_free_events(),
2416 self.can_force_early_return(),
2417 self.can_get_owned_monitor_stack_depth_info(),
2418 self.can_get_constant_pool(),
2419 self.can_set_native_method_prefix(),
2420 self.can_retransform_classes(),
2421 self.can_retransform_any_class(),
2422 self.can_generate_resource_exhaustion_heap_events(),
2423 self.can_generate_resource_exhaustion_threads_events(),
2424 self.can_generate_early_vmstart(),
2425 self.can_generate_early_class_hook_events(),
2426 self.can_generate_sampled_object_alloc_events(),
2427 self.can_support_virtual_threads(),
2428 ))
2429 }
2430}
2431
2432#[repr(C)]
2433#[derive(Debug, Default, Clone, Copy)]
2434pub struct jvmtiHeapReferenceInfoReserved {
2435 pub reserved1: jlong,
2436 pub reserved2: jlong,
2437 pub reserved3: jlong,
2438 pub reserved4: jlong,
2439 pub reserved5: jlong,
2440 pub reserved6: jlong,
2441 pub reserved7: jlong,
2442 pub reserved8: jlong,
2443}
2444
2445pub const JVMTI_HEAP_FILTER_TAGGED: jint = 0x4;
2446pub const JVMTI_HEAP_FILTER_UNTAGGED: jint = 0x8;
2447pub const JVMTI_HEAP_FILTER_CLASS_TAGGED: jint = 0x10;
2448pub const JVMTI_HEAP_FILTER_CLASS_UNTAGGED: jint = 0x20;
2449pub const JVMTI_VISIT_OBJECTS: jint = 0x100;
2450pub const JVMTI_VISIT_ABORT: jint = 0x8000;
2451
2452#[repr(C)]
2453#[derive(Debug, Eq, PartialEq, Copy, Clone, Hash, Ord, PartialOrd)]
2454pub enum jvmtiHeapReferenceKind {
2455 CLASS = 0x1,
2456 FIELD = 0x2,
2457 ARRAY_ELEMENT = 0x3,
2458 CLASS_LOADER = 0x4,
2459 SIGNERS = 0x5,
2460 PROTECTION_DOMAIN = 0x6,
2461 INTERFACE = 0x7,
2462 STATIC_FIELD = 0x8,
2463 CONSTANT_POOL = 0x9,
2464 SUPERCLASS = 0x10,
2465 JNI_GLOBAL = 0x21,
2466 SYSTEM_CLASS = 0x22,
2467 MONITOR = 0x23,
2468 STACK_LOCAL = 0x24,
2469 JNI_LOCAL = 0x25,
2470 THREAD = 0x26,
2471 OTHER = 0x27,
2472}
2473pub const JVMTI_HEAP_REFERENCE_CLASS: jint = 0x1;
2474
2475pub const JVMTI_HEAP_REFERENCE_FIELD: jint = 0x2;
2476pub const JVMTI_HEAP_REFERENCE_ARRAY_ELEMENT: jint = 0x3;
2477pub const JVMTI_HEAP_REFERENCE_CLASS_LOADER: jint = 0x4;
2478pub const JVMTI_HEAP_REFERENCE_SIGNERS: jint = 0x5;
2479pub const JVMTI_HEAP_REFERENCE_PROTECTION_DOMAIN: jint = 0x6;
2480pub const JVMTI_HEAP_REFERENCE_INTERFACE: jint = 0x7;
2481pub const JVMTI_HEAP_REFERENCE_STATIC_FIELD: jint = 0x8;
2482pub const JVMTI_HEAP_REFERENCE_CONSTANT_POOL: jint = 0x9;
2483pub const JVMTI_HEAP_REFERENCE_SUPERCLASS: jint = 0x10;
2484pub const JVMTI_HEAP_REFERENCE_JNI_GLOBAL: jint = 0x21;
2485pub const JVMTI_HEAP_REFERENCE_SYSTEM_CLASS: jint = 0x22;
2486pub const JVMTI_HEAP_REFERENCE_MONITOR: jint = 0x23;
2487pub const JVMTI_HEAP_REFERENCE_STACK_LOCAL: jint = 0x24;
2488pub const JVMTI_HEAP_REFERENCE_JNI_LOCAL: jint = 0x25;
2489pub const JVMTI_HEAP_REFERENCE_THREAD: jint = 0x26;
2490pub const JVMTI_HEAP_REFERENCE_OTHER: jint = 0x27;
2491
2492#[repr(C)]
2493#[derive(Debug, Eq, PartialEq, Copy, Clone, Hash, Ord, PartialOrd)]
2494pub enum jvmtiPrimitiveType {
2495 JVMTI_PRIMITIVE_TYPE_BOOLEAN = 90,
2496 JVMTI_PRIMITIVE_TYPE_BYTE = 66,
2497 JVMTI_PRIMITIVE_TYPE_CHAR = 67,
2498 JVMTI_PRIMITIVE_TYPE_SHORT = 83,
2499 JVMTI_PRIMITIVE_TYPE_INT = 73,
2500 JVMTI_PRIMITIVE_TYPE_LONG = 74,
2501 JVMTI_PRIMITIVE_TYPE_FLOAT = 70,
2502 JVMTI_PRIMITIVE_TYPE_DOUBLE = 68,
2503}
2504pub const JVMTI_PRIMITIVE_TYPE_BOOLEAN: c_int = 90;
2505pub const JVMTI_PRIMITIVE_TYPE_BYTE: c_int = 66;
2506pub const JVMTI_PRIMITIVE_TYPE_CHAR: c_int = 67;
2507pub const JVMTI_PRIMITIVE_TYPE_SHORT: c_int = 83;
2508pub const JVMTI_PRIMITIVE_TYPE_INT: c_int = 73;
2509pub const JVMTI_PRIMITIVE_TYPE_LONG: c_int = 74;
2510pub const JVMTI_PRIMITIVE_TYPE_FLOAT: c_int = 70;
2511pub const JVMTI_PRIMITIVE_TYPE_DOUBLE: c_int = 68;
2512
2513#[repr(C)]
2514#[derive(Debug, Default, Clone, Copy)]
2515pub struct jvmtiHeapReferenceInfoField {
2516 pub index: jint,
2517}
2518
2519#[repr(C)]
2520#[derive(Debug, Default, Clone, Copy)]
2521pub struct jvmtiHeapReferenceInfoArray {
2522 pub index: jint,
2523}
2524
2525#[repr(C)]
2526#[derive(Debug, Default, Clone, Copy)]
2527pub struct jvmtiHeapReferenceInfoConstantPool {
2528 pub index: jint,
2529}
2530
2531#[repr(C)]
2532#[derive(Debug, Clone, Copy)]
2533pub struct jvmtiHeapReferenceInfoStackLocal {
2534 pub thread_tag: jlong,
2535 pub thread_id: jlong,
2536 pub depth: jint,
2537 pub method: jmethodID,
2538 pub location: jlocation,
2539 pub slot: jint,
2540}
2541
2542impl Default for jvmtiHeapReferenceInfoStackLocal {
2543 fn default() -> Self {
2544 Self {
2545 thread_tag: 0,
2546 thread_id: 0,
2547 depth: 0,
2548 method: null_mut(),
2549 location: 0,
2550 slot: 0,
2551 }
2552 }
2553}
2554
2555#[repr(C)]
2556#[derive(Debug, Clone, Copy)]
2557pub struct jvmtiHeapReferenceInfoJniLocal {
2558 pub thread_tag: jlong,
2559 pub thread_id: jlong,
2560 pub depth: jint,
2561 pub method: jmethodID,
2562}
2563
2564impl Default for jvmtiHeapReferenceInfoJniLocal {
2565 fn default() -> Self {
2566 Self {
2567 thread_tag: 0,
2568 thread_id: 0,
2569 depth: 0,
2570 method: null_mut(),
2571 }
2572 }
2573}
2574
2575#[repr(C)]
2576pub union jvmtiHeapReferenceInfo {
2577 pub field: jvmtiHeapReferenceInfoField,
2578 pub array: jvmtiHeapReferenceInfoArray,
2579 pub constant_pool: jvmtiHeapReferenceInfoConstantPool,
2580 pub stack_local: jvmtiHeapReferenceInfoStackLocal,
2581 pub jni_local: jvmtiHeapReferenceInfoJniLocal,
2582 pub other: jvmtiHeapReferenceInfoReserved,
2583}
2584
2585pub type jvmtiHeapIterationCallback = extern "system" fn(class_tag: jlong, size: jlong, tag_ptr: *mut jlong, length: jint, user_data: *mut c_void) -> jint;
2586pub type jvmtiHeapReferenceCallback = extern "system" fn(
2587 reference_kind: jvmtiHeapReferenceKind,
2588 reference_info: *const jvmtiHeapReferenceInfo,
2589 class_tag: jlong,
2590 referrer_class_tag: jlong,
2591 size: jlong,
2592 tag_ptr: *mut jlong,
2593 referrer_tag_ptr: *mut jlong,
2594 length: jint,
2595 user_data: *mut c_void,
2596) -> jint;
2597
2598pub type jvmtiPrimitiveFieldCallback = extern "system" fn(
2599 kind: jvmtiHeapReferenceKind,
2600 info: *const jvmtiHeapReferenceInfo,
2601 object_class_tag: jlong,
2602 object_tag_ptr: *mut jlong,
2603 value: jvalue,
2604 value_type: jvmtiPrimitiveType,
2605 user_data: *mut c_void,
2606) -> jint;
2607
2608pub type jvmtiArrayPrimitiveValueCallback = extern "system" fn(
2609 class_tag: jlong,
2610 size: jlong,
2611 tag_ptr: *mut jlong,
2612 element_count: jint,
2613 element_type: jvmtiPrimitiveType,
2614 elements: *const c_void,
2615 user_data: *mut c_void,
2616) -> jint;
2617
2618pub type jvmtiStringPrimitiveValueCallback =
2619 extern "system" fn(class_tag: jlong, size: jlong, tag_ptr: *mut jlong, value: *const jchar, value_length: jint, user_data: *mut c_void) -> jint;
2620
2621pub type jvmtiReservedCallback = extern "system" fn() -> jint;
2622
2623#[repr(C)]
2624#[derive(Debug, Clone, Default)]
2625pub struct jvmtiHeapCallbacks {
2626 pub heap_iteration_callback: Option<jvmtiHeapIterationCallback>,
2627 pub heap_reference_callback: Option<jvmtiHeapReferenceCallback>,
2628 pub primitive_field_callback: Option<jvmtiPrimitiveFieldCallback>,
2629 pub array_primitive_value_callback: Option<jvmtiArrayPrimitiveValueCallback>,
2630 pub string_primitive_value_callback: Option<jvmtiStringPrimitiveValueCallback>,
2631 pub reserved5: Option<jvmtiReservedCallback>,
2632 pub reserved6: Option<jvmtiReservedCallback>,
2633 pub reserved7: Option<jvmtiReservedCallback>,
2634 pub reserved8: Option<jvmtiReservedCallback>,
2635 pub reserved9: Option<jvmtiReservedCallback>,
2636 pub reserved10: Option<jvmtiReservedCallback>,
2637 pub reserved11: Option<jvmtiReservedCallback>,
2638 pub reserved12: Option<jvmtiReservedCallback>,
2639 pub reserved13: Option<jvmtiReservedCallback>,
2640 pub reserved14: Option<jvmtiReservedCallback>,
2641 pub reserved15: Option<jvmtiReservedCallback>,
2642}
2643
2644#[derive(Debug, Default, Eq, PartialEq, Copy, Clone, Ord, PartialOrd, Hash)]
2645#[repr(C)]
2646pub enum jvmtiIterationControl {
2647 #[default]
2648 JVMTI_ITERATION_ABORT = 0,
2649 JVMTI_ITERATION_CONTINUE = 1,
2650 JVMTI_ITERATION_IGNORE = 2,
2651}
2652
2653/// jvmtiHeapRootKind cant enum this because we are called with it, making addition in a future version of JVMTI UB in rust.
2654pub type jvmtiHeapRootKind = c_int;
2655pub const JVMTI_HEAP_ROOT_JNI_GLOBAL: jvmtiHeapRootKind = 1;
2656pub const JVMTI_HEAP_ROOT_SYSTEM_CLASS: jvmtiHeapRootKind = 2;
2657pub const JVMTI_HEAP_ROOT_MONITOR: jvmtiHeapRootKind = 3;
2658pub const JVMTI_HEAP_ROOT_STACK_LOCAL: jvmtiHeapRootKind = 4;
2659pub const JVMTI_HEAP_ROOT_JNI_LOCAL: jvmtiHeapRootKind = 5;
2660pub const JVMTI_HEAP_ROOT_THREAD: jvmtiHeapRootKind = 6;
2661pub const JVMTI_HEAP_ROOT_OTHER: jvmtiHeapRootKind = 7;
2662
2663/// jvmtiHeapRootKind cant enum this because we are called with it, making addition in a future version of JVMTI UB in rust.
2664pub type jvmtiObjectReferenceKind = c_int;
2665
2666pub const JVMTI_REFERENCE_CLASS: jvmtiObjectReferenceKind = 1;
2667pub const JVMTI_REFERENCE_FIELD: jvmtiObjectReferenceKind = 2;
2668pub const JVMTI_REFERENCE_ARRAY_ELEMENT: jvmtiObjectReferenceKind = 3;
2669pub const JVMTI_REFERENCE_CLASS_LOADER: jvmtiObjectReferenceKind = 4;
2670pub const JVMTI_REFERENCE_SIGNERS: jvmtiObjectReferenceKind = 5;
2671pub const JVMTI_REFERENCE_PROTECTION_DOMAIN: jvmtiObjectReferenceKind = 6;
2672pub const JVMTI_REFERENCE_INTERFACE: jvmtiObjectReferenceKind = 7;
2673pub const JVMTI_REFERENCE_STATIC_FIELD: jvmtiObjectReferenceKind = 8;
2674pub const JVMTI_REFERENCE_CONSTANT_POOL: jvmtiObjectReferenceKind = 9;
2675
2676// GetClassStatus bitmask values
2677
2678/// Class bytecodes have been verified
2679pub const JVMTI_CLASS_STATUS_VERIFIED: jint = 1;
2680/// Class preparation is complete
2681pub const JVMTI_CLASS_STATUS_PREPARED: jint = 2;
2682/// Class initialization is complete. Static initializer has been run.
2683pub const JVMTI_CLASS_STATUS_INITIALIZED: jint = 4;
2684/// Error during initialization makes class unusable
2685pub const JVMTI_CLASS_STATUS_ERROR: jint = 8;
2686/// Class is an array. If set, all other bits are zero.
2687pub const JVMTI_CLASS_STATUS_ARRAY: jint = 16;
2688/// Class is a primitive class (for example, java.lang.Integer.TYPE). If set, all other bits are zero.
2689pub const JVMTI_CLASS_STATUS_PRIMITIVE: jint = 32;
2690
2691#[derive(Debug, Default, Eq, PartialEq, Copy, Clone, Ord, PartialOrd, Hash)]
2692#[repr(C)]
2693pub enum jvmtiHeapObjectFilter {
2694 JVMTI_HEAP_OBJECT_TAGGED = 1,
2695 JVMTI_HEAP_OBJECT_UNTAGGED = 2,
2696 #[default]
2697 JVMTI_HEAP_OBJECT_EITHER = 3,
2698}
2699
2700pub type jvmtiHeapObjectCallback = extern "system" fn(class_tag: jlong, size: jlong, tag_ptr: *mut jlong, user_data: *mut c_void) -> jvmtiIterationControl;
2701
2702pub type jvmtiHeapRootCallback =
2703 extern "system" fn(root_kind: jvmtiHeapRootKind, class_tag: jlong, size: jlong, tag_ptr: *mut jlong, user_data: *mut c_void) -> jvmtiIterationControl;
2704
2705pub type jvmtiStackReferenceCallback = extern "system" fn(
2706 root_kind: jvmtiHeapRootKind,
2707 class_tag: jlong,
2708 size: jlong,
2709 tag_ptr: *mut jlong,
2710 thread_tag: jlong,
2711 depth: jint,
2712 method: jmethodID,
2713 slot: jint,
2714 user_data: *mut c_void,
2715) -> jvmtiIterationControl;
2716
2717pub type jvmtiObjectReferenceCallback = extern "system" fn(
2718 reference_kind: jvmtiObjectReferenceKind,
2719 class_tag: jlong,
2720 size: jlong,
2721 tag_ptr: *mut jlong,
2722 referrer_tag: jlong,
2723 referrer_index: jint,
2724 user_data: *mut c_void,
2725) -> jvmtiIterationControl;
2726
2727impl From<jvmtiHeapIterationCallback> for jvmtiHeapCallbacks {
2728 fn from(value: jvmtiHeapIterationCallback) -> Self {
2729 Self {
2730 heap_iteration_callback: Some(value),
2731 ..Default::default()
2732 }
2733 }
2734}
2735
2736impl From<jvmtiHeapReferenceCallback> for jvmtiHeapCallbacks {
2737 fn from(value: jvmtiHeapReferenceCallback) -> Self {
2738 Self {
2739 heap_reference_callback: Some(value),
2740 ..Default::default()
2741 }
2742 }
2743}
2744
2745impl From<jvmtiPrimitiveFieldCallback> for jvmtiHeapCallbacks {
2746 fn from(value: jvmtiPrimitiveFieldCallback) -> Self {
2747 Self {
2748 primitive_field_callback: Some(value),
2749 ..Default::default()
2750 }
2751 }
2752}
2753
2754impl From<jvmtiArrayPrimitiveValueCallback> for jvmtiHeapCallbacks {
2755 fn from(value: jvmtiArrayPrimitiveValueCallback) -> Self {
2756 Self {
2757 array_primitive_value_callback: Some(value),
2758 ..Default::default()
2759 }
2760 }
2761}
2762
2763impl From<jvmtiStringPrimitiveValueCallback> for jvmtiHeapCallbacks {
2764 fn from(value: jvmtiStringPrimitiveValueCallback) -> Self {
2765 Self {
2766 string_primitive_value_callback: Some(value),
2767 ..Default::default()
2768 }
2769 }
2770}
2771
2772pub type jvmtiStartFunction = extern "system" fn(JVMTIEnv, JNIEnv, *mut c_void);
2773
2774#[derive(Debug, Clone, Copy)]
2775#[repr(C)]
2776pub struct jvmtiClassDefinition {
2777 pub klass: jclass,
2778 pub class_byte_count: jint,
2779 pub class_bytes: *const c_uchar,
2780}
2781
2782#[derive(Debug, Clone, Copy)]
2783#[repr(C)]
2784pub struct jvmtiMonitorUsage {
2785 pub owner: jthread,
2786 pub entry_count: jint,
2787 pub waiter_count: jint,
2788 pub waiters: *mut jthread,
2789 pub notify_waiter_count: jint,
2790 pub notify_waiters: *mut jthread,
2791}
2792
2793#[derive(Debug, Clone, Copy, Hash, Eq, PartialEq)]
2794#[repr(C)]
2795pub struct jvmtiLineNumberEntry {
2796 pub start_location: jlocation,
2797 pub line_number: jint,
2798}
2799
2800#[derive(Debug, Clone, Copy)]
2801#[repr(C)]
2802pub struct jvmtiLocalVariableEntry {
2803 pub start_location: jlocation,
2804 pub length: jint,
2805 pub name: *mut c_char,
2806 pub signature: *mut c_char,
2807 pub generic_signature: *mut c_char,
2808 pub slot: jint,
2809}
2810
2811/// Vtable of `JVMTIEnv` is passed like this.
2812type JVMTIEnvVTable = SyncMutPtr<*mut *mut c_void>;
2813
2814#[derive(Debug, Clone, Copy)]
2815#[repr(transparent)]
2816pub struct JVMTIEnv {
2817 /// The vtable that contains all the functions
2818 vtable: JVMTIEnvVTable,
2819}
2820
2821impl SealedEnvVTable for JVMTIEnv {
2822 fn can_jni() -> bool {
2823 false
2824 }
2825
2826 fn can_jvmti() -> bool {
2827 true
2828 }
2829}
2830
2831impl From<*mut c_void> for JVMTIEnv {
2832 #[allow(clippy::not_unsafe_ptr_arg_deref)]
2833 fn from(value: *mut c_void) -> Self {
2834 Self {
2835 vtable: value.as_sync_mut().cast(),
2836 }
2837 }
2838}
2839
2840impl JVMTIEnv {
2841 ///
2842 /// resolves the function pointer given its linkage index of the jvmt vtable.
2843 /// The indices are documented and guaranteed by the Oracle JVM Spec.
2844 /// NOTE: Oracle has documented them with index starting at 1 so you have to subtract 1!
2845 ///
2846 #[inline(always)]
2847 unsafe fn jvmti<X>(&self, index: usize) -> X {
2848 unsafe { core::mem::transmute_copy(&(self.vtable.read_volatile().add(index).read_volatile())) }
2849 }
2850
2851 /// Returns the raw jvmti vtable.
2852 /// Calling this function is usually not needed.
2853 #[must_use]
2854 pub const fn vtable(&self) -> *mut c_void {
2855 self.vtable.inner().cast()
2856 }
2857
2858 /// Return the JVM TI version via `version_ptr`.
2859 ///
2860 /// The return value is the version identifier.
2861 /// The version identifier includes major, minor and micro version as well as the interface type.
2862 ///
2863 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetVersionNumber>
2864 ///
2865 /// # Safety
2866 /// JVM Implementation dependant
2867 ///
2868 pub unsafe fn GetVersionNumber(&self, version_ptr: *mut jint) -> jvmtiError {
2869 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jint) -> jvmtiError>(87)(self.vtable, version_ptr) }
2870 }
2871
2872 /// Return the current phase of VM execution.
2873 ///
2874 /// The phases proceed in sequence:
2875 /// * `JVMTI_PHASE_ONLOAD` - `OnLoad` phase: while in the `Agent_OnLoad` or, for statically linked agents, the `Agent_OnLoad_<agent-lib-name>` function.
2876 /// * `JVMTI_PHASE_PRIMORDIAL` - `Primordial` phase: between return from `Agent_OnLoad` or `Agent_OnLoad_<agent-lib-name>` and the `VMStart` event.
2877 /// * `JVMTI_PHASE_START` - `Start` phase: when the `VMStart` event is sent and until the `VMInit` event is sent.
2878 /// * `JVMTI_PHASE_LIVE` - `Live` phase: when the `VMInit` event is sent and until the `VMDeath` event returns.
2879 /// * `JVMTI_PHASE_DEAD` - `Dead` phase: after the `VMDeath` event returns or after start-up failure.
2880 ///
2881 /// In the case of start-up failure the VM will proceed directly to the dead phase skipping
2882 /// intermediate phases and neither a `VMInit` nor `VMDeath` event will be sent.
2883 ///
2884 /// JNI functions (except the Invocation API) must only be used in the start or live phases.
2885 /// Most JVM TI events are sent only in the live phase.
2886 ///
2887 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetPhase>
2888 ///
2889 /// # Safety
2890 /// JVM Implementation dependant
2891 ///
2892 pub unsafe fn GetPhase(&self, phase: *mut jvmtiPhase) -> jvmtiError {
2893 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut c_int) -> jvmtiError>(132)(self.vtable, phase) }
2894 }
2895
2896 /// Allocate an area of memory through the JVM TI allocator.
2897 ///
2898 /// The allocated memory should be freed with Deallocate.
2899 ///
2900 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#Allocate>
2901 ///
2902 /// # Safety
2903 /// The receiver pointer must not be dangling.
2904 ///
2905 pub unsafe fn Allocate(&self, size: jlong, mem_ptr: *mut *mut c_uchar) -> jvmtiError {
2906 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jlong, *mut *mut c_uchar) -> jvmtiError>(45)(self.vtable, size, mem_ptr) }
2907 }
2908
2909 /// Deallocate mem using the JVM TI allocator.
2910 ///
2911 /// This function should be used to deallocate any memory allocated and returned by a JVM TI function (including memory allocated with Allocate).
2912 /// All allocated memory must be deallocated or the memory cannot be reclaimed.
2913 ///
2914 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#Deallocate>
2915 ///
2916 /// # Safety
2917 /// The pointer must have been allocated by the JVMTI allocator using allocate or returned by some JVMTI function.
2918 /// Naturally use after free problems may arise if the memory is used after this function is called.
2919 ///
2920 pub unsafe fn Deallocate<T>(&self, mem: *const T) -> jvmtiError {
2921 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const c_uchar) -> jvmtiError>(46)(self.vtable, mem.cast()) }
2922 }
2923
2924 /// Get the state of a thread.
2925 ///
2926 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetThreadState>
2927 ///
2928 /// # Safety
2929 /// The `thread` must be a valid strong reference to a thread.
2930 /// The `thread_state_ptr` must not be a dangling pointer.
2931 ///
2932 pub unsafe fn GetThreadState(&self, thread: jthread, thread_state_ptr: *mut jint) -> jvmtiError {
2933 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, *mut jint) -> jvmtiError>(16)(self.vtable, thread, thread_state_ptr) }
2934 }
2935
2936 /// Get the current thread.
2937 ///
2938 /// The current thread is the Java programming language thread which has called the function.
2939 /// The function may return a null pointer in the start phase if the `can_generate_early_vmstart` capability is enabled and the java.lang.Thread class has not been initialized yet.
2940 /// Note that most JVM TI functions that take a thread as an argument will accept null to mean the current thread.
2941 ///
2942 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetCurrentThread>
2943 ///
2944 /// # Safety
2945 /// The thread receiver pointer must not be dangling.
2946 ///
2947 pub unsafe fn GetCurrentThread(&self, thread: *mut jthread) -> jvmtiError {
2948 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jthread) -> jvmtiError>(17)(self.vtable, thread) }
2949 }
2950
2951 /// Get all live platform threads that are attached to the VM.
2952 ///
2953 /// The list of threads includes agent threads.
2954 /// It does not include virtual threads.
2955 /// A thread is live if `java.lang.Thread.isAlive()` would return true, that is, the thread has been started and has not yet terminated.
2956 /// The universe of threads is determined by the context of the JVM TI environment, which typically is all threads attached to the VM.
2957 ///
2958 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetAllThreads>
2959 ///
2960 /// # Safety
2961 /// All pointer parameters must not be dangling.
2962 ///
2963 pub unsafe fn GetAllThreads(&self, threads_count_ptr: *mut jint, threads_ptr: *mut *mut jthread) -> jvmtiError {
2964 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jint, *mut *mut jthread) -> jvmtiError>(3)(self.vtable, threads_count_ptr, threads_ptr) }
2965 }
2966
2967 /// Get all live platform threads that are attached to the VM as a Vec.
2968 /// Each jthread inside the returned Vec must be freed by the caller by calling `JniEnv::DeleteLocalRef`
2969 ///
2970 /// This convenience function automatically handles deallocating the memory using the jvmti allocator.
2971 ///
2972 /// The list of threads includes agent threads.
2973 /// It does not include virtual threads.
2974 /// A thread is live if `java.lang.Thread.isAlive()` would return true, that is, the thread has been started and has not yet terminated.
2975 /// The universe of threads is determined by the context of the JVM TI environment, which typically is all threads attached to the VM.
2976 ///
2977 /// # Safety
2978 /// JVM implementation specific.
2979 ///
2980 /// # Panics
2981 /// If the jvm returns unexpected data such as negative array lengths or null pointers without providing an error code.
2982 ///
2983 /// # Errors
2984 /// If the jvm fails to list the threads.
2985 ///
2986 pub unsafe fn GetAllThreads_as_vec(&self) -> Result<Vec<jthread>, jvmtiError> {
2987 unsafe {
2988 let mut count = 0;
2989 let mut threads_ptr = null_mut();
2990 self.GetAllThreads(&raw mut count, &raw mut threads_ptr).into_result()?;
2991 let count = usize::try_from(count).expect("JVMTI GetAllThreads provided an array with a negative number of threads");
2992 if count == 0 {
2993 if !threads_ptr.is_null() {
2994 _ = self.Deallocate(threads_ptr);
2995 }
2996 return Ok(Vec::new());
2997 }
2998
2999 assert!(
3000 !threads_ptr.is_null(),
3001 "JVMTI GetAllThreads returned a null pointer thread array without returning an error"
3002 );
3003 let result = core::slice::from_raw_parts(threads_ptr, count).to_vec();
3004 _ = self.Deallocate(threads_ptr);
3005 Ok(result)
3006 }
3007 }
3008
3009 /// Suspend the specified thread.
3010 ///
3011 /// If the calling thread is specified,
3012 /// this function will not return until some other thread calls `ResumeThread`.
3013 /// If the thread is currently suspended, this function does nothing and returns an error.
3014 ///
3015 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SuspendThread>
3016 ///
3017 /// # Safety
3018 /// The thread must be a valid strong reference to a thread.
3019 ///
3020 pub unsafe fn SuspendThread(&self, thread: jthread) -> jvmtiError {
3021 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread) -> jvmtiError>(4)(self.vtable, thread) }
3022 }
3023
3024 /// Suspend the `request_count` threads specified in the `request_list` array.
3025 ///
3026 /// Threads may be resumed with `ResumeThreadList` or `ResumeThread`.
3027 /// If the calling thread is specified in the `request_list` array, this function will not return until some other thread resumes it.
3028 /// Errors encountered in the suspension of a thread are returned in the results array, not in the return value of this function.
3029 /// Threads that are currently suspended do not change state.
3030 ///
3031 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SuspendThreadList>
3032 ///
3033 /// # Safety
3034 /// All threads must be valid strong references to a thread.
3035 /// the `request_list` parameter must be a valid array.
3036 /// None of the pointer parameters must be dangling.
3037 ///
3038 pub unsafe fn SuspendThreadList(&self, request_count: jint, request_list: *const jthread, results: *mut jvmtiError) -> jvmtiError {
3039 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint, *const jthread, *mut jvmtiError) -> jvmtiError>(91)(self.vtable, request_count, request_list, results) }
3040 }
3041
3042 /// Suspend all virtual threads except those in the exception list.
3043 /// Virtual threads that are currently suspended do not change state.
3044 /// Virtual threads may be resumed with `ResumeAllVirtualThreads` or `ResumeThreadList` or `ResumeThread`.
3045 ///
3046 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SuspendAllVirtualThreads>
3047 ///
3048 /// # Safety
3049 /// All threads must be valid strong references to a thread.
3050 /// the `except_list` and `except_count` parameter must be a valid array.
3051 /// `except_list` must not be a dangling pointer.
3052 ///
3053 pub unsafe fn SuspendAllVirtualThreads(&self, except_count: jint, except_list: *const jthread) -> jvmtiError {
3054 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint, *const jthread) -> jvmtiError>(117)(self.vtable, except_count, except_list) }
3055 }
3056
3057 /// Resume a suspended thread.
3058 ///
3059 /// Any threads currently suspended through a JVM TI suspend function (eg. `SuspendThread`) will resume execution;
3060 /// all other threads are unaffected.
3061 ///
3062 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ResumeThread>
3063 ///
3064 /// # Safety
3065 /// thread must refer to a valid strong reference to a thread.
3066 ///
3067 pub unsafe fn ResumeThread(&self, thread: jthread) -> jvmtiError {
3068 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread) -> jvmtiError>(5)(self.vtable, thread) }
3069 }
3070
3071 /// Resume the `request_count` threads specified in the `request_list` array.
3072 /// Any thread suspended through a JVM TI suspend function (eg. `SuspendThreadList`) will resume execution.
3073 ///
3074 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ResumeThreadList>
3075 ///
3076 /// # Safety
3077 /// All threads must be valid strong references to a thread.
3078 /// The `request_list` parameter must be a valid array.
3079 /// None of the pointer parameters must be dangling.
3080 ///
3081 pub unsafe fn ResumeThreadList(&self, request_count: jint, request_list: *const jthread, results: *mut jvmtiError) -> jvmtiError {
3082 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint, *const jthread, *mut jvmtiError) -> jvmtiError>(92)(self.vtable, request_count, request_list, results) }
3083 }
3084
3085 /// Resume all virtual threads except those in the exception list.
3086 /// Virtual threads that are currently resumed do not change state.
3087 /// Virtual threads may be suspended with `SuspendAllVirtualThreads` or `SuspendThreadList` or `SuspendThread`.
3088 ///
3089 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ResumeAllVirtualThreads>
3090 ///
3091 /// # Safety
3092 /// All threads must be valid strong references to a thread.
3093 /// The `except_list` and `except_count` parameter must be a valid array.
3094 /// `except_list` must not be a dangling pointer.
3095 ///
3096 pub unsafe fn ResumeAllVirtualThreads(&self, except_count: jint, except_list: *const jthread) -> jvmtiError {
3097 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint, *const jthread) -> jvmtiError>(118)(self.vtable, except_count, except_list) }
3098 }
3099
3100 /// Send the specified asynchronous exception to the specified thread.
3101 ///
3102 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#StopThread>
3103 ///
3104 /// # Safety
3105 /// thread must refer to a valid strong reference to a thread.
3106 /// exception must refer to a valid strong reference to a object.
3107 ///
3108 pub unsafe fn StopThread(&self, thread: jthread, exception: jobject) -> jvmtiError {
3109 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jobject) -> jvmtiError>(6)(self.vtable, thread, exception) }
3110 }
3111
3112 /// Interrupt the specified thread (similar to java.lang.Thread.interrupt).
3113 ///
3114 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#InterruptThread>
3115 ///
3116 /// # Safety
3117 /// thread must refer to a valid strong reference to a thread.
3118 ///
3119 pub unsafe fn InterruptThread(&self, thread: jthread) -> jvmtiError {
3120 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread) -> jvmtiError>(7)(self.vtable, thread) }
3121 }
3122
3123 /// Get thread information. The fields of the jvmtiThreadInfo structure are filled in with details of the specified thread.
3124 ///
3125 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetThreadInfo>
3126 ///
3127 /// # Safety
3128 /// thread must refer to a valid strong reference to a thread.
3129 /// `info_ptr` must not be dangling.
3130 ///
3131 pub unsafe fn GetThreadInfo(&self, thread: jthread, info_ptr: *mut jvmtiThreadInfo) -> jvmtiError {
3132 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, *mut jvmtiThreadInfo) -> jvmtiError>(8)(self.vtable, thread, info_ptr) }
3133 }
3134
3135 /// Get information about the monitors owned by the specified thread.
3136 ///
3137 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetOwnedMonitorInfo>
3138 ///
3139 /// # Safety
3140 /// thread must refer to a valid strong reference to a thread.
3141 /// pointer parameters must not be dangling.
3142 ///
3143 pub unsafe fn GetOwnedMonitorInfo(&self, thread: jthread, owned_monitor_count_ptr: *mut jint, owned_monitors_ptr: *mut *mut jobject) -> jvmtiError {
3144 unsafe {
3145 self.jvmti::<extern "system" fn(JVMTIEnvVTable, crate::jthread, *mut jint, *mut *mut jobject) -> jvmtiError>(9)(
3146 self.vtable,
3147 thread,
3148 owned_monitor_count_ptr,
3149 owned_monitors_ptr,
3150 )
3151 }
3152 }
3153
3154 /// Get information about the monitors owned by the specified thread and the depth of the stack frame which locked them.
3155 ///
3156 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetOwnedMonitorStackDepthInfo>
3157 ///
3158 /// # Safety
3159 /// thread must refer to a valid strong reference to a thread.
3160 /// pointer parameters must not be dangling.
3161 ///
3162 pub unsafe fn GetOwnedMonitorStackDepthInfo(&self, thread: jthread, monitor_info_count_ptr: *mut jint, monitor_info_ptr: *mut *mut jvmtiMonitorStackDepthInfo) -> jvmtiError {
3163 unsafe {
3164 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, *mut jint, *mut *mut jvmtiMonitorStackDepthInfo) -> jvmtiError>(152)(
3165 self.vtable,
3166 thread,
3167 monitor_info_count_ptr,
3168 monitor_info_ptr,
3169 )
3170 }
3171 }
3172
3173 /// Get the object, if any, whose monitor the specified thread is waiting to enter or waiting to regain through java.lang.Object.wait.
3174 ///
3175 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetCurrentContendedMonitor>
3176 ///
3177 /// # Safety
3178 /// `thread` must refer to a valid strong reference to a thread.
3179 /// `monitor_ptr` parameter must not be dangling.
3180 ///
3181 pub unsafe fn GetCurrentContendedMonitor(&self, thread: jthread, monitor_ptr: *mut jobject) -> jvmtiError {
3182 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, *mut jobject) -> jvmtiError>(10)(self.vtable, thread, monitor_ptr) }
3183 }
3184
3185 /// Starts the execution of an agent thread. with the specified native function.
3186 ///
3187 /// The parameter arg is forwarded on to the start function (specified with proc) as its single argument.
3188 /// This function allows the creation of agent threads for handling communication with another process or for handling events without the need to load a special subclass of java.lang.Thread or implementer of java.lang.Runnable.
3189 /// Instead, the created thread can run entirely in native code. However, the created thread does require a newly created instance of java.lang.Thread (referenced by the argument thread) to which it will be associated.
3190 /// The thread object can be created with JNI calls.
3191 ///
3192 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#RunAgentThread>
3193 ///
3194 /// # Safety
3195 /// `thread` must refer to a valid strong reference to a thread.
3196 /// `proc` must refer to a extern system fn with a matching signature.
3197 ///
3198 pub unsafe fn RunAgentThread(&self, thread: jthread, proc: jvmtiStartFunction, arg: *mut c_void, priority: jint) -> jvmtiError {
3199 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jvmtiStartFunction, *mut c_void, jint) -> jvmtiError>(11)(self.vtable, thread, proc, arg, priority) }
3200 }
3201
3202 /// Starts the execution of an agent thread. with the specified rust closure/function.
3203 ///
3204 /// This is a convenience function that automatically handles wrapping of a rust `FnOnce` to
3205 /// be invoked by the JVM in a new thread.
3206 ///
3207 /// In case of error the `proc` parameter is dropped without ever being executed.
3208 ///
3209 /// # Safety
3210 /// `thread` must refer to a valid strong reference to a thread.
3211 /// `proc` must not panic when called. (compile with panic=abort or use `panic::catch_unwind`.)
3212 /// # Example
3213 /// ```rust
3214 /// use jni_simple::{JNIEnv, JVMTIEnv};
3215 ///
3216 /// fn start_agent_thread(jvmti: JVMTIEnv, env: JNIEnv) {
3217 /// unsafe {
3218 /// //Do this once in your init function, remember to check for errors!
3219 /// let thread_class = env.FindClass("java/lang/Thread");
3220 /// let thread_constructor = env.GetMethodID(thread_class, "<init>", "()V");
3221 ///
3222 /// // Create a new java thread handle.
3223 /// let virgin_thread = env.NewObject0(thread_class, thread_constructor);
3224 /// // Customize your thread here as needed using jni. (set_name for example)
3225 ///
3226 /// eprintln!("JVMTI Agent thread {:?}", std::thread::current().id());
3227 ///
3228 /// jvmti.RunAgentThread_fn(virgin_thread, 1, |jvmti, env| {
3229 /// eprintln!("JVMTI Agent thread {:?}", std::thread::current().id());
3230 /// //...
3231 /// }).expect("Failed to start agent thread");
3232 /// }
3233 /// }
3234 /// ```
3235 ///
3236 pub unsafe fn RunAgentThread_fn(&self, thread: jthread, priority: jint, proc: impl FnOnce(Self, JNIEnv) + 'static + Send + Sync) -> jvmtiError {
3237 extern "system" fn agent_new_thread_wrapper_shim(jvmti: JVMTIEnv, env: JNIEnv, arg: *mut c_void) {
3238 // SAFETY: As long as the jvm passes us the pointer we gave it
3239 // and doesnt call this function in case of it returning an error we should be good.
3240 // Both of those assumptions are fair for any properly implemented jvm.
3241 unsafe { Box::from_raw(arg.cast::<Box<dyn FnOnce(JVMTIEnv, JNIEnv) + 'static + Send + Sync>>())(jvmti, env) };
3242 }
3243
3244 unsafe {
3245 let boxed = Box::new(proc) as Box<dyn FnOnce(Self, JNIEnv) + 'static + Send + Sync>;
3246 //We must double box it because otherwise we run into compiler error E0277.
3247 let raw_box = Box::into_raw(Box::new(boxed));
3248 let err = self.RunAgentThread(thread, agent_new_thread_wrapper_shim, raw_box.cast(), priority);
3249 if err.is_ok() {
3250 //No error we asssume agent_new_thread_wrapper_shim was or is going to be invoked.
3251 return err;
3252 }
3253
3254 // Reclaim the memory in case of error.
3255 // SAFETY: We assume the jvm did not call agent_new_thread_wrapper_shim with this pointer in case of error.
3256 _ = Box::from_raw(raw_box);
3257
3258 err
3259 }
3260 }
3261
3262 /// The VM stores a pointer value associated with each environment-thread pair.
3263 ///
3264 /// This pointer value is called thread-local storage.
3265 ///
3266 /// This value is null unless set with this function. Agents can allocate memory in which they store thread specific information.
3267 /// By setting thread-local storage it can then be accessed with `GetThreadLocalStorage`.
3268 /// This function is called by the agent to set the value of the JVM TI thread-local storage.
3269 /// JVM TI supplies to the agent a pointer-size thread-local storage that can be used to record per-thread information.
3270 ///
3271 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetThreadLocalStorage>
3272 ///
3273 /// # Safety
3274 /// `thread` must refer to a valid strong reference to a thread.
3275 ///
3276 pub unsafe fn SetThreadLocalStorage(&self, thread: jthread, data: *mut c_void) -> jvmtiError {
3277 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, *const c_void) -> jvmtiError>(102)(self.vtable, thread, data) }
3278 }
3279
3280 /// Called by the agent to get the value of the JVM TI thread-local storage.
3281 ///
3282 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetThreadLocalStorage>
3283 ///
3284 /// # Safety
3285 /// `thread` must refer to a valid strong reference to a thread.
3286 /// `data_ptr` must not be dangling.
3287 ///
3288 pub unsafe fn GetThreadLocalStorage(&self, thread: jthread, data_ptr: *mut *mut c_void) -> jvmtiError {
3289 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, *mut *mut c_void) -> jvmtiError>(101)(self.vtable, thread, data_ptr) }
3290 }
3291
3292 /// Return all top-level (parentless) thread groups in the VM.
3293 ///
3294 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetTopThreadGroups>
3295 ///
3296 /// # Safety
3297 /// all pointer parameters must not be dangling.
3298 ///
3299 pub unsafe fn GetTopThreadGroups(&self, group_count_ptr: *mut jint, groups_ptr: *mut *mut jthreadGroup) -> jvmtiError {
3300 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jint, *mut *mut jthreadGroup) -> jvmtiError>(12)(self.vtable, group_count_ptr, groups_ptr) }
3301 }
3302
3303 /// Return all top-level (parentless) thread groups in the VM.
3304 ///
3305 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetThreadGroupInfo>
3306 ///
3307 /// # Safety
3308 /// all pointer parameters must not be dangling.
3309 ///
3310 pub unsafe fn GetThreadGroupInfo(&self, group: jthreadGroup, info_ptr: *mut jvmtiThreadGroupInfo) -> jvmtiError {
3311 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthreadGroup, *mut jvmtiThreadGroupInfo) -> jvmtiError>(13)(self.vtable, group, info_ptr) }
3312 }
3313
3314 /// Get the live platform threads and the child thread groups in this thread group. Virtual threads are not returned by this function.
3315 ///
3316 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetThreadGroupChildren>
3317 ///
3318 /// # Safety
3319 /// all pointer parameters must not be dangling.
3320 ///
3321 pub unsafe fn GetThreadGroupChildren(
3322 &self,
3323 group: jthreadGroup,
3324 thread_count_ptr: *mut jint,
3325 threads_ptr: *mut *mut jthread,
3326 group_count_ptr: *mut jint,
3327 groups_ptr: *mut *mut jthreadGroup,
3328 ) -> jvmtiError {
3329 unsafe {
3330 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthreadGroup, *mut jint, *mut *mut jthread, *mut jint, *mut *mut jthreadGroup) -> jvmtiError>(14)(
3331 self.vtable,
3332 group,
3333 thread_count_ptr,
3334 threads_ptr,
3335 group_count_ptr,
3336 groups_ptr,
3337 )
3338 }
3339 }
3340
3341 /// Returns via `capabilities_ptr` the JVM TI features that can potentially be possessed by this environment at this time.
3342 /// The returned capabilities differ from the complete set of capabilities implemented by the VM in two cases:
3343 /// * another environment possesses capabilities that can only be possessed by one environment
3344 /// * the current phase is live, and certain capabilities can only be added during the `OnLoad` phase.
3345 ///
3346 /// The `AddCapabilities` function may be used to set any or all or these capabilities.
3347 /// Currently possessed capabilities are included.
3348 ///
3349 /// Typically this function is used in the `OnLoad` function.
3350 /// Some virtual machines may allow a limited set of capabilities to be added in the live phase.
3351 /// In this case, the set of potentially available capabilities will likely differ from the `OnLoad` phase set.
3352 ///
3353 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetPotentialCapabilities>
3354 ///
3355 /// # Safety
3356 /// `capabilities_ptr` pointer must not be dangling.
3357 ///
3358 pub unsafe fn GetPotentialCapabilities(&self, capabilities_ptr: *mut jvmtiCapabilities) -> jvmtiError {
3359 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jvmtiCapabilities) -> jvmtiError>(139)(self.vtable, capabilities_ptr) }
3360 }
3361
3362 /// Returns via `capabilities_ptr` the optional JVM TI features which this environment currently possesses.
3363 ///
3364 /// Each possessed capability is indicated by a one (1) in the corresponding bitfield of the capabilities structure.
3365 /// An environment does not possess a capability unless it has been successfully added with `AddCapabilities`.
3366 /// An environment only loses possession of a capability if it has been relinquished with `RelinquishCapabilities`.
3367 /// Thus, this function returns the net result of the `AddCapabilities` and `RelinquishCapabilities` calls which have been made.
3368 ///
3369 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetPotentialCapabilities>
3370 ///
3371 /// # Safety
3372 /// `capabilities_ptr` pointer must not be dangling.
3373 ///
3374 pub unsafe fn GetCapabilities(&self, capabilities_ptr: *mut jvmtiCapabilities) -> jvmtiError {
3375 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jvmtiCapabilities) -> jvmtiError>(88)(self.vtable, capabilities_ptr) }
3376 }
3377
3378 /// Set new capabilities by adding the capabilities whose values are set to one in `capabilities_ptr`.
3379 /// All previous capabilities are retained.
3380 /// Typically this function is used in the `OnLoad` function.
3381 /// Some virtual machines may allow a limited set of capabilities to be added in the live phase.
3382 ///
3383 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#AddCapabilities>
3384 ///
3385 /// # Safety
3386 /// `capabilities_ptr` pointer must not be dangling.
3387 ///
3388 pub unsafe fn AddCapabilities(&self, capabilities_ptr: *const jvmtiCapabilities) -> jvmtiError {
3389 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const jvmtiCapabilities) -> jvmtiError>(141)(self.vtable, capabilities_ptr) }
3390 }
3391
3392 /// Relinquish the capabilities whose values are set to one in `capabilities_ptr`.
3393 ///
3394 /// Some implementations may allow only one environment to have a capability.
3395 /// This function releases capabilities so that they may be used by other agents.
3396 /// All other capabilities are retained. The capability will no longer be present in `GetCapabilities`.
3397 /// Attempting to relinquish a capability that the agent does not possess is not an error.
3398 ///
3399 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#AddCapabilities>
3400 ///
3401 /// # Safety
3402 /// `capabilities_ptr` pointer must not be dangling.
3403 pub unsafe fn RelinquishCapabilities(&self, capabilities_ptr: *const jvmtiCapabilities) -> jvmtiError {
3404 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const jvmtiCapabilities) -> jvmtiError>(142)(self.vtable, capabilities_ptr) }
3405 }
3406
3407 /// Get the number of frames currently in the specified thread's call stack.
3408 ///
3409 /// If this function is called for a thread actively executing bytecodes
3410 /// (for example, not the current thread and not suspended),
3411 /// the information returned is transient.
3412 ///
3413 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetFrameCount>
3414 ///
3415 /// # Safety
3416 /// `count_ptr` pointer must not be dangling.
3417 pub unsafe fn GetFrameCount(&self, thread: jthread, count_ptr: *mut jint) -> jvmtiError {
3418 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, *mut jint) -> jvmtiError>(15)(self.vtable, thread, count_ptr) }
3419 }
3420
3421 /// Pop the current frame of thread's stack. Popping a frame takes you to the previous frame.
3422 ///
3423 /// When the thread is resumed, the execution state of the thread is reset to the state immediately before the called method was invoked.
3424 /// * the current frame is discarded as the previous frame becomes the current one
3425 /// * the operand stack is restored--the argument values are added back and if the invoke was not invokestatic, objectref is added back as well
3426 /// * the Java virtual machine PC is restored to the opcode of the invoke instruction
3427 ///
3428 /// Note however, that any changes to the arguments, which occurred in the called method, remain; when execution continues, the first instruction to execute will be the invoke.
3429 /// Between calling `PopFrame` and resuming the thread the state of the stack is undefined. To pop frames beyond the first, these three steps must be repeated:
3430 /// * suspend the thread via an event (step, breakpoint, ...)
3431 /// * call `PopFrame`
3432 /// * resume the thread
3433 ///
3434 /// A lock acquired by calling the called method (if it is a synchronized method)
3435 /// and locks acquired by entering synchronized blocks within the called method are released.
3436 /// Note: this does not apply to native locks or java.util.concurrent.locks locks.
3437 ///
3438 /// Finally blocks are not executed.
3439 /// Changes to global state are not addressed and thus remain changed.
3440 /// The specified thread must be suspended or must be the current thread.
3441 /// Both the called method and calling method must be non-native Java programming language methods.
3442 /// No JVM TI events are generated by this function.
3443 ///
3444 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#PopFrame>
3445 ///
3446 /// # Safety
3447 /// `thread` must refer to a valid strong reference to a thread.
3448 pub unsafe fn PopFrame(&self, thread: jthread) -> jvmtiError {
3449 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread) -> jvmtiError>(79)(self.vtable, thread) }
3450 }
3451
3452 /// For a Java programming language frame, return the location of the instruction currently executing.
3453 ///
3454 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetFrameLocation>
3455 ///
3456 /// # Safety
3457 /// `method_ptr` and `location_ptr` pointer must not be dangling.
3458 pub unsafe fn GetFrameLocation(&self, thread: jthread, depth: jint, method_ptr: *mut jmethodID, location_ptr: *mut jlocation) -> jvmtiError {
3459 unsafe {
3460 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, *mut jmethodID, *mut jlocation) -> jvmtiError>(18)(self.vtable, thread, depth, method_ptr, location_ptr)
3461 }
3462 }
3463
3464 /// When the frame that is currently at depth is popped from the stack,
3465 /// generate a `FramePop` event. See the `FramePop` event for details.
3466 /// Only frames corresponding to non-native Java programming language methods can receive notification.
3467 ///
3468 /// The specified thread must be suspended or must be the current thread.
3469 ///
3470 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#NotifyFramePop>
3471 ///
3472 /// # Safety
3473 /// `thread` must refer to a valid strong reference to a thread.
3474 pub unsafe fn NotifyFramePop(&self, thread: jthread, depth: jint) -> jvmtiError {
3475 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint) -> jvmtiError>(19)(self.vtable, thread, depth) }
3476 }
3477
3478 /// This function can be used to return from a method whose result type is Object or a subclass of Object.
3479 ///
3480 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ForceEarlyReturnObject>
3481 ///
3482 /// # Safety
3483 /// `thread` must refer to a valid strong reference to a thread.
3484 /// `value` must be a valid strong reference to a object or null.
3485 pub unsafe fn ForceEarlyReturnObject(&self, thread: jthread, value: jobject) -> jvmtiError {
3486 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jobject) -> jvmtiError>(80)(self.vtable, thread, value) }
3487 }
3488
3489 /// This function can be used to return from a method whose result type is int, short, char, byte, or boolean.
3490 ///
3491 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ForceEarlyReturnInt>
3492 ///
3493 /// # Safety
3494 /// `thread` must refer to a valid strong reference to a thread.
3495 pub unsafe fn ForceEarlyReturnInt(&self, thread: jthread, value: jint) -> jvmtiError {
3496 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint) -> jvmtiError>(81)(self.vtable, thread, value) }
3497 }
3498
3499 /// This function can be used to return from a method whose result type is long.
3500 ///
3501 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ForceEarlyReturnLong>
3502 ///
3503 /// # Safety
3504 /// `thread` must refer to a valid strong reference to a thread.
3505 pub unsafe fn ForceEarlyReturnLong(&self, thread: jthread, value: jlong) -> jvmtiError {
3506 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jlong) -> jvmtiError>(82)(self.vtable, thread, value) }
3507 }
3508
3509 /// This function can be used to return from a method whose result type is float.
3510 ///
3511 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ForceEarlyReturnFloat>
3512 ///
3513 /// # Safety
3514 /// `thread` must refer to a valid strong reference to a thread.
3515 pub unsafe fn ForceEarlyReturnFloat(&self, thread: jthread, value: jfloat) -> jvmtiError {
3516 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jfloat) -> jvmtiError>(83)(self.vtable, thread, value) }
3517 }
3518
3519 /// This function can be used to return from a method whose result type is double.
3520 ///
3521 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ForceEarlyReturnDouble>
3522 ///
3523 /// # Safety
3524 /// `thread` must refer to a valid strong reference to a thread.
3525 pub unsafe fn ForceEarlyReturnDouble(&self, thread: jthread, value: jdouble) -> jvmtiError {
3526 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jdouble) -> jvmtiError>(84)(self.vtable, thread, value) }
3527 }
3528
3529 /// This function can be used to return from a method with no result type. That is, the called method must be declared void.
3530 ///
3531 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ForceEarlyReturnVoid>
3532 ///
3533 /// # Safety
3534 /// `thread` must refer to a valid strong reference to a thread.
3535 pub unsafe fn ForceEarlyReturnVoid(&self, thread: jthread) -> jvmtiError {
3536 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread) -> jvmtiError>(85)(self.vtable, thread) }
3537 }
3538
3539 /// This function initiates a traversal over the objects that are directly and indirectly reachable from the specified object or, if `initial_object` is not specified, all objects reachable from the heap roots.
3540 ///
3541 /// The heap root are the set of system classes, JNI globals, references from platform thread stacks, and other objects used as roots for the purposes of garbage collection.
3542 ///
3543 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#FollowReferences>
3544 ///
3545 /// # Safety
3546 /// `klass` must be a valid strong reference to a class.
3547 /// `inital_object` must be a valid strong reference to a object.
3548 /// `callbacks` must not be a dangling pointer.
3549 pub unsafe fn FollowReferences(&self, heap_filter: jint, klass: jclass, initial_object: jobject, callbacks: *const jvmtiHeapCallbacks, user_data: *const c_void) -> jvmtiError {
3550 unsafe {
3551 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint, jclass, jobject, *const jvmtiHeapCallbacks, *const c_void) -> jvmtiError>(114)(
3552 self.vtable,
3553 heap_filter,
3554 klass,
3555 initial_object,
3556 callbacks,
3557 user_data,
3558 )
3559 }
3560 }
3561
3562 /// Initiate an iteration over all objects in the heap. This includes both reachable and unreachable objects.
3563 ///
3564 /// Objects are visited in no particular order.
3565 ///
3566 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IterateThroughHeap>
3567 ///
3568 /// # Safety
3569 /// `klass` must refer to a valid strong reference to a class.
3570 /// `callbacks` must not be a dangling pointer.
3571 pub unsafe fn IterateThroughHeap(&self, heap_filter: jint, klass: jclass, callbacks: *const jvmtiHeapCallbacks, user_data: *const c_void) -> jvmtiError {
3572 unsafe {
3573 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint, jclass, *const jvmtiHeapCallbacks, *const c_void) -> jvmtiError>(115)(
3574 self.vtable,
3575 heap_filter,
3576 klass,
3577 callbacks,
3578 user_data,
3579 )
3580 }
3581 }
3582
3583 /// Retrieve the tag associated with an object.
3584 ///
3585 /// The tag is a long value typically used to store a unique identifier or pointer to object information.
3586 /// The tag is set with `SetTag`. Objects for which no tags have been set return a tag value of zero.
3587 ///
3588 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetTag>
3589 ///
3590 /// # Safety
3591 /// `object` must refer to a valid strong reference to a class.
3592 /// `tag_ptr` must not be a dangling pointer.
3593 pub unsafe fn GetTag(&self, object: jobject, tag_ptr: *mut jlong) -> jvmtiError {
3594 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, *mut jlong) -> jvmtiError>(105)(self.vtable, object, tag_ptr) }
3595 }
3596
3597 /// Set the tag associated with an object.
3598 /// The tag is a long value typically used to store a unique identifier or pointer to object information.
3599 /// The tag is visible with `GetTag`.
3600 ///
3601 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetTag>
3602 ///
3603 /// # Safety
3604 /// `object` must refer to a valid strong reference to a class.
3605 pub unsafe fn SetTag(&self, object: jobject, tag: jlong) -> jvmtiError {
3606 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, jlong) -> jvmtiError>(106)(self.vtable, object, tag) }
3607 }
3608
3609 /// Return objects in the heap with the specified tags.
3610 ///
3611 /// The format is parallel arrays of objects and tags.
3612 ///
3613 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetObjectsWithTags>
3614 ///
3615 /// # Safety
3616 /// all pointer arguments must not be dangling.
3617 /// `tags` and `tag_count` must form a valid array.
3618 pub unsafe fn GetObjectsWithTags(
3619 &self,
3620 tag_count: jint,
3621 tags: *const jlong,
3622 count_ptr: *mut jint,
3623 object_result_ptr: *mut *mut jobject,
3624 tag_result_ptr: *mut *mut jlong,
3625 ) -> jvmtiError {
3626 unsafe {
3627 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint, *const jlong, *mut jint, *mut *mut jobject, *mut *mut jlong) -> jvmtiError>(113)(
3628 self.vtable,
3629 tag_count,
3630 tags,
3631 count_ptr,
3632 object_result_ptr,
3633 tag_result_ptr,
3634 )
3635 }
3636 }
3637
3638 /// Force the VM to perform a garbage collection.
3639 ///
3640 /// The garbage collection is as complete as possible.
3641 /// This function does not cause finalizers to be run.
3642 /// This function does not return until the garbage collection is finished.
3643 ///
3644 /// Although garbage collection is as complete as possible there is no guarantee
3645 /// that all `ObjectFree` events will have been sent by the time that this function returns.
3646 /// In particular, an object may be prevented from being freed because it is awaiting finalization.
3647 ///
3648 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ForceGarbageCollection>
3649 ///
3650 /// # Safety
3651 /// JVM Implementation dependant
3652 pub unsafe fn ForceGarbageCollection(&self) -> jvmtiError {
3653 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable) -> jvmtiError>(107)(self.vtable) }
3654 }
3655
3656 /// This function iterates over all objects that are directly and indirectly reachable from the specified object.
3657 ///
3658 /// For each object A (known as the referrer) with a reference to object B the specified callback function is called to describe the object reference.
3659 /// The callback is called exactly once for each reference from a referrer; this is true even if there are reference cycles or multiple paths to the referrer.
3660 /// There may be more than one reference between a referrer and a referree, These may be distinguished by the `jvmtiObjectReferenceCallback.reference_kind` and `jvmtiObjectReferenceCallback.referrer_index`.
3661 /// The callback for an object will always occur after the callback for its referrer.
3662 ///
3663 /// See `FollowReferences` for the object references which are reported.
3664 /// During the execution of this function the state of the heap does not change: no objects are allocated, no objects are garbage collected, and the state of objects (including held values) does not change.
3665 /// As a result, threads executing Java programming language code, threads attempting to resume the execution of Java programming language code, and threads attempting to execute JNI functions are typically stalled.
3666 ///
3667 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IterateOverObjectsReachableFromObject>
3668 ///
3669 /// # Safety
3670 /// `object_reference_callback` must be valid.
3671 /// `object` must be a valid strong reference to a object.
3672 #[deprecated(
3673 note = "This function was introduced in the original JVM TI version 1.0. It has been superseded in JVM TI version 1.2 (Java SE 6) and will be changed to return an error in a future release."
3674 )]
3675 pub unsafe fn IterateOverObjectsReachableFromObject(&self, object: jobject, object_reference_callback: jvmtiObjectReferenceCallback, user_data: *const c_void) -> jvmtiError {
3676 unsafe {
3677 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, jvmtiObjectReferenceCallback, *const c_void) -> jvmtiError>(108)(
3678 self.vtable,
3679 object,
3680 object_reference_callback,
3681 user_data,
3682 )
3683 }
3684 }
3685
3686 /// This function iterates over the root objects and all objects that are directly and indirectly reachable from the root objects.
3687 ///
3688 /// The root objects comprise the set of system classes, JNI globals, references from platform thread stacks,
3689 /// and other objects used as roots for the purposes of garbage collection.
3690 ///
3691 /// For each root the `heap_root_callback` or `stack_ref_callback` callback is called.
3692 /// An object can be a root object for more than one reason and in that case the appropriate callback is called for each reason.
3693 ///
3694 /// For each object reference the `object_ref_callback` callback function is called to describe the object reference.
3695 /// The callback is called exactly once for each reference from a referrer.
3696 /// This is true even if there are reference cycles or multiple paths to the referrer.
3697 /// There may be more than one reference between a referrer and a referree,
3698 /// These may be distinguished by the `jvmtiObjectReferenceCallback.reference_kind` and `jvmtiObjectReferenceCallback.referrer_index`.
3699 /// The callback for an object will always occur after the callback for its referrer.
3700 ///
3701 /// See `FollowReferences` for the object references which are reported.
3702 ///
3703 /// Roots are always reported to the profiler before any object references are reported.
3704 /// In other words, the `object_ref_callback` callback will not be called until the appropriate callback has been called for all roots.
3705 /// If the `object_ref_callback` callback is specified as null then this function returns after reporting the root objects to the profiler.
3706 ///
3707 /// During the execution of this function the state of the heap does not change: no objects are allocated,
3708 /// no objects are garbage collected, and the state of objects (including held values) does not change.
3709 /// As a result, threads executing Java programming language code,
3710 /// threads attempting to resume the execution of Java programming language code,
3711 /// and threads attempting to execute JNI functions are typically stalled.
3712 ///
3713 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IterateOverReachableObjects>
3714 ///
3715 /// # Safety
3716 /// the callback functions must be valid.
3717 #[deprecated(
3718 note = "This function was introduced in the original JVM TI version 1.0. It has been superseded in JVM TI version 1.2 (Java SE 6) and will be changed to return an error in a future release."
3719 )]
3720 pub unsafe fn IterateOverReachableObjects(
3721 &self,
3722 heap_root_callback: Option<jvmtiHeapRootCallback>,
3723 stack_ref_callback: Option<jvmtiStackReferenceCallback>,
3724 object_ref_callback: Option<jvmtiObjectReferenceCallback>,
3725 user_data: *const c_void,
3726 ) -> jvmtiError {
3727 unsafe {
3728 self.jvmti::<extern "system" fn(
3729 JVMTIEnvVTable,
3730 Option<jvmtiHeapRootCallback>,
3731 Option<jvmtiStackReferenceCallback>,
3732 Option<jvmtiObjectReferenceCallback>,
3733 *const c_void,
3734 ) -> jvmtiError>(109)(self.vtable, heap_root_callback, stack_ref_callback, object_ref_callback, user_data)
3735 }
3736 }
3737
3738 /// Iterate over all objects in the heap. This includes both reachable and unreachable objects.
3739 ///
3740 /// The `object_filter` parameter indicates the objects for which the callback function is called.
3741 ///
3742 /// If this parameter is `JVMTI_HEAP_OBJECT_TAGGED` then the callback will only be called for every object that is tagged.
3743 ///
3744 /// If the parameter is `JVMTI_HEAP_OBJECT_UNTAGGED` then the callback will only be for objects that are not tagged.
3745 ///
3746 /// If the parameter is `JVMTI_HEAP_OBJECT_EITHER` then the callback will be called for every object in the heap, irrespective of whether it is tagged or not.
3747 /// During the execution of this function the state of the heap does not change: no objects are allocated, no objects are garbage collected,
3748 /// and the state of objects (including held values) does not change.
3749 ///
3750 /// As a result, threads executing Java programming language code, threads attempting to resume the execution of Java programming language code,
3751 /// and threads attempting to execute JNI functions are typically stalled.
3752 ///
3753 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IterateOverHeap>
3754 ///
3755 /// # Safety
3756 /// the callback functions must be valid.
3757 #[deprecated(
3758 note = "This function was introduced in the original JVM TI version 1.0. It has been superseded in JVM TI version 1.2 (Java SE 6) and will be changed to return an error in a future release."
3759 )]
3760 pub unsafe fn IterateOverHeap(&self, object_filter: jvmtiHeapObjectFilter, heap_object_callback: jvmtiHeapObjectCallback, user_data: *const c_void) -> jvmtiError {
3761 unsafe {
3762 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jvmtiHeapObjectFilter, jvmtiHeapObjectCallback, *const c_void) -> jvmtiError>(110)(
3763 self.vtable,
3764 object_filter,
3765 heap_object_callback,
3766 user_data,
3767 )
3768 }
3769 }
3770
3771 /// Iterate over all objects in the heap that are instances of the specified class.
3772 ///
3773 /// This includes direct instances of the specified class and instances of all subclasses of the specified class.
3774 /// This includes both reachable and unreachable objects.
3775 ///
3776 /// The `object_filter` parameter indicates the objects for which the callback function is called.
3777 ///
3778 /// If this parameter is `JVMTI_HEAP_OBJECT_TAGGED` then the callback will only be called for every object that is tagged.
3779 ///
3780 /// If the parameter is `JVMTI_HEAP_OBJECT_UNTAGGED` then the callback will only be called for objects that are not tagged.
3781 ///
3782 /// If the parameter is `JVMTI_HEAP_OBJECT_EITHER` then the callback will be called for every object in the heap, irrespective of whether it is tagged or not.
3783 ///
3784 /// During the execution of this function the state of the heap does not change: no objects are allocated, no objects are garbage collected, and the state of objects (including held values) does not change.
3785 /// As a result, threads executing Java programming language code, threads attempting to resume the execution of Java programming language code, and threads attempting to execute JNI functions are typically stalled.
3786 ///
3787 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IterateOverInstancesOfClass>
3788 ///
3789 /// # Safety
3790 /// the callback functions must be valid.
3791 /// `klaas` parameter must be a valid strong reference.
3792 #[deprecated(
3793 note = "This function was introduced in the original JVM TI version 1.0. It has been superseded in JVM TI version 1.2 (Java SE 6) and will be changed to return an error in a future release."
3794 )]
3795 pub unsafe fn IterateOverInstancesOfClass(
3796 &self,
3797 klass: jclass,
3798 object_filter: jvmtiHeapObjectFilter,
3799 heap_object_callback: jvmtiHeapObjectCallback,
3800 user_data: *const c_void,
3801 ) -> jvmtiError {
3802 unsafe {
3803 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, jvmtiHeapObjectFilter, jvmtiHeapObjectCallback, *const c_void) -> jvmtiError>(111)(
3804 self.vtable,
3805 klass,
3806 object_filter,
3807 heap_object_callback,
3808 user_data,
3809 )
3810 }
3811 }
3812
3813 /// This function can be used to retrieve the value of a local variable whose type is Object or a subclass of Object.
3814 ///
3815 /// The specified thread must be suspended or must be the current thread.
3816 ///
3817 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetLocalObject>
3818 ///
3819 /// # Safety
3820 /// `thread` is a valid strong reference to a thread.
3821 /// `value_ptr` is not a dangling pointer.
3822 pub unsafe fn GetLocalObject(&self, thread: jthread, depth: jint, slot: jint, value_ptr: *mut jobject) -> jvmtiError {
3823 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, jint, *mut jobject) -> jvmtiError>(20)(self.vtable, thread, depth, slot, value_ptr) }
3824 }
3825
3826 /// This function can be used to retrieve the value of the local object variable at slot 0 (the "this" object) from non-static frames.
3827 ///
3828 /// This function can retrieve the "this" object from native method frames, whereas `GetLocalObject()` would return `JVMTI_ERROR_OPAQUE_FRAME` in those cases.
3829 /// The specified thread must be suspended or must be the current thread.
3830 ///
3831 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetLocalInstance>
3832 ///
3833 /// # Safety
3834 /// `thread` is a valid strong reference to a thread.
3835 /// `value_ptr` is not a dangling pointer.
3836 pub unsafe fn GetLocalInstance(&self, thread: jthread, depth: jint, value_ptr: *mut jobject) -> jvmtiError {
3837 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, *mut jobject) -> jvmtiError>(154)(self.vtable, thread, depth, value_ptr) }
3838 }
3839
3840 /// This function can be used to retrieve the value of a local variable whose type is int, short, char, byte, or boolean.
3841 ///
3842 /// The specified thread must be suspended or must be the current thread.
3843 ///
3844 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetLocalInt>
3845 ///
3846 /// # Safety
3847 /// `thread` is a valid strong reference to a thread.
3848 /// `value_ptr` is not a dangling pointer.
3849 pub unsafe fn GetLocalInt(&self, thread: jthread, depth: jint, slot: jint, value_ptr: *mut jint) -> jvmtiError {
3850 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, jint, *mut jint) -> jvmtiError>(21)(self.vtable, thread, depth, slot, value_ptr) }
3851 }
3852
3853 /// This function can be used to retrieve the value of a local variable whose type is long.
3854 ///
3855 /// The specified thread must be suspended or must be the current thread.
3856 ///
3857 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetLocalLong>
3858 ///
3859 /// # Safety
3860 /// `thread` is a valid strong reference to a thread.
3861 /// `value_ptr` is not a dangling pointer.
3862 pub unsafe fn GetLocalLong(&self, thread: jthread, depth: jint, slot: jint, value_ptr: *mut jlong) -> jvmtiError {
3863 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, jint, *mut jlong) -> jvmtiError>(22)(self.vtable, thread, depth, slot, value_ptr) }
3864 }
3865
3866 /// This function can be used to retrieve the value of a local variable whose type is float.
3867 ///
3868 /// The specified thread must be suspended or must be the current thread.
3869 ///
3870 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetLocalFloat>
3871 ///
3872 /// # Safety
3873 /// `thread` is a valid strong reference to a thread.
3874 /// `value_ptr` is not a dangling pointer.
3875 pub unsafe fn GetLocalFloat(&self, thread: jthread, depth: jint, slot: jint, value_ptr: *mut jfloat) -> jvmtiError {
3876 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, jint, *mut jfloat) -> jvmtiError>(23)(self.vtable, thread, depth, slot, value_ptr) }
3877 }
3878
3879 /// This function can be used to retrieve the value of a local variable whose type is double.
3880 ///
3881 /// The specified thread must be suspended or must be the current thread.
3882 ///
3883 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetLocalDouble>
3884 ///
3885 /// # Safety
3886 /// `thread` is a valid strong reference to a thread.
3887 /// `value_ptr` is not a dangling pointer.
3888 pub unsafe fn GetLocalDouble(&self, thread: jthread, depth: jint, slot: jint, value_ptr: *mut jdouble) -> jvmtiError {
3889 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, jint, *mut jdouble) -> jvmtiError>(24)(self.vtable, thread, depth, slot, value_ptr) }
3890 }
3891
3892 /// This function can be used to set the value of a local variable whose type is Object or a subclass of Object.
3893 ///
3894 /// The specified thread must be suspended or must be the current thread.
3895 ///
3896 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetLocalObject>
3897 ///
3898 /// # Safety
3899 /// `thread` is a valid strong reference to a thread.
3900 /// `value` is a valid strong reference or null.
3901 pub unsafe fn SetLocalObject(&self, thread: jthread, depth: jint, slot: jint, value: jobject) -> jvmtiError {
3902 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, jint, jobject) -> jvmtiError>(25)(self.vtable, thread, depth, slot, value) }
3903 }
3904
3905 /// This function can be used to set the value of a local variable whose type is int, short, char, byte, or boolean.
3906 ///
3907 /// The specified thread must be suspended or must be the current thread.
3908 ///
3909 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetLocalInt>
3910 ///
3911 /// # Safety
3912 /// `thread` is a valid strong reference to a thread.
3913 pub unsafe fn SetLocalInt(&self, thread: jthread, depth: jint, slot: jint, value: jint) -> jvmtiError {
3914 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, jint, jint) -> jvmtiError>(26)(self.vtable, thread, depth, slot, value) }
3915 }
3916
3917 /// This function can be used to set the value of a local variable whose type is long.
3918 ///
3919 /// The specified thread must be suspended or must be the current thread.
3920 ///
3921 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetLocalLong>
3922 ///
3923 /// # Safety
3924 /// `thread` is a valid strong reference to a thread.
3925 pub unsafe fn SetLocalLong(&self, thread: jthread, depth: jint, slot: jint, value: jlong) -> jvmtiError {
3926 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, jint, jlong) -> jvmtiError>(27)(self.vtable, thread, depth, slot, value) }
3927 }
3928
3929 /// This function can be used to set the value of a local variable whose type is float.
3930 ///
3931 /// The specified thread must be suspended or must be the current thread.
3932 ///
3933 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetLocalFloat>
3934 ///
3935 /// # Safety
3936 /// `thread` is a valid strong reference to a thread.
3937 pub unsafe fn SetLocalFloat(&self, thread: jthread, depth: jint, slot: jint, value: jfloat) -> jvmtiError {
3938 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, jint, jfloat) -> jvmtiError>(28)(self.vtable, thread, depth, slot, value) }
3939 }
3940
3941 /// This function can be used to set the value of a local variable whose type is double.
3942 ///
3943 /// The specified thread must be suspended or must be the current thread.
3944 ///
3945 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetLocalDouble>
3946 ///
3947 /// # Safety
3948 /// `thread` is a valid strong reference to a thread.
3949 pub unsafe fn SetLocalDouble(&self, thread: jthread, depth: jint, slot: jint, value: jdouble) -> jvmtiError {
3950 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, jint, jint, jdouble) -> jvmtiError>(29)(self.vtable, thread, depth, slot, value) }
3951 }
3952
3953 /// Set a breakpoint at the instruction indicated by method and location. An instruction can only have one breakpoint.
3954 /// Whenever the designated instruction is about to be executed, a Breakpoint event is generated.
3955 ///
3956 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetBreakpoint>
3957 ///
3958 /// # Safety
3959 /// `method` must be valid
3960 pub unsafe fn SetBreakpoint(&self, method: jmethodID, location: jlocation) -> jvmtiError {
3961 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, jlocation) -> jvmtiError>(37)(self.vtable, method, location) }
3962 }
3963
3964 /// Clear the breakpoint at the bytecode indicated by method and location.
3965 ///
3966 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ClearBreakpoint>
3967 ///
3968 /// # Safety
3969 /// `method` must be valid
3970 pub unsafe fn ClearBreakpoint(&self, method: jmethodID, location: jlocation) -> jvmtiError {
3971 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, jlocation) -> jvmtiError>(37)(self.vtable, method, location) }
3972 }
3973
3974 /// Generate a `FieldAccess` event when the field specified by klass and field is about to be accessed.
3975 ///
3976 /// An event will be generated for each access of the field until it is canceled with `ClearFieldAccessWatch`.
3977 /// Field accesses from Java programming language code or from JNI code are watched, fields modified by other means are not watched.
3978 /// Note that JVM TI users should be aware that their own field accesses will trigger the watch.
3979 /// A field can only have one field access watch set.
3980 /// Modification of a field is not considered an access--use `SetFieldModificationWatch` to monitor modifications.
3981 ///
3982 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetFieldAccessWatch>
3983 ///
3984 /// # Safety
3985 /// `klass` must be a valid strong reference to a class.
3986 /// `field` must be valid
3987 pub unsafe fn SetFieldAccessWatch(&self, klass: jclass, field: jfieldID) -> jvmtiError {
3988 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, jfieldID) -> jvmtiError>(40)(self.vtable, klass, field) }
3989 }
3990
3991 /// Cancel a field access watch previously set by `SetFieldAccessWatch`, on the field specified by klass and field.
3992 ///
3993 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ClearFieldAccessWatch>
3994 ///
3995 /// # Safety
3996 /// `klass` must be a valid strong reference to a class.
3997 /// `field` must be valid
3998 pub unsafe fn ClearFieldAccessWatch(&self, klass: jclass, field: jfieldID) -> jvmtiError {
3999 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, jfieldID) -> jvmtiError>(41)(self.vtable, klass, field) }
4000 }
4001
4002 /// Cancel a field modification watch previously set by `SetFieldModificationWatch`, on the field specified by klass and field.
4003 ///
4004 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetFieldModificationWatch>
4005 ///
4006 /// # Safety
4007 /// `klass` must be a valid strong reference to a class.
4008 /// `field` must be valid
4009 pub unsafe fn SetFieldModificationWatch(&self, klass: jclass, field: jfieldID) -> jvmtiError {
4010 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, jfieldID) -> jvmtiError>(42)(self.vtable, klass, field) }
4011 }
4012
4013 /// Cancel a field modification watch previously set by `SetFieldModificationWatch`, on the field specified by klass and field.
4014 ///
4015 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#ClearFieldModificationWatch>
4016 ///
4017 /// # Safety
4018 /// `klass` must be a valid strong reference to a class.
4019 /// `field` must be valid
4020 pub unsafe fn ClearFieldModificationWatch(&self, klass: jclass, field: jfieldID) -> jvmtiError {
4021 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, jfieldID) -> jvmtiError>(43)(self.vtable, klass, field) }
4022 }
4023
4024 /// Return an array of all modules loaded in the virtual machine.
4025 /// The array includes the unnamed module for each class loader.
4026 /// The number of modules in the array is returned via `module_count_ptr`, and the array itself via `modules_ptr`.
4027 ///
4028 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetAllModules>
4029 ///
4030 /// # Safety
4031 /// all pointer parameters must not be dangling.
4032 pub unsafe fn GetAllModules(&self, module_count_ptr: *mut jint, modules_ptr: *mut *mut jobject) -> jvmtiError {
4033 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jint, *mut *mut jobject) -> jvmtiError>(2)(self.vtable, module_count_ptr, modules_ptr) }
4034 }
4035
4036 ///
4037 /// Return an array of all modules loaded in the virtual machine as a Vec.
4038 /// The array includes the unnamed module for each class loader.
4039 ///
4040 /// This convenience function automatically handles deallocating the memory using the jvmti allocator.
4041 ///
4042 /// # Safety
4043 /// JVM implementation specific
4044 ///
4045 /// # Errors
4046 /// If the call to `GetAllModules` fails.
4047 /// Errors of the JVMTI Deallocator are silently ignored and the memory is leaked.
4048 ///
4049 /// # Panics
4050 /// If JVMTI provides a negative number of modules without returning an error.
4051 /// If JVMTI provides a null array of modules with a count of more than 0 without return return an error.
4052 pub unsafe fn GetAllModules_as_vec(&self) -> Result<Vec<jobject>, jvmtiError> {
4053 unsafe {
4054 let mut count: jsize = 0;
4055 let mut classes_ptr = null_mut();
4056 self.GetAllModules(&raw mut count, &raw mut classes_ptr).into_result()?;
4057
4058 //We dont risk deallocating the array in the panic case.
4059 let count = usize::try_from(count).expect("JVMTI GetAllModules provided an array with a negative number of modules.");
4060 if count == 0 {
4061 if !classes_ptr.is_null() {
4062 _ = self.Deallocate(classes_ptr);
4063 }
4064 return Ok(Vec::new());
4065 }
4066
4067 assert!(
4068 !classes_ptr.is_null(),
4069 "JVMTI GetAllModules returned a null pointer module array without returning an error"
4070 );
4071
4072 let result = core::slice::from_raw_parts(classes_ptr, count).to_vec();
4073 _ = self.Deallocate(classes_ptr);
4074
4075 Ok(result)
4076 }
4077 }
4078
4079 /// Return the java.lang.Module object for a named module defined to a class loader that contains a given package.
4080 ///
4081 /// The module is returned via `module_ptr`.
4082 /// If a named module is defined to the class loader and it contains the package then that named module is returned, otherwise null is returned.
4083 ///
4084 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetNamedModule>
4085 ///
4086 /// # Safety
4087 /// `class_loader` must be a valid strong reference or null
4088 /// all pointer parameters must not be dangling.
4089 pub unsafe fn GetNamedModule(&self, class_loader: jobject, package_name: impl UseCString, module_ptr: *mut jobject) -> jvmtiError {
4090 unsafe {
4091 package_name.use_as_const_c_char(|package_name| {
4092 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, *const c_char, *mut jobject) -> jvmtiError>(39)(self.vtable, class_loader, package_name, module_ptr)
4093 })
4094 }
4095 }
4096
4097 /// Update a module to read another module.
4098 ///
4099 /// This function is a no-op when module is an unnamed module.
4100 /// This function facilitates the instrumentation of code in named modules where that instrumentation requires expanding the set of modules that a module reads.
4101 ///
4102 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#AddModuleReads>
4103 ///
4104 /// # Safety
4105 /// `module` must be a valid strong reference or null
4106 /// `to_module` must be a valid strong reference or null
4107 pub unsafe fn AddModuleReads(&self, module: jobject, to_module: jobject) -> jvmtiError {
4108 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, jobject) -> jvmtiError>(93)(self.vtable, module, to_module) }
4109 }
4110
4111 /// Update a module to export a package to another module.
4112 ///
4113 /// This function is a no-op when module is an unnamed module or an open module.
4114 /// This function facilitates the instrumentation of code in named modules where that instrumentation requires expanding the set of packages that a module exports.
4115 ///
4116 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#AddModuleExports>
4117 ///
4118 /// # Safety
4119 /// `module` must be a valid strong reference or null
4120 /// `to_module` must be a valid strong reference or null
4121 /// all pointer parameters must not be dangling.
4122 pub unsafe fn AddModuleExports(&self, module: jobject, pkg_name: impl UseCString, to_module: jobject) -> jvmtiError {
4123 unsafe {
4124 pkg_name.use_as_const_c_char(|pkg_name| {
4125 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, *const c_char, jobject) -> jvmtiError>(94)(self.vtable, module, pkg_name, to_module)
4126 })
4127 }
4128 }
4129
4130 /// Update a module to open a package to another module.
4131 ///
4132 /// This function is a no-op when module is an unnamed module or an open module.
4133 /// This function facilitates the instrumentation of code in modules where that instrumentation requires expanding the set of packages that a module opens to other modules.
4134 ///
4135 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#AddModuleOpens>
4136 ///
4137 /// # Safety
4138 /// `module` must be a valid strong reference or null
4139 /// `to_module` must be a valid strong reference or null
4140 /// all pointer parameters must not be dangling.
4141 pub unsafe fn AddModuleOpens(&self, module: jobject, pkg_name: impl UseCString, to_module: jobject) -> jvmtiError {
4142 unsafe {
4143 pkg_name.use_as_const_c_char(|pkg_name| {
4144 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, *const c_char, jobject) -> jvmtiError>(95)(self.vtable, module, pkg_name, to_module)
4145 })
4146 }
4147 }
4148
4149 /// Updates a module to add a service to the set of services that a module uses.
4150 ///
4151 /// This function is a no-op when the module is an unnamed module.
4152 /// This function facilitates the instrumentation of code in named modules where that instrumentation requires expanding the set of services that a module is using.
4153 ///
4154 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#AddModuleUses>
4155 ///
4156 /// # Safety
4157 /// `module` must be a valid strong reference or null
4158 /// `service` must be a valid strong reference or null
4159 pub unsafe fn AddModuleUses(&self, module: jobject, service: jclass) -> jvmtiError {
4160 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, jclass) -> jvmtiError>(96)(self.vtable, module, service) }
4161 }
4162
4163 /// Updates a module to add a service to the set of services that a module provides.
4164 ///
4165 /// This function is a no-op when the module is an unnamed module.
4166 /// This function facilitates the instrumentation of code in named modules where that instrumentation requires changes to the services that are provided.
4167 ///
4168 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#AddModuleProvides>
4169 ///
4170 /// # Safety
4171 /// `module` must be a valid strong reference or null
4172 /// `service` must be a valid strong reference or null
4173 /// `impl_class` must be a valid strong reference or null
4174 pub unsafe fn AddModuleProvides(&self, module: jobject, service: jclass, impl_class: jclass) -> jvmtiError {
4175 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, jclass, jclass) -> jvmtiError>(97)(self.vtable, module, service, impl_class) }
4176 }
4177
4178 /// Determines whether a module is modifiable.
4179 ///
4180 /// If a module is modifiable then this module can be updated with `AddModuleReads`, `AddModuleExports`, `AddModuleOpens`, `AddModuleUses`, and `AddModuleProvides`.
4181 /// If a module is not modifiable then the module can not be updated with these functions.
4182 /// The result of this function is always `JNI_TRUE` when called to determine if an unnamed module is modifiable.
4183 ///
4184 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IsModifiableModule>
4185 ///
4186 /// # Safety
4187 /// `module` must be a valid strong reference or null
4188 /// `service` must be a valid strong reference or null
4189 /// `impl_class` must be a valid strong reference or null
4190 /// `is_modifiable_module_ptr` must not be dangling
4191 pub unsafe fn IsModifiableModule(&self, module: jobject, is_modifiable_module_ptr: impl JBooleanMutPtr) -> jvmtiError {
4192 is_modifiable_module_ptr.use_jboolean_mut(|is_modifiable_module_ptr| unsafe {
4193 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, *mut jboolean) -> jvmtiError>(98)(self.vtable, module, is_modifiable_module_ptr)
4194 })
4195 }
4196
4197 /// Return an array of all classes loaded in the virtual machine.
4198 ///
4199 /// The number of classes in the array is returned via `class_count_ptr`, and the array itself via `classes_ptr`.
4200 ///
4201 /// A class or interface creation can be triggered by one of the following:
4202 /// * By loading and deriving a class from a class file representation using a class loader (see The Java™ Virtual Machine Specification, Chapter 5.3).
4203 /// * By invoking `Lookup::defineHiddenClass` that creates a hidden class or interface from a class file representation.
4204 /// * By invoking methods in certain Java SE Platform APIs such as reflection.
4205 ///
4206 /// An array class is created directly by the Java virtual machine. The creation can be triggered by using class loaders or by invoking methods in certain Java SE Platform APIs such as reflection.
4207 /// The returned list includes all classes and interfaces, including hidden classes or interfaces, and also array classes of all types (including arrays of primitive types). Primitive classes (for example, java.lang.Integer.TYPE) are not included in the returned list.
4208 ///
4209 /// The returned array should be freed with Deallocate. The objects returned by `classes_ptr` are JNI local references and must be managed.
4210 ///
4211 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetLoadedClasses>
4212 ///
4213 /// # Safety
4214 /// all pointer parameters must not be dangling.
4215 pub unsafe fn GetLoadedClasses(&self, count_ptr: *mut jint, classes_ptr: *mut *mut jclass) -> jvmtiError {
4216 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jint, *mut *mut jclass) -> jvmtiError>(77)(self.vtable, count_ptr, classes_ptr) }
4217 }
4218
4219 ///
4220 /// Return a Vec of all classes loaded in the virtual machine.
4221 /// This convenience function will internally call `GetLoadedClasses` and `Deallocate`
4222 /// to manage the JVMTI buffer for you.
4223 ///
4224 /// This function ignores errors returned by the `Deallocate` and just, presumably, leaks the jvmti buffer.
4225 ///
4226 /// A class or interface creation can be triggered by one of the following:
4227 /// * By loading and deriving a class from a class file representation using a class loader (see The Java™ Virtual Machine Specification, Chapter 5.3).
4228 /// * By invoking `Lookup::defineHiddenClass` that creates a hidden class or interface from a class file representation.
4229 /// * By invoking methods in certain Java SE Platform APIs such as reflection.
4230 ///
4231 /// An array class is created directly by the Java virtual machine. The creation can be triggered by using class loaders or by invoking methods in certain Java SE Platform APIs such as reflection.
4232 /// The returned list includes all classes and interfaces, including hidden classes or interfaces, and also array classes of all types (including arrays of primitive types). Primitive classes (for example, java.lang.Integer.TYPE) are not included in the returned list.
4233 ///
4234 /// The objects returned in the `Vec` are JNI local references and must be managed.
4235 ///
4236 /// # Safety
4237 /// JVM implementation specific
4238 ///
4239 /// # Errors
4240 /// If the call to `GetLoadedClasses` fails.
4241 ///
4242 /// # Panics
4243 /// If JVMTI provides a negative number of loaded classes without returning an error.
4244 /// If JVMTI provides a null array of loaded classes with a count of more than 0 without return return an error.
4245 pub unsafe fn GetLoadedClasses_as_vec(&self) -> Result<Vec<jclass>, jvmtiError> {
4246 unsafe {
4247 let mut count: jsize = 0;
4248 let mut classes_ptr = null_mut();
4249 self.GetLoadedClasses(&raw mut count, &raw mut classes_ptr).into_result()?;
4250
4251 //We dont risk deallocating the array in the panic case.
4252 let count = usize::try_from(count).expect("JVMTI provided an array with a negative number of loaded classes.");
4253 if count == 0 {
4254 if !classes_ptr.is_null() {
4255 _ = self.Deallocate(classes_ptr);
4256 }
4257 return Ok(Vec::new());
4258 }
4259
4260 assert!(!classes_ptr.is_null(), "JVMTI returned a null pointer classes array without returning an error");
4261
4262 let result = core::slice::from_raw_parts(classes_ptr, count).to_vec();
4263 _ = self.Deallocate(classes_ptr);
4264
4265 Ok(result)
4266 }
4267 }
4268
4269 /// Returns an array of all classes which this class loader can find by name via `ClassLoader::loadClass`, `Class::forName` and bytecode linkage.
4270 ///
4271 /// That is, all classes for which `initiating_loader` has been recorded as an initiating loader.
4272 /// Each class in the returned array was created by this class loader, either by defining it directly or by delegation to another class loader.
4273 /// See The Java™ Virtual Machine Specification, Chapter 5.3.
4274 /// The returned list does not include hidden classes or interfaces or array classes whose element type is a hidden class or interface as they cannot be discovered by any class loader.
4275 /// The number of classes in the array is returned via `class_count_ptr`, and the array itself via `classes_ptr`.
4276 /// See `Lookup::defineHiddenClass`.
4277 ///
4278 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetClassLoaderClasses>
4279 ///
4280 /// # Safety
4281 /// `initiating_loader` must be a valid strong reference or null.
4282 /// all pointer parameters must not be dangling.
4283 pub unsafe fn GetClassLoaderClasses(&self, initiating_loader: jobject, count_ptr: *mut jint, classes_ptr: *mut *mut jclass) -> jvmtiError {
4284 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, *mut jint, *mut *mut jclass) -> jvmtiError>(78)(self.vtable, initiating_loader, count_ptr, classes_ptr) }
4285 }
4286
4287 /// Returns an Vec of all classes which this class loader can find by name via `ClassLoader::loadClass`, `Class::forName` and bytecode linkage.
4288 ///
4289 /// This convenience method takes care of deallocating the buffer returned by jvmti using the jvmti allocator.
4290 /// This method silently ignores errors from the jvmti allocator and leaks the memory in that case.
4291 ///
4292 /// That is, all classes for which `initiating_loader` has been recorded as an initiating loader.
4293 /// Each class in the returned array was created by this class loader, either by defining it directly or by delegation to another class loader.
4294 /// See The Java™ Virtual Machine Specification, Chapter 5.3.
4295 /// The returned list does not include hidden classes or interfaces or array classes whose element type is a hidden class or interface as they cannot be discovered by any class loader.
4296 /// The number of classes in the array is returned via `class_count_ptr`, and the array itself via `classes_ptr`.
4297 /// See `Lookup::defineHiddenClass`.
4298 ///
4299 /// # Errors
4300 /// If the call to `GetClassLoaderClasses` fails.
4301 ///
4302 /// # Panics
4303 /// If JVMTI provides a negative number of loaded classes without returning an error.
4304 /// If JVMTI provides a null array of loaded classes with a count of more than 0 without return return an error.
4305 ///
4306 /// # Safety
4307 /// `initiating_loader` must be a valid strong reference or null.
4308 pub unsafe fn GetClassLoaderClasses_as_vec(&self, initiating_loader: jobject) -> Result<Vec<jclass>, jvmtiError> {
4309 unsafe {
4310 let mut count: jsize = 0;
4311 let mut classes_ptr = null_mut();
4312 self.GetClassLoaderClasses(initiating_loader, &raw mut count, &raw mut classes_ptr).into_result()?;
4313
4314 //We dont risk deallocating the array in the panic case.
4315 let count = usize::try_from(count).expect("JVMTI GetClassLoaderClasses provided an array with a negative number of loaded classes.");
4316 if count == 0 {
4317 if !classes_ptr.is_null() {
4318 _ = self.Deallocate(classes_ptr);
4319 }
4320 return Ok(Vec::new());
4321 }
4322
4323 assert!(
4324 !classes_ptr.is_null(),
4325 "JVMTI GetClassLoaderClasses returned a null pointer classes array without returning an error"
4326 );
4327
4328 let result = core::slice::from_raw_parts(classes_ptr, count).to_vec();
4329 _ = self.Deallocate(classes_ptr);
4330
4331 Ok(result)
4332 }
4333 }
4334
4335 /// Return the name and the generic signature of the class indicated by klass.
4336 ///
4337 /// If the class is a class or interface, then:
4338 /// - If the class or interface is not hidden, then the returned name is the JNI type signature.
4339 /// For example, java.util.List is "Ljava/util/List;"
4340 /// - If the class or interface is hidden, then the returned name is a string of the form: "L" + N + "." + S + ";"
4341 /// where N is the binary name encoded in internal form (JVMS 4.2.1) indicated by the class file passed to `Lookup::defineHiddenClass`,
4342 /// and S is an unqualified name. The returned name is not a type descriptor and does not conform to JVMS 4.3.2.
4343 /// For example, com.foo.Foo/AnySuffix is "Lcom/foo/Foo.AnySuffix;"
4344 ///
4345 /// If the class indicated by klass represents an array class, then the returned name is a string consisting of one or more "[" characters representing the depth of the array nesting, followed by the class signature of the element type. For example the class signature of java.lang.String[] is "[Ljava/lang/String;" and that of int[] is "[I".
4346 /// If the class indicated by klass represents primitive type or void, then the returned name is the type signature character of the corresponding primitive type. For example, java.lang.Integer.TYPE is "I".
4347 ///
4348 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetClassSignature>
4349 ///
4350 /// # Safety
4351 /// `klass` must be a valid strong reference or null.
4352 /// all pointer parameters must not be dangling.
4353 ///
4354 /// # Example
4355 /// ```rust
4356 /// use jni_simple::*;
4357 /// use std::ptr::null_mut;
4358 /// use std::ffi::CStr;
4359 ///
4360 /// // would return "Ljava/lang/String;" for the string class for ex.
4361 /// fn get_class_name(jvmti: JVMTIEnv, class_or_iface: jclass) -> String {
4362 /// unsafe {
4363 /// let mut class_name = null_mut();
4364 /// assert!(jvmti.GetClassSignature(class_or_iface, &raw mut class_name, null_mut()).is_ok());
4365 /// //Beware, the string is in CESU encoding which may not work for some class names.
4366 /// let name : String = CStr::from_ptr(class_name).to_string_lossy().to_string();
4367 /// assert!(jvmti.Deallocate(class_name).is_ok());
4368 /// return name;
4369 /// }
4370 /// }
4371 /// ```
4372 ///
4373 pub unsafe fn GetClassSignature(&self, klass: jclass, signature_ptr: *mut *mut c_char, generic_ptr: *mut *mut c_char) -> jvmtiError {
4374 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut *mut c_char, *mut *mut c_char) -> jvmtiError>(47)(self.vtable, klass, signature_ptr, generic_ptr) }
4375 }
4376
4377 /// Get the status of the class. Zero or more of the following bits can be set.
4378 ///
4379 /// - `JVMTI_CLASS_STATUS_VERIFIED` - Class bytecodes have been verified
4380 /// - `JVMTI_CLASS_STATUS_PREPARED` - Class preparation is complete
4381 /// - `JVMTI_CLASS_STATUS_INITIALIZED` - Class initialization is complete. Static initializer has been run.
4382 /// - `JVMTI_CLASS_STATUS_ERROR` - Error during initialization makes class unusable
4383 /// - `JVMTI_CLASS_STATUS_ARRAY` - Class is an array. If set, all other bits are zero.
4384 /// - `JVMTI_CLASS_STATUS_PRIMITIVE` - Class is a primitive class (for example, java.lang.Integer.TYPE). If set, all other bits are zero.
4385 ///
4386 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetClassStatus>
4387 ///
4388 /// # Safety
4389 /// `klass` must be a valid strong reference or null.
4390 /// `status_ptr` must not be dangling.
4391 ///
4392 /// # Example
4393 /// ```rust
4394 /// use jni_simple::*;
4395 ///
4396 /// fn is_primitive_class(jvmti: JVMTIEnv, klass: jclass) -> bool {
4397 /// let mut status: jint = 0;
4398 /// unsafe {
4399 /// assert!(jvmti.GetClassStatus(klass, &raw mut status).is_ok());
4400 /// }
4401 /// status == JVMTI_CLASS_STATUS_PRIMITIVE
4402 /// }
4403 ///
4404 /// ```
4405 pub unsafe fn GetClassStatus(&self, klass: jclass, status_ptr: *mut jint) -> jvmtiError {
4406 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut jint) -> jvmtiError>(48)(self.vtable, klass, status_ptr) }
4407 }
4408
4409 /// For the class indicated by klass, return the source file name via `source_name_ptr`.
4410 ///
4411 /// The returned string is a file name only and never contains a directory name.
4412 ///
4413 /// For primitive classes (for example, java.lang.Integer.TYPE) and for arrays this function returns `JVMTI_ERROR_ABSENT_INFORMATION`.
4414 ///
4415 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetSourceFileName>
4416 ///
4417 /// # Safety
4418 /// `klass` must be a valid strong reference or null.
4419 /// `source_name_ptr` must not be dangling.
4420 pub unsafe fn GetSourceFileName(&self, klass: jclass, source_name_ptr: *mut *mut c_char) -> jvmtiError {
4421 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut *mut c_char) -> jvmtiError>(49)(self.vtable, klass, source_name_ptr) }
4422 }
4423
4424 /// For the class indicated by klass, return the source file name as a String.
4425 ///
4426 /// The returned string is a file name only and never contains a directory name.
4427 ///
4428 /// For primitive classes (for example, java.lang.Integer.TYPE) and for arrays this function returns `JVMTI_ERROR_ABSENT_INFORMATION`.
4429 ///
4430 /// This function serves as a convinence wrapper function and automatically handles JVMTI memory for you.
4431 ///
4432 /// # Errors
4433 /// This function will return `Err(JVMTI_ERROR_NONE)` in case the file name contains
4434 /// supplementary characters in CESU-8 encoding. Otherwise Err values always come from the jvm.
4435 ///
4436 /// # Safety
4437 /// `klass` must be a valid strong reference or null.
4438 /// `source_name_ptr` must not be dangling.
4439 pub unsafe fn GetSourceFileName_as_string(&self, klass: jclass) -> Result<String, jvmtiError> {
4440 unsafe {
4441 let mut str = null_mut();
4442 let res = self.GetSourceFileName(klass, &raw mut str);
4443 if !res.is_ok() {
4444 if !str.is_null() {
4445 _ = self.Deallocate(str);
4446 }
4447 return Err(res);
4448 }
4449
4450 if str.is_null() {
4451 //TODO should we panic here?
4452 return Ok(String::new());
4453 }
4454
4455 let Ok(val) = CStr::from_ptr(str).to_str() else {
4456 _ = self.Deallocate(str);
4457 //CESU-8 my old friend
4458 return Err(JVMTI_ERROR_NONE);
4459 };
4460
4461 let copy = val.to_string();
4462 _ = self.Deallocate(str);
4463
4464 Ok(copy)
4465 }
4466 }
4467
4468 /// For the class indicated by klass, return the access flags via `modifiers_ptr`.
4469 ///
4470 /// Access flags are defined in The Java™ Virtual Machine Specification, Chapter 4.
4471 ///
4472 /// If the class is an array class, then its public, private, and protected modifiers are the same as those of its component type.
4473 /// For arrays of primitives, this component type is represented by one of the primitive classes (for example, java.lang.Integer.TYPE).
4474 /// If the class is a primitive class, its public modifier is always true, and its protected and private modifiers are always false.
4475 /// If the class is an array class or a primitive class then its final modifier is always true and its interface modifier is always false.
4476 /// The values of its other modifiers are not determined by this specification.
4477 ///
4478 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetClassModifiers>
4479 ///
4480 /// # Safety
4481 /// `klass` must be a valid strong reference or null.
4482 /// `modifiers_ptr` must not be dangling.
4483 pub unsafe fn GetClassModifiers(&self, klass: jclass, modifiers_ptr: *mut jint) -> jvmtiError {
4484 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut jint) -> jvmtiError>(50)(self.vtable, klass, modifiers_ptr) }
4485 }
4486
4487 /// For the class indicated by klass, return a count of methods via `method_count_ptr` and a list of method IDs via `methods_ptr`.
4488 ///
4489 /// The method list contains constructors and static initializers as well as true methods.
4490 /// Only directly declared methods are returned (not inherited methods).
4491 /// An empty method list is returned for array classes and primitive classes (for example, java.lang.Integer.TYPE).
4492 ///
4493 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetClassMethods>
4494 ///
4495 /// # Safety
4496 /// `klass` must be a valid strong reference or null.
4497 /// `method_count_ptr` and `methods_ptr` must not be dangling.
4498 pub unsafe fn GetClassMethods(&self, klass: jclass, method_count_ptr: *mut jint, methods_ptr: *mut *mut jmethodID) -> jvmtiError {
4499 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut jint, *mut *mut jmethodID) -> jvmtiError>(51)(self.vtable, klass, method_count_ptr, methods_ptr) }
4500 }
4501
4502 /// Returns a Vec containing all methods of the class.
4503 /// This functions serves as a convenience function which calls `GetClassMethods`
4504 /// as well as free's the returned memory using the jvmti deallocator after copying the result
4505 /// to a Vec.
4506 ///
4507 /// The method list contains constructors and static initializers as well as true methods.
4508 /// Only directly declared methods are returned (not inherited methods).
4509 /// An empty method list is returned for array classes and primitive classes (for example, java.lang.Integer.TYPE).
4510 ///
4511 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetClassMethods>
4512 ///
4513 /// # Errors
4514 /// If `GetClassMethods` returns anything that is not `JVMTI_ERROR_NONE`
4515 /// Errors from the jvmti decallocator are silently ignored and the memory is leaked.
4516 ///
4517 /// # Panics
4518 /// if jvmti returns an array with a negative length or a null pointer array without
4519 /// returning an error code.
4520 ///
4521 /// # Safety
4522 /// `klass` must be a valid strong reference or null.
4523 pub unsafe fn GetClassMethods_as_vec(&self, klass: jclass) -> Result<Vec<jmethodID>, jvmtiError> {
4524 unsafe {
4525 let mut count: jsize = 0;
4526 let mut classes_ptr = null_mut();
4527 self.GetClassMethods(klass, &raw mut count, &raw mut classes_ptr).into_result()?;
4528
4529 //We dont risk deallocating the array in the panic case.
4530 let count = usize::try_from(count).expect("JVMTI GetClassMethods provided an array with a negative number of methods.");
4531 if count == 0 {
4532 if !classes_ptr.is_null() {
4533 _ = self.Deallocate(classes_ptr);
4534 }
4535 return Ok(Vec::new());
4536 }
4537
4538 assert!(
4539 !classes_ptr.is_null(),
4540 "JVMTI GetClassMethods returned a null pointer method array without returning an error"
4541 );
4542
4543 let result = core::slice::from_raw_parts(classes_ptr, count).to_vec();
4544 _ = self.Deallocate(classes_ptr);
4545
4546 Ok(result)
4547 }
4548 }
4549
4550 /// For the class indicated by klass, return a count of fields via `field_count_ptr` and a list of field IDs via `fields_ptr`.
4551 ///
4552 /// Only directly declared fields are returned (not inherited fields).
4553 /// Fields are returned in the order they occur in the class file.
4554 /// An empty field list is returned for array classes and primitive classes (for example, java.lang.Integer.TYPE).
4555 /// Use JNI to determine the length of an array.
4556 ///
4557 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetClassFields>
4558 ///
4559 /// # Safety
4560 /// `klass` must be a valid strong reference or null.
4561 /// `field_count_ptr` and `fields_ptr` must not be dangling.
4562 pub unsafe fn GetClassFields(&self, klass: jclass, field_count_ptr: *mut jint, fields_ptr: *mut *mut jfieldID) -> jvmtiError {
4563 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut jint, *mut *mut jfieldID) -> jvmtiError>(52)(self.vtable, klass, field_count_ptr, fields_ptr) }
4564 }
4565
4566 /// Returns a Vec containing all fields of the class.
4567 /// This functions serves as a convenience function which calls `GetClassFields`
4568 /// as well as free's the returned memory using the jvmti deallocator after copying the result
4569 /// to a Vec.
4570 ///
4571 /// Only directly declared fields are returned (not inherited fields).
4572 /// Fields are returned in the order they occur in the class file.
4573 /// An empty field list is returned for array classes and primitive classes (for example, java.lang.Integer.TYPE).
4574 /// Use JNI to determine the length of an array.
4575 ///
4576 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetClassFields>
4577 ///
4578 /// # Errors
4579 /// If `GetClassFields` returns anything that is not `JVMTI_ERROR_NONE`
4580 /// Errors from the jvmti decallocator are silently ignored and the memory is leaked.
4581 ///
4582 /// # Panics
4583 /// If jvmti returns an array with a negative length or a null pointer array without
4584 /// returning an error code.
4585 ///
4586 /// # Safety
4587 /// `klass` must be a valid strong reference or null.
4588 pub unsafe fn GetClassFields_as_vec(&self, klass: jclass) -> Result<Vec<jfieldID>, jvmtiError> {
4589 unsafe {
4590 let mut count: jsize = 0;
4591 let mut classes_ptr = null_mut();
4592 self.GetClassFields(klass, &raw mut count, &raw mut classes_ptr).into_result()?;
4593
4594 //We dont risk deallocating the array in the panic case.
4595 let count = usize::try_from(count).expect("JVMTI GetClassFields provided an array with a negative number of methods.");
4596 if count == 0 {
4597 if !classes_ptr.is_null() {
4598 _ = self.Deallocate(classes_ptr);
4599 }
4600 return Ok(Vec::new());
4601 }
4602
4603 assert!(
4604 !classes_ptr.is_null(),
4605 "JVMTI GetClassFields returned a null pointer method array without returning an error"
4606 );
4607
4608 let result = core::slice::from_raw_parts(classes_ptr, count).to_vec();
4609 _ = self.Deallocate(classes_ptr);
4610
4611 Ok(result)
4612 }
4613 }
4614
4615 /// Return the direct super-interfaces of this class. For a class, this function returns the interfaces declared in its implements clause.
4616 ///
4617 /// For an interface, this function returns the interfaces declared in its extends clause.
4618 /// An empty interface list is returned for array classes and primitive classes (for example, java.lang.Integer.TYPE).
4619 ///
4620 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetImplementedInterfaces>
4621 ///
4622 /// # Safety
4623 /// `klass` must be a valid strong reference or null.
4624 /// `interface_count_ptr` and `interfaces_ptr` must not be dangling.
4625 pub unsafe fn GetImplementedInterfaces(&self, klass: jclass, interface_count_ptr: *mut jint, interfaces_ptr: *mut *mut jclass) -> jvmtiError {
4626 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut jint, *mut *mut jclass) -> jvmtiError>(53)(self.vtable, klass, interface_count_ptr, interfaces_ptr) }
4627 }
4628
4629 /// Return the direct super-interfaces of this class. For a class, this function returns the interfaces declared in its implements clause.
4630 ///
4631 /// For an interface, this function returns the interfaces declared in its extends clause.
4632 /// An empty interface list is returned for array classes and primitive classes (for example, java.lang.Integer.TYPE).
4633 ///
4634 /// # Errors
4635 /// If `GetImplementedInterfaces` returns anything that is not `JVMTI_ERROR_NONE`
4636 /// Errors from the jvmti decallocator are silently ignored and the memory is leaked.
4637 ///
4638 /// # Panics
4639 /// If jvmti returns an array with a negative length or a null pointer array without
4640 /// returning an error code.
4641 ///
4642 /// # Safety
4643 /// `klass` must be a valid strong reference or null.
4644 pub unsafe fn GetImplementedInterfaces_as_vec(&self, klass: jclass) -> Result<Vec<jclass>, jvmtiError> {
4645 unsafe {
4646 let mut count: jsize = 0;
4647 let mut classes_ptr = null_mut();
4648 self.GetImplementedInterfaces(klass, &raw mut count, &raw mut classes_ptr).into_result()?;
4649
4650 //We dont risk deallocating the array in the panic case.
4651 let count = usize::try_from(count).expect("JVMTI GetImplementedInterfaces provided an array with a negative number of classes.");
4652 if count == 0 {
4653 if !classes_ptr.is_null() {
4654 _ = self.Deallocate(classes_ptr);
4655 }
4656 return Ok(Vec::new());
4657 }
4658
4659 assert!(
4660 !classes_ptr.is_null(),
4661 "JVMTI GetImplementedInterfaces returned a null pointer class array without returning an error"
4662 );
4663
4664 let result = core::slice::from_raw_parts(classes_ptr, count).to_vec();
4665 _ = self.Deallocate(classes_ptr);
4666
4667 Ok(result)
4668 }
4669 }
4670
4671 /// For the class indicated by klass, return the minor and major version numbers, as defined in The Java™ Virtual Machine Specification, Chapter 4.
4672 ///
4673 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetClassVersionNumbers>
4674 ///
4675 /// # Safety
4676 /// `klass` must be a valid strong reference or null.
4677 /// `minor_version_ptr` and `major_version_ptr` must not be dangling.
4678 pub unsafe fn GetClassVersionNumbers(&self, klass: jclass, minor_version_ptr: *mut jint, major_version_ptr: *mut jint) -> jvmtiError {
4679 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut jint, *mut jint) -> jvmtiError>(144)(self.vtable, klass, minor_version_ptr, major_version_ptr) }
4680 }
4681
4682 /// For the class indicated by klass, return the raw bytes of the constant pool in the format of the `constant_pool` item of The Java™ Virtual Machine Specification, Chapter 4.
4683 ///
4684 /// The format of the constant pool may differ between versions of the Class File Format, so, the minor and major class version numbers should be checked for compatibility.
4685 ///
4686 /// The returned constant pool might not have the same layout or contents as the constant pool in the defining class file.
4687 /// The constant pool returned by `GetConstantPool()` may have more or fewer entries than the defining constant pool.
4688 /// Entries may be in a different order. The constant pool returned by `GetConstantPool()` will match the constant pool used by `GetBytecodes()`.
4689 /// That is, the bytecodes returned by `GetBytecodes()` will have constant pool indices which refer to constant pool entries returned by `GetConstantPool()`.
4690 /// Note that since `RetransformClasses` and `RedefineClasses` can change the constant pool, the constant pool returned by this function can change accordingly.
4691 /// Thus, the correspondence between `GetConstantPool()` and `GetBytecodes()` does not hold if there is an intervening class retransformation or redefinition.
4692 /// The value of a constant pool entry used by a given bytecode will match that of the defining class file (even if the indices don't match).
4693 /// Constant pool entries which are not used directly or indirectly by bytecodes (for example, UTF-8 strings associated with annotations) are not required to exist in the returned constant pool.
4694 ///
4695 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetConstantPool>
4696 ///
4697 /// # Safety
4698 /// `klass` must be a valid strong reference or null.
4699 /// all pointer parameters must not be dangling.
4700 pub unsafe fn GetConstantPool(
4701 &self,
4702 klass: jclass,
4703 constant_pool_count_ptr: *mut jint,
4704 constant_pool_byte_count_ptr: *mut jint,
4705 constant_pool_bytes_ptr: *mut *mut c_uchar,
4706 ) -> jvmtiError {
4707 unsafe {
4708 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut jint, *mut jint, *mut *mut c_uchar) -> jvmtiError>(145)(
4709 self.vtable,
4710 klass,
4711 constant_pool_count_ptr,
4712 constant_pool_byte_count_ptr,
4713 constant_pool_bytes_ptr,
4714 )
4715 }
4716 }
4717
4718 /// Determines whether a class object reference represents an interface.
4719 /// The jboolean result is `JNI_TRUE` if the "class" is actually an interface,
4720 /// `JNI_FALSE` otherwise.
4721 ///
4722 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IsInterface>
4723 ///
4724 /// # Safety
4725 /// `klass` must be a valid strong reference or null.
4726 /// all pointer parameters must not be dangling.
4727 pub unsafe fn IsInterface(&self, klass: jclass, is_interface_ptr: impl JBooleanMutPtr) -> jvmtiError {
4728 is_interface_ptr.use_jboolean_mut(|is_interface_ptr| unsafe {
4729 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut jboolean) -> jvmtiError>(54)(self.vtable, klass, is_interface_ptr)
4730 })
4731 }
4732
4733 /// Determines whether a class object reference represents an array.
4734 /// The jboolean result is true if the class is an array, false otherwise.
4735 ///
4736 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IsArrayClass>
4737 ///
4738 /// # Safety
4739 /// `klass` must be a valid strong reference or null.
4740 /// all pointer parameters must not be dangling.
4741 pub unsafe fn IsArrayClass(&self, klass: jclass, is_array_class_ptr: impl JBooleanMutPtr) -> jvmtiError {
4742 is_array_class_ptr.use_jboolean_mut(|is_array_class_ptr| unsafe {
4743 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut jboolean) -> jvmtiError>(55)(self.vtable, klass, is_array_class_ptr)
4744 })
4745 }
4746
4747 /// Determines whether a class is modifiable.
4748 ///
4749 /// If a class is modifiable (`is_modifiable_class_ptr` returns `JNI_TRUE`)
4750 /// the class can be redefined with `RedefineClasses` (assuming the agent possesses the `can_redefine_classes` capability)
4751 /// or retransformed with `RetransformClasses` (assuming the agent possesses the `can_retransform_classes` capability).
4752 /// If a class is not modifiable (`is_modifiable_class_ptr` returns `JNI_FALSE`) the class can be neither redefined nor retransformed.
4753 /// Primitive classes (for example, java.lang.Integer.TYPE), array classes, and some implementation defined classes are never modifiable.
4754 ///
4755 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IsModifiableClass>
4756 ///
4757 /// # Safety
4758 /// `klass` must be a valid strong reference or null.
4759 /// all pointer parameters must not be dangling.
4760 pub unsafe fn IsModifiableClass(&self, klass: jclass, is_modifiable_class_ptr: impl JBooleanMutPtr) -> jvmtiError {
4761 is_modifiable_class_ptr.use_jboolean_mut(|is_modifiable_class_ptr| unsafe {
4762 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut jboolean) -> jvmtiError>(44)(self.vtable, klass, is_modifiable_class_ptr)
4763 })
4764 }
4765
4766 /// For the class indicated by klass, return via `classloader_ptr` a reference to the class loader for the class.
4767 ///
4768 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IsModifiableClass>
4769 ///
4770 /// # Safety
4771 /// `klass` must be a valid strong reference or null.
4772 /// all pointer parameters must not be dangling.
4773 pub unsafe fn GetClassLoader(&self, klass: jclass, classloader_ptr: *mut jobject) -> jvmtiError {
4774 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut jobject) -> jvmtiError>(56)(self.vtable, klass, classloader_ptr) }
4775 }
4776
4777 /// For the class indicated by klass, return the debug extension via `source_debug_extension_ptr`.
4778 /// The returned string contains exactly the debug extension information present in the class file of klass.
4779 ///
4780 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetSourceDebugExtension>
4781 ///
4782 /// # Safety
4783 /// `klass` must be a valid strong reference or null.
4784 /// all pointer parameters must not be dangling.
4785 pub unsafe fn GetSourceDebugExtension(&self, klass: jclass, source_debug_extension_ptr: *mut *mut c_char) -> jvmtiError {
4786 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, *mut *mut c_char) -> jvmtiError>(89)(self.vtable, klass, source_debug_extension_ptr) }
4787 }
4788
4789 /// This function facilitates the bytecode instrumentation of already loaded classes.
4790 ///
4791 /// To replace the class definition without reference to the existing bytecodes,
4792 /// as one might do when recompiling from source for fix-and-continue debugging,
4793 /// `RedefineClasses` function should be used instead.
4794 ///
4795 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#RetransformClasses>
4796 ///
4797 /// # Safety
4798 /// `klass` must be a valid strong reference or null.
4799 /// all pointer parameters must not be dangling.
4800 pub unsafe fn RetransformClasses(&self, class_count: jint, classes: *const jclass) -> jvmtiError {
4801 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint, *const jclass) -> jvmtiError>(151)(self.vtable, class_count, classes) }
4802 }
4803
4804 /// All classes given are redefined according to the definitions supplied.
4805 ///
4806 /// This function is used to replace the definition of a class with a new definition, as might be needed in fix-and-continue debugging.
4807 /// Where the existing class file bytes are to be transformed, for example in bytecode instrumentation, `RetransformClasses` should be used.
4808 ///
4809 /// Redefinition can cause new versions of methods to be installed.
4810 /// Old method versions may become obsolete The new method version will be used on new invokes.
4811 /// If a method has active stack frames, those active frames continue to run the bytecodes of the original method version.
4812 /// If resetting of stack frames is desired, use `PopFrame` to pop frames with obsolete method versions.
4813 ///
4814 /// This function does not cause any initialization except that which would occur under the customary JVM semantics.
4815 /// In other words, redefining a class does not cause its initializers to be run.
4816 /// The values of static fields will remain as they were prior to the call.
4817 ///
4818 /// Threads need not be suspended.
4819 /// All breakpoints in the class are cleared.
4820 /// All attributes are updated.
4821 /// Instances of the redefined class are not affected, fields retain their previous values.
4822 /// Tags on the instances are also unaffected.
4823 /// In response to this call, the JVM TI event Class File Load Hook will be sent (if enabled),
4824 /// but no other JVM TI events will be sent.
4825 ///
4826 /// The redefinition may change method bodies, the constant pool and attributes (unless explicitly prohibited).
4827 /// The redefinition must not add, remove or rename fields or methods, change the signatures of methods, change modifiers, or change inheritance.
4828 /// The redefinition must not change the `NestHost`, `NestMembers`, `Record`, or `PermittedSubclasses` attributes.
4829 /// These restrictions may be lifted in future versions.
4830 /// See the error return description for information on error codes returned if an unsupported redefinition is attempted.
4831 /// The class file bytes are not verified or installed until they have passed through the chain of `ClassFileLoadHook` events,
4832 /// thus the returned error code reflects the result of the transformations applied to the bytes passed into `class_definitions`.
4833 ///
4834 /// If any error code is returned other than `JVMTI_ERROR_NONE`,
4835 /// none of the classes to be redefined will have a new definition installed.
4836 ///
4837 /// When this function returns (with the error code of `JVMTI_ERROR_NONE`)
4838 /// all of the classes to be redefined will have their new definitions installed.
4839 ///
4840 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#RedefineClasses>
4841 ///
4842 /// # Safety
4843 /// `class_count` and `class_definitions` must form a valid array.
4844 /// all pointer parameters must not be dangling.
4845 /// `class_definitions` must be internally consistent and valid. (no dangling pointers, size + byte pointer must match)
4846 pub unsafe fn RedefineClasses(&self, class_count: jint, class_definitions: *const jvmtiClassDefinition) -> jvmtiError {
4847 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint, *const jvmtiClassDefinition) -> jvmtiError>(86)(self.vtable, class_count, class_definitions) }
4848 }
4849
4850 /// For the object indicated by object, return via `size_ptr` the size of the object.
4851 ///
4852 /// This size is an implementation-specific approximation of the amount of storage consumed by this object.
4853 /// It may include some or all of the object's overhead, and thus is useful for comparison within an implementation but not between implementations.
4854 /// The estimate may change during a single invocation of the JVM.
4855 ///
4856 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetObjectSize>
4857 ///
4858 /// # Safety
4859 /// `object` must be a valid strong reference or null.
4860 /// all pointer parameters must not be dangling.
4861 pub unsafe fn GetObjectSize(&self, object: jobject, size_ptr: *mut jlong) -> jvmtiError {
4862 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, *mut jlong) -> jvmtiError>(153)(self.vtable, object, size_ptr) }
4863 }
4864
4865 /// For the object indicated by object, return via `hash_code_ptr` a hash code.
4866 ///
4867 /// This hash code could be used to maintain a hash table of object references, however, on some implementations this can cause significant performance impacts,
4868 /// in most cases tags will be a more efficient means of associating information with objects.
4869 ///
4870 /// This function guarantees the same hash code value for a particular object throughout its life
4871 ///
4872 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetObjectHashCode>
4873 ///
4874 /// # Safety
4875 /// `object` must be a valid strong reference or null.
4876 /// all pointer parameters must not be dangling.
4877 pub unsafe fn GetObjectHashCode(&self, object: jobject, hash_code_ptr: *mut jint) -> jvmtiError {
4878 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, *mut jint) -> jvmtiError>(57)(self.vtable, object, hash_code_ptr) }
4879 }
4880
4881 /// Get information about the object's monitor. The fields of the jvmtiMonitorUsage structure are filled in with information about usage of the monitor.
4882 ///
4883 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetObjectMonitorUsage>
4884 ///
4885 /// # Safety
4886 /// `object` must be a valid strong reference or null.
4887 /// all pointer parameters must not be dangling.
4888 pub unsafe fn GetObjectMonitorUsage(&self, object: jobject, info_ptr: *mut jvmtiMonitorUsage) -> jvmtiError {
4889 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jobject, *mut jvmtiMonitorUsage) -> jvmtiError>(58)(self.vtable, object, info_ptr) }
4890 }
4891
4892 /// For the field indicated by klass and field, return the field name via `name_ptr` and field signature via `signature_ptr`.
4893 ///
4894 /// Field signatures are defined in the JNI Specification and are referred to as field descriptors in The Java™ Virtual Machine Specification, Chapter 4.3.2.
4895 ///
4896 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetFieldName>
4897 ///
4898 /// # Safety
4899 /// `klass` must be a valid strong reference or null.
4900 /// `field` must be a valid field reference in the class referred to by `klass`
4901 /// all pointer parameters must not be dangling.
4902 pub unsafe fn GetFieldName(&self, klass: jclass, field: jfieldID, name_ptr: *mut *mut c_char, signature_ptr: *mut *mut c_char, generic_ptr: *mut *mut c_char) -> jvmtiError {
4903 unsafe {
4904 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, jfieldID, *mut *mut c_char, *mut *mut c_char, *mut *mut c_char) -> jvmtiError>(59)(
4905 self.vtable,
4906 klass,
4907 field,
4908 name_ptr,
4909 signature_ptr,
4910 generic_ptr,
4911 )
4912 }
4913 }
4914
4915 /// For the field indicated by klass and field return the class that defined it via `declaring_class_ptr`.
4916 /// The declaring class will either be klass, a superclass, or an implemented interface.
4917 ///
4918 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetFieldDeclaringClass>
4919 ///
4920 /// # Safety
4921 /// `klass` must be a valid strong reference or null.
4922 /// `field` must be a valid field reference in the class referred to by `klass`
4923 /// all pointer parameters must not be dangling.
4924 pub unsafe fn GetFieldDeclaringClass(&self, klass: jclass, field: jfieldID, declaring_class_ptr: *mut jclass) -> jvmtiError {
4925 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, jfieldID, *mut jclass) -> jvmtiError>(60)(self.vtable, klass, field, declaring_class_ptr) }
4926 }
4927
4928 /// For the field indicated by klass and field return the access flags via `modifiers_ptr`.
4929 ///
4930 /// Access flags are defined in The Java™ Virtual Machine Specification, Chapter 4.
4931 ///
4932 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetFieldModifiers>
4933 ///
4934 /// # Safety
4935 /// `klass` must be a valid strong reference or null.
4936 /// `field` must be a valid field reference in the class referred to by `klass`
4937 /// all pointer parameters must not be dangling.
4938 pub unsafe fn GetFieldModifiers(&self, klass: jclass, field: jfieldID, modifiers_ptr: *mut jint) -> jvmtiError {
4939 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, jfieldID, *mut jint) -> jvmtiError>(61)(self.vtable, klass, field, modifiers_ptr) }
4940 }
4941
4942 /// For the field indicated by klass and field, return a value indicating whether the field is synthetic via `is_synthetic_ptr`.
4943 ///
4944 /// Synthetic fields are generated by the compiler but not present in the original source code.
4945 ///
4946 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IsFieldSynthetic>
4947 ///
4948 /// # Safety
4949 /// `klass` must be a valid strong reference or null.
4950 /// `field` must be a valid field reference in the class referred to by `klass`
4951 /// all pointer parameters must not be dangling.
4952 pub unsafe fn IsFieldSynthetic(&self, klass: jclass, field: jfieldID, is_synthetic_ptr: impl JBooleanMutPtr) -> jvmtiError {
4953 is_synthetic_ptr.use_jboolean_mut(|is_synthetic_ptr| unsafe {
4954 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jclass, jfieldID, *mut jboolean) -> jvmtiError>(62)(self.vtable, klass, field, is_synthetic_ptr)
4955 })
4956 }
4957
4958 /// For the method indicated by method, return the method name via `name_ptr` and method signature via `signature_ptr`.
4959 ///
4960 /// Method signatures are defined in the JNI Specification and are referred to as method descriptors in The Java™ Virtual Machine Specification, Chapter 4.3.3.
4961 /// Note this is different than method signatures as defined in the Java Language Specification.
4962 ///
4963 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetMethodName>
4964 ///
4965 /// # Safety
4966 /// `method` must be a valid methodID or null.
4967 /// all pointer parameters must not be dangling.
4968 pub unsafe fn GetMethodName(&self, method: jmethodID, name_ptr: *mut *mut c_char, signature_ptr: *mut *mut c_char, generic_ptr: *mut *mut c_char) -> jvmtiError {
4969 unsafe {
4970 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut *mut c_char, *mut *mut c_char, *mut *mut c_char) -> jvmtiError>(63)(
4971 self.vtable,
4972 method,
4973 name_ptr,
4974 signature_ptr,
4975 generic_ptr,
4976 )
4977 }
4978 }
4979
4980 /// For the method indicated by method, return the class that defined it via `declaring_class_ptr`.
4981 ///
4982 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetMethodDeclaringClass>
4983 ///
4984 /// # Safety
4985 /// `method` must be a valid methodID or null.
4986 /// all pointer parameters must not be dangling.
4987 pub unsafe fn GetMethodDeclaringClass(&self, method: jmethodID, declaring_class_ptr: *mut jclass) -> jvmtiError {
4988 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut jclass) -> jvmtiError>(64)(self.vtable, method, declaring_class_ptr) }
4989 }
4990
4991 /// For the method indicated by method, return the access flags via `modifiers_ptr`.
4992 ///
4993 /// Access flags are defined in The Java™ Virtual Machine Specification, Chapter 4.
4994 ///
4995 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetMethodModifiers>
4996 ///
4997 /// # Safety
4998 /// `method` must be a valid methodID or null.
4999 /// all pointer parameters must not be dangling.
5000 pub unsafe fn GetMethodModifiers(&self, method: jmethodID, modifiers_ptr: *mut jint) -> jvmtiError {
5001 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut jint) -> jvmtiError>(65)(self.vtable, method, modifiers_ptr) }
5002 }
5003
5004 /// For the method indicated by method, return the number of local variable slots used by the method,
5005 /// including the local variables used to pass parameters to the method on its invocation.
5006 ///
5007 /// See `max_locals` in The Java™ Virtual Machine Specification, Chapter 4.7.3.
5008 ///
5009 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetMaxLocals>
5010 ///
5011 /// # Safety
5012 /// `method` must be a valid methodID or null.
5013 /// all pointer parameters must not be dangling.
5014 pub unsafe fn GetMaxLocals(&self, method: jmethodID, max_ptr: *mut jint) -> jvmtiError {
5015 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut jint) -> jvmtiError>(67)(self.vtable, method, max_ptr) }
5016 }
5017
5018 /// For the method indicated by method, return via `max_ptr` the number of local variable slots used by the method's arguments.
5019 ///
5020 /// Note that two-word arguments use two slots.
5021 ///
5022 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetArgumentsSize>
5023 ///
5024 /// # Safety
5025 /// `method` must be a valid methodID or null.
5026 /// all pointer parameters must not be dangling.
5027 pub unsafe fn GetArgumentsSize(&self, method: jmethodID, max_ptr: *mut jint) -> jvmtiError {
5028 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut jint) -> jvmtiError>(68)(self.vtable, method, max_ptr) }
5029 }
5030
5031 /// For the method indicated by method, return a table of source line number entries.
5032 /// The size of the table is returned via `entry_count_ptr` and the table itself is returned via `table_ptr`.
5033 ///
5034 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetLineNumberTable>
5035 ///
5036 /// # Safety
5037 /// `method` must be a valid methodID or null.
5038 /// all pointer parameters must not be dangling.
5039 pub unsafe fn GetLineNumberTable(&self, method: jmethodID, entry_count_ptr: *mut jint, table_ptr: *mut *mut jvmtiLineNumberEntry) -> jvmtiError {
5040 unsafe {
5041 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut jint, *mut *mut jvmtiLineNumberEntry) -> jvmtiError>(69)(
5042 self.vtable,
5043 method,
5044 entry_count_ptr,
5045 table_ptr,
5046 )
5047 }
5048 }
5049
5050 /// For the method indicated by method, return the beginning and ending addresses through `start_location_ptr` and `end_location_ptr`.
5051 /// In a conventional bytecode indexing scheme, `start_location_ptr` will always point to zero and `end_location_ptr` will always point to the bytecode count minus one.
5052 ///
5053 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetMethodLocation>
5054 ///
5055 /// # Safety
5056 /// `method` must be a valid methodID or null.
5057 /// all pointer parameters must not be dangling.
5058 pub unsafe fn GetMethodLocation(&self, method: jmethodID, start_location_ptr: *mut jlocation, end_location_ptr: *mut jlocation) -> jvmtiError {
5059 unsafe {
5060 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut jlocation, *mut jlocation) -> jvmtiError>(70)(self.vtable, method, start_location_ptr, end_location_ptr)
5061 }
5062 }
5063
5064 /// Return local variable information.
5065 ///
5066 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetLocalVariableTable>
5067 ///
5068 /// # Safety
5069 /// `method` must be a valid methodID or null.
5070 /// all pointer parameters must not be dangling.
5071 pub unsafe fn GetLocalVariableTable(&self, method: jmethodID, entry_count_ptr: *mut jint, table_ptr: *mut *mut jvmtiLocalVariableEntry) -> jvmtiError {
5072 unsafe {
5073 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut jint, *mut *mut jvmtiLocalVariableEntry) -> jvmtiError>(71)(
5074 self.vtable,
5075 method,
5076 entry_count_ptr,
5077 table_ptr,
5078 )
5079 }
5080 }
5081
5082 /// For the method indicated by method, return the bytecodes that implement the method. The number of bytecodes is returned via `bytecode_count_ptr`.
5083 ///
5084 /// The bytecodes themselves are returned via `bytecodes_ptr`.
5085 ///
5086 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetBytecodes>
5087 ///
5088 /// # Safety
5089 /// `method` must be a valid methodID or null.
5090 /// all pointer parameters must not be dangling.
5091 pub unsafe fn GetBytecodes(&self, method: jmethodID, bytecode_count_ptr: *mut jint, bytecodes_ptr: *mut *mut c_uchar) -> jvmtiError {
5092 unsafe {
5093 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut jint, *mut *mut c_uchar) -> jvmtiError>(74)(self.vtable, method, bytecode_count_ptr, bytecodes_ptr)
5094 }
5095 }
5096
5097 /// For the method indicated by method, return a value indicating whether the method is native via `is_native_ptr`.
5098 ///
5099 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IsMethodNative>
5100 ///
5101 /// # Safety
5102 /// `method` must be a valid methodID or null.
5103 /// all pointer parameters must not be dangling.
5104 pub unsafe fn IsMethodNative(&self, method: jmethodID, is_native_ptr: impl JBooleanMutPtr) -> jvmtiError {
5105 is_native_ptr.use_jboolean_mut(|is_native_ptr| unsafe {
5106 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut jboolean) -> jvmtiError>(75)(self.vtable, method, is_native_ptr)
5107 })
5108 }
5109
5110 /// For the method indicated by method, return a value indicating whether the method is synthetic via `is_synthetic_ptr`.
5111 ///
5112 /// Synthetic methods are generated by the compiler but not present in the original source code.
5113 ///
5114 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IsMethodSynthetic>
5115 ///
5116 /// # Safety
5117 /// `method` must be a valid methodID or null.
5118 /// all pointer parameters must not be dangling.
5119 pub unsafe fn IsMethodSynthetic(&self, method: jmethodID, is_synthetic_ptr: impl JBooleanMutPtr) -> jvmtiError {
5120 is_synthetic_ptr.use_jboolean_mut(|is_synthetic_ptr| unsafe {
5121 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut jboolean) -> jvmtiError>(76)(self.vtable, method, is_synthetic_ptr)
5122 })
5123 }
5124
5125 /// Determine if a method ID refers to an obsolete method version.
5126 ///
5127 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#IsMethodObsolete>
5128 ///
5129 /// # Safety
5130 /// `method` must be a valid methodID or null.
5131 /// all pointer parameters must not be dangling.
5132 pub unsafe fn IsMethodObsolete(&self, method: jmethodID, is_obsolete_ptr: impl JBooleanMutPtr) -> jvmtiError {
5133 is_obsolete_ptr.use_jboolean_mut(|is_obsolete_ptr| unsafe {
5134 self.jvmti::<extern "system" fn(JVMTIEnvVTable, jmethodID, *mut jboolean) -> jvmtiError>(90)(self.vtable, method, is_obsolete_ptr)
5135 })
5136 }
5137
5138 /// This function modifies the failure handling of native method resolution by allowing retry with a prefix applied to the name.
5139 ///
5140 /// When used with the `ClassFileLoadHook` event, it enables native methods to be instrumented.
5141 ///
5142 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetNativeMethodPrefix>
5143 ///
5144 /// # Safety
5145 /// `prefix` must be a rust string type or a valid zero terminated utf-8 string or null.
5146 /// all pointer parameters must not be dangling.
5147 pub unsafe fn SetNativeMethodPrefix(&self, prefix: impl UseCString) -> jvmtiError {
5148 unsafe { prefix.use_as_const_c_char(|prefix| self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const c_char) -> jvmtiError>(72)(self.vtable, prefix)) }
5149 }
5150
5151 /// For a normal agent, `SetNativeMethodPrefix` will provide all needed native method prefixing.
5152 /// For a meta-agent that performs multiple independent class file transformations (for example as a proxy for another layer of agents) this function allows each transformation to have its own prefix.
5153 /// The prefixes are applied in the order supplied and are processed in the same manner as described for the application of prefixes from multiple JVM TI environments in `SetNativeMethodPrefix`.
5154 ///
5155 /// Any previous prefixes are replaced. Thus, calling this function with a `prefix_count` of 0 disables prefixing in this environment.
5156 ///
5157 /// `SetNativeMethodPrefix` and this function are the two ways to set the prefixes.
5158 /// Calling `SetNativeMethodPrefix` with a prefix is the same as calling this function with `prefix_count` of 1.
5159 /// Calling `SetNativeMethodPrefix` with NULL is the same as calling this function with `prefix_count` of 0.
5160 ///
5161 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetNativeMethodPrefix>
5162 ///
5163 /// # Safety
5164 /// `prefixes` must contain valid zero terminated utf-8 strings.
5165 /// `prefix_count` and `prefixes` must form a valid array.
5166 /// all pointer parameters must not be dangling.
5167 pub unsafe fn SetNativeMethodPrefixes(&self, prefix_count: jint, prefixes: *mut *mut c_char) -> jvmtiError {
5168 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint, *mut *mut c_char) -> jvmtiError>(73)(self.vtable, prefix_count, prefixes) }
5169 }
5170
5171 /// Create a raw monitor.
5172 ///
5173 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#CreateRawMonitor>
5174 ///
5175 /// For the `monitor_ptr` argument the following rust datatypes are supported:
5176 /// - `*mut jrawMonitorID`
5177 /// - `&mut jrawMonitorID`
5178 /// - `&AtomicPtr<jrawMonitorIDType>`
5179 ///
5180 /// # Usage Recommendation
5181 /// If you have access to a pure-rust based re-entrant mutex in your environment then
5182 /// there is not really a need to use jvmti raw monitors at all.
5183 /// jvmti raw monitors are probably only useful to you if your java agent does
5184 /// not use the rust standard library. (no-std)
5185 ///
5186 ///
5187 /// # Safety
5188 /// `name` must be a rust string type or a valid zero terminated utf-8 string or null.
5189 /// `monitor_ptr` must not be a dangling raw pointer
5190 ///
5191 /// # Example
5192 /// ```rust
5193 /// use std::ptr::null_mut;
5194 /// use std::sync::atomic::AtomicPtr;
5195 /// use std::time::Duration;
5196 /// use jni_simple::*;
5197 ///
5198 /// static JVMTI_MONITOR: AtomicPtr<jrawMonitorIDType> = AtomicPtr::new(null_mut());
5199 ///
5200 /// // called once when your jvmti agent loads.
5201 /// fn init_mutex(env: JVMTIEnv) {
5202 /// unsafe {
5203 /// assert!(env.CreateRawMonitor("monitor of my custom java debugger 123", &JVMTI_MONITOR).is_ok());
5204 /// }
5205 /// }
5206 ///
5207 /// fn do_some_exclusive_work(env: JVMTIEnv) {
5208 /// unsafe {
5209 /// // The jvmti raw monitors are always re-entrant.
5210 /// // Just call RawMonitorExit the same number of times you call RawMonitorEnter
5211 /// assert!(env.RawMonitorEnter(&JVMTI_MONITOR).is_ok());
5212 ///
5213 /// // Some jni/jvmti functions require some level of mutual exclusion
5214 /// // Depending on the state of the jvm.
5215 /// std::thread::sleep(Duration::from_millis(1000));
5216 ///
5217 /// // I recommend doing this in a `defer!` block from either the `defer-lite` or `defer-heavy` crate.
5218 /// // Its a bad idea to not do this due to either unwinding or the ? operator returning early.
5219 /// assert!(env.RawMonitorExit(&JVMTI_MONITOR).is_ok());
5220 /// }
5221 /// }
5222 ///
5223 /// ```
5224 ///
5225 pub unsafe fn CreateRawMonitor<T: ReceiveJrawMonitorID>(&self, name: impl UseCString, monitor_ptr: T) -> jvmtiError {
5226 unsafe {
5227 if T::is_direct() {
5228 //Raw pointer
5229 return name.use_as_const_c_char(|name| {
5230 self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const c_char, *mut jrawMonitorID) -> jvmtiError>(30)(self.vtable, name, monitor_ptr.direct_arg())
5231 });
5232 }
5233
5234 let mut monitor: jrawMonitorID = null_mut();
5235 let ret = name.use_as_const_c_char(|name| {
5236 self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const c_char, *mut jrawMonitorID) -> jvmtiError>(30)(self.vtable, name, &raw mut monitor)
5237 });
5238 if ret == JVMTI_ERROR_NONE {
5239 monitor_ptr.receive(monitor);
5240 }
5241 ret
5242 }
5243 }
5244
5245 /// Destroy the raw monitor.
5246 ///
5247 /// If the monitor being destroyed has been entered by this thread, it will be exited before it is destroyed.
5248 /// If the monitor being destroyed has been entered by another thread, an error will be returned and the monitor will not be destroyed.
5249 ///
5250 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#DestroyRawMonitor>
5251 ///
5252 /// # Safety
5253 /// `monitor` must be a valid raw monitor
5254 pub unsafe fn DestroyRawMonitor(&self, monitor: impl AsJrawMonitorID) -> jvmtiError {
5255 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jrawMonitorID) -> jvmtiError>(31)(self.vtable, monitor.jraw_monitor_id()) }
5256 }
5257
5258 /// Gain exclusive ownership of a raw monitor.
5259 ///
5260 /// The same thread may enter a monitor more then once.
5261 /// The thread must exit the monitor the same number of times as it is entered.
5262 /// If a monitor is entered during `OnLoad` (before attached threads exist) and has not exited when attached threads come into existence,
5263 /// the enter is considered to have occurred on the main thread.
5264 ///
5265 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#RawMonitorEnter>
5266 ///
5267 /// # Safety
5268 /// `monitor` must be a valid raw monitor
5269 pub unsafe fn RawMonitorEnter(&self, monitor: impl AsJrawMonitorID) -> jvmtiError {
5270 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jrawMonitorID) -> jvmtiError>(32)(self.vtable, monitor.jraw_monitor_id()) }
5271 }
5272
5273 /// Release exclusive ownership of a raw monitor.
5274 ///
5275 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#RawMonitorExit>
5276 ///
5277 /// # Safety
5278 /// `monitor` must be a valid raw monitor
5279 pub unsafe fn RawMonitorExit(&self, monitor: impl AsJrawMonitorID) -> jvmtiError {
5280 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jrawMonitorID) -> jvmtiError>(33)(self.vtable, monitor.jraw_monitor_id()) }
5281 }
5282
5283 /// Wait for notification of the raw monitor.
5284 ///
5285 /// Causes the current thread to wait until either another thread calls `RawMonitorNotify` or `RawMonitorNotifyAll` for the specified raw monitor, or the specified timeout has elapsed.
5286 ///
5287 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#RawMonitorWait>
5288 ///
5289 /// # Safety
5290 /// `monitor` must be a valid raw monitor
5291 pub unsafe fn RawMonitorWait(&self, monitor: impl AsJrawMonitorID) -> jvmtiError {
5292 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jrawMonitorID) -> jvmtiError>(34)(self.vtable, monitor.jraw_monitor_id()) }
5293 }
5294
5295 /// Notify a single thread waiting on the raw monitor.
5296 ///
5297 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#RawMonitorNotify>
5298 ///
5299 /// # Safety
5300 /// `monitor` must be a valid raw monitor
5301 pub unsafe fn RawMonitorNotify(&self, monitor: impl AsJrawMonitorID) -> jvmtiError {
5302 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jrawMonitorID) -> jvmtiError>(35)(self.vtable, monitor.jraw_monitor_id()) }
5303 }
5304
5305 /// Notify all threads waiting on the raw monitor.
5306 ///
5307 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#RawMonitorNotifyAll>
5308 ///
5309 /// # Safety
5310 /// `monitor` must be a valid raw monitor
5311 pub unsafe fn RawMonitorNotifyAll(&self, monitor: impl AsJrawMonitorID) -> jvmtiError {
5312 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jrawMonitorID) -> jvmtiError>(36)(self.vtable, monitor.jraw_monitor_id()) }
5313 }
5314
5315 /// Set the JNI function table in all current and future JNI environments.
5316 ///
5317 /// As a result, all future JNI calls are directed to the specified functions.
5318 /// Use `GetJNIFunctionTable` to get the function table to pass to this function.
5319 /// For this function to take effect the updated table entries must be used by the JNI clients.
5320 /// The table is copied--changes to the local copy of the table have no effect.
5321 /// This function affects only the function table, all other aspects of the environment are unaffected.
5322 ///
5323 /// # Compiler Optimizations
5324 /// Since the table is defined const in the C headers some compilers may optimize away the access to the table,
5325 /// thus preventing this function from taking effect.
5326 /// This is entirely dependant on the compiler and its settings that was used to compile the JNI Client.
5327 /// The rust compiler settings used to compile the JVMTI agent have no effect on this.
5328 ///
5329 /// ## Rust Compiler Optimizations
5330 /// The rust compiler does not as of rust version 1.89 perform any optimization that prevents this function from taking effect with rust JNI Clients
5331 /// regardless of chosen rust compiler settings and flags.
5332 /// It is very unlikely that future versions of the rust compiler will change this behavior.
5333 ///
5334 ///
5335 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetJNIFunctionTable>
5336 ///
5337 /// # Safety
5338 /// `function_table` must be a valid initialized jni function table
5339 pub unsafe fn SetJNIFunctionTable(&self, function_table: jniNativeInterface) -> jvmtiError {
5340 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jniNativeInterface) -> jvmtiError>(119)(self.vtable, function_table) }
5341 }
5342
5343 /// Get the JNI function table. The JNI function table is copied into allocated memory.
5344 ///
5345 /// If `SetJNIFunctionTable` has been called, the modified (not the original) function table is returned.
5346 /// Only the function table is copied, no other aspects of the environment are copied.
5347 ///
5348 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetJNIFunctionTable>
5349 ///
5350 /// # Safety
5351 /// `function_table` must not be dangling
5352 pub unsafe fn GetJNIFunctionTable(&self, function_table: *mut jniNativeInterface) -> jvmtiError {
5353 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jniNativeInterface) -> jvmtiError>(120)(self.vtable, function_table) }
5354 }
5355
5356 /// Set the functions to be called for each event.
5357 ///
5358 /// The callbacks are specified by supplying a replacement function table.
5359 ///
5360 /// The function table is copied, changes to the local copy of the table have no effect.
5361 /// This is an atomic action, all callbacks are set at once.
5362 ///
5363 /// No events are sent before this function is called.
5364 /// When an entry is NULL or when the event is beyond `size_of_callbacks` no event is sent.
5365 /// Details on events are described later in this document.
5366 ///
5367 /// An event must be enabled and have a callback in order to be sent,
5368 /// the order in which this function and `SetEventNotificationMode` are called does not affect the result.
5369 ///
5370 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetEventCallbacks>
5371 ///
5372 /// # Safety
5373 /// `callbacks` must not be dangling
5374 #[expect(clippy::cast_possible_truncation)] // size_of::<jvmtiEventCallbacks>() will never be larger than jint::MAX
5375 #[expect(clippy::cast_possible_wrap)]
5376 pub unsafe fn SetEventCallbacks(&self, callbacks: *const jvmtiEventCallbacks) -> jvmtiError {
5377 unsafe {
5378 self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const jvmtiEventCallbacks, jint) -> jvmtiError>(121)(self.vtable, callbacks, size_of::<jvmtiEventCallbacks>() as jint)
5379 }
5380 }
5381
5382 /// Raw variant of `SetEventCallbacks` which allows for passing an arbitrary payload.
5383 /// This is useful when attempting to use a jvmti version that is newer than what jni-simple supports.
5384 ///
5385 /// # Safety
5386 /// The `callbacks` and `size_of_callbacks` must match what the jvm expects.
5387 pub unsafe fn SetEventCallbacks_raw(&self, callbacks: *const c_void, size_of_callbacks: jint) -> jvmtiError {
5388 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const jvmtiEventCallbacks, jint) -> jvmtiError>(121)(self.vtable, callbacks.cast(), size_of_callbacks) }
5389 }
5390
5391 /// Control the generation of events.
5392 ///
5393 /// Calling this function either enables or disables future generation of specific jvmti events.
5394 /// If `event_thread` is null then this control the behavior of event generation a global level.
5395 /// Otherwise changes are only made for the given thread.
5396 ///
5397 /// The following events cannot be controlled at the thread level through this function:
5398 /// - `VMInit`
5399 /// - `VMStart`
5400 /// - `VMDeath`
5401 /// - `ThreadStart`
5402 /// - `VirtualThreadStart`
5403 /// - `CompiledMethodLoad`
5404 /// - `CompiledMethodUnload`
5405 /// - `DynamicCodeGenerated`
5406 /// - `DataDumpRequest`
5407 ///
5408 /// Initially, no events are enabled at either the thread level or the global level.
5409 /// Any needed capabilities (see Event Enabling Capabilities below) must be possessed before calling this function.
5410 ///
5411 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetEventNotificationMode>
5412 ///
5413 /// # Safety
5414 /// `event_thread` must either be null or a valid strong reference to a jthread.
5415 /// The `callbacks` and `size_of_callbacks` must match what the jvm expects.
5416 pub unsafe fn SetEventNotificationMode(&self, mode: jvmtiEventMode, event_type: jvmtiEvent, event_thread: jthread) -> jvmtiError {
5417 unsafe { self.jvmti::<extern "C" fn(JVMTIEnvVTable, jvmtiEventMode, jvmtiEvent, jthread, ...) -> jvmtiError>(1)(self.vtable, mode, event_type, event_thread) }
5418 }
5419
5420 /// Allows for calling undocumented variadic extensions.
5421 /// The current jvmti specification only provides this function with the disclaimer
5422 /// "for future expansion"
5423 ///
5424 /// Since rust does support c-variadics yet calling this from rust is non trivial.
5425 ///
5426 /// # Safety
5427 /// There are a lot of things that can go wrong when calling this function, see the example.
5428 /// using this function requires deep knowledge of jvm implementation specific details.
5429 /// Use with care and only if necessary.
5430 ///
5431 /// # Example
5432 /// ```rust
5433 /// use std::ffi::{c_int, c_void};
5434 /// use core::ptr::null_mut;
5435 /// use jni_simple::*;
5436 ///
5437 /// fn enable_very_special_custom_event(env: JVMTIEnv) {
5438 /// unsafe {
5439 /// //NOTE: jvmtiEvent with a value 5 does not exist, this is just for illustrative purposes!
5440 /// //This example assumes that the hypothetical global jni event 5 would want a jint extension parameter.
5441 /// let _err : jvmtiError = env.SetEventNotificationMode_extension::<extern "C" fn(*mut c_void, jvmtiEventMode, c_int, jthread, ...) -> jvmtiError>()
5442 /// (env.vtable(), jvmtiEventMode::JVMTI_ENABLE, 5, null_mut(), 4i32);
5443 /// }
5444 /// }
5445 /// ```
5446 #[must_use]
5447 pub unsafe fn SetEventNotificationMode_extension<X>(&self) -> X {
5448 unsafe { self.jvmti::<X>(1) }
5449 }
5450
5451 /// Generate events to represent the current state of the VM.
5452 ///
5453 /// For example, if `event_type` is `JVMTI_EVENT_COMPILED_METHOD_LOAD`, a `CompiledMethodLoad` event will be sent for each currently compiled method.
5454 /// Methods that were loaded and now have been unloaded are not sent.
5455 /// The history of what events have previously been sent does not effect what events are sent by this function,
5456 /// for example, all currently compiled methods will be sent each time this function is called.
5457 ///
5458 /// This function is useful when events may have been missed due to the agent attaching after program execution begins; this function generates the missed events.
5459 ///
5460 /// Attempts to execute Java programming language code or JNI functions may be paused until this function returns,
5461 /// so neither should be called from the thread sending the event.
5462 ///
5463 /// This function returns only after the missed events have been sent, processed and have returned.
5464 ///
5465 /// The event may be sent on a different thread than the thread on which the event occurred.
5466 /// The callback for the event must be set with `SetEventCallbacks` and the event must be enabled with `SetEventNotificationMode` or the events will not occur.
5467 /// If the VM no longer has the information to generate some or all of the requested events, the events are simply not sent - no error is returned.
5468 ///
5469 /// Only the following events are supported:
5470 /// - `CompiledMethodLoad`
5471 /// - `DynamicCodeGenerated`
5472 ///
5473 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GenerateEvents>
5474 ///
5475 /// # Safety
5476 /// `function_table` must not be dangling
5477 pub unsafe fn GenerateEvents(&self, event_type: jvmtiEvent) -> jvmtiError {
5478 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jvmtiEvent) -> jvmtiError>(122)(self.vtable, event_type) }
5479 }
5480
5481 /// Returns the set of extension functions.
5482 ///
5483 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetExtensionFunctions>
5484 ///
5485 /// # Safety
5486 /// all pointer parameters must not be dangling
5487 pub unsafe fn GetExtensionFunctions(&self, extension_count_ptr: *mut jint, extensions: *mut *mut jvmtiExtensionFunctionInfo) -> jvmtiError {
5488 unsafe {
5489 self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jint, *mut *mut jvmtiExtensionFunctionInfo) -> jvmtiError>(123)(self.vtable, extension_count_ptr, extensions)
5490 }
5491 }
5492
5493 /// Returns the set of extension events.
5494 ///
5495 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetExtensionEvents>
5496 ///
5497 /// # Safety
5498 /// all pointer parameters must not be dangling
5499 pub unsafe fn GetExtensionEvents(&self, extension_count_ptr: *mut jint, extensions: *mut *mut jvmtiExtensionEventInfo) -> jvmtiError {
5500 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jint, *mut *mut jvmtiExtensionEventInfo) -> jvmtiError>(124)(self.vtable, extension_count_ptr, extensions) }
5501 }
5502
5503 /// Sets the callback function for an extension event and enables the event. Or, if the callback is NULL, disables the event.
5504 ///
5505 /// Note that unlike standard events, setting the callback and enabling the event are a single operation.
5506 ///
5507 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetExtensionEventCallback>
5508 ///
5509 /// # Safety
5510 /// all pointer parameters must not be dangling
5511 /// `callback` must match the function signature that the jvm implementation expects.
5512 pub unsafe fn SetExtensionEventCallback(&self, extension_event_index: jint, callback: jvmtiExtensionEvent) -> jvmtiError {
5513 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint, jvmtiExtensionEvent) -> jvmtiError>(125)(self.vtable, extension_event_index, callback) }
5514 }
5515
5516 /// Get information about the `GetCurrentThreadCpuTime` timer.
5517 ///
5518 /// The fields of the jvmtiTimerInfo structure are filled in with details about the timer.
5519 ///
5520 /// This information is specific to the platform and the implementation of `GetCurrentThreadCpuTime` and thus does not vary by thread nor does it vary during a particular invocation of the VM.
5521 ///
5522 /// Note that the implementations of `GetCurrentThreadCpuTime` and `GetThreadCpuTime` may differ,
5523 /// and thus the values returned by `GetCurrentThreadCpuTimerInfo` and `GetThreadCpuTimerInfo` may differ,
5524 /// see `GetCurrentThreadCpuTime` for more information.
5525 ///
5526 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetCurrentThreadCpuTimerInfo>
5527 ///
5528 /// # Safety
5529 /// all pointer parameters must not be dangling
5530 pub unsafe fn GetCurrentThreadCpuTimerInfo(&self, info_ptr: *mut jvmtiTimerInfo) -> jvmtiError {
5531 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jvmtiTimerInfo) -> jvmtiError>(133)(self.vtable, info_ptr) }
5532 }
5533
5534 /// Return the CPU time utilized by the current thread.
5535 ///
5536 /// Note that the `GetThreadCpuTime` function provides CPU time for any thread, including the current thread.
5537 /// `GetCurrentThreadCpuTime` exists to support platforms which cannot supply CPU time for threads other than the current thread
5538 /// or which have more accurate information for the current thread (see `GetCurrentThreadCpuTimerInfo` vs `GetThreadCpuTimerInfo`).
5539 ///
5540 /// An implementation is not required to support this function when the current thread is a virtual thread, in which case `JVMTI_ERROR_UNSUPPORTED_OPERATION` will be returned.
5541 /// see `GetCurrentThreadCpuTime` for more information.
5542 ///
5543 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetCurrentThreadCpuTime>
5544 ///
5545 /// # Safety
5546 /// all pointer parameters must not be dangling
5547 pub unsafe fn GetCurrentThreadCpuTime(&self, nanos_ptr: *mut jlong) -> jvmtiError {
5548 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jlong) -> jvmtiError>(134)(self.vtable, nanos_ptr) }
5549 }
5550
5551 /// Get information about the `GetCurrentThreadCpuTime` timer.
5552 ///
5553 /// The fields of the jvmtiTimerInfo structure are filled in with details about the timer.
5554 ///
5555 /// This information is specific to the platform and the implementation of `GetCurrentThreadCpuTime` and thus does not vary by thread nor does it vary during a particular invocation of the VM.
5556 ///
5557 /// Note that the implementations of `GetCurrentThreadCpuTime` and `GetThreadCpuTime` may differ,
5558 /// and thus the values returned by `GetCurrentThreadCpuTimerInfo` and `GetThreadCpuTimerInfo` may differ,
5559 /// see `GetCurrentThreadCpuTime` for more information.
5560 ///
5561 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetCurrentThreadCpuTimerInfo>
5562 ///
5563 /// # Safety
5564 /// all pointer parameters must not be dangling
5565 pub unsafe fn GetThreadCpuTimerInfo(&self, info_ptr: *mut jvmtiTimerInfo) -> jvmtiError {
5566 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jvmtiTimerInfo) -> jvmtiError>(135)(self.vtable, info_ptr) }
5567 }
5568
5569 /// Return the CPU time utilized by the specified thread.
5570 ///
5571 /// Get information about this timer with `GetThreadCpuTimerInfo`.
5572 ///
5573 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetThreadCpuTime>
5574 ///
5575 /// # Safety
5576 /// all pointer parameters must not be dangling
5577 pub unsafe fn GetThreadCpuTime(&self, thread: jthread, nanos_ptr: *mut jlong) -> jvmtiError {
5578 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jthread, *mut jlong) -> jvmtiError>(136)(self.vtable, thread, nanos_ptr) }
5579 }
5580
5581 /// Get information about the `GetTime` timer.
5582 ///
5583 /// The fields of the jvmtiTimerInfo structure are filled in with details about the timer.
5584 /// This information will not change during a particular invocation of the VM.
5585 ///
5586 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetTimerInfo>
5587 ///
5588 /// # Safety
5589 /// all pointer parameters must not be dangling
5590 pub unsafe fn GetTimerInfo(&self, info_ptr: *mut jvmtiTimerInfo) -> jvmtiError {
5591 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jvmtiTimerInfo) -> jvmtiError>(137)(self.vtable, info_ptr) }
5592 }
5593
5594 /// Return the current value of the system timer, in nanoseconds.
5595 ///
5596 /// The value returned represents nanoseconds since some fixed but arbitrary time (perhaps in the future, so values may be negative).
5597 ///
5598 /// This function provides nanosecond precision, but not necessarily nanosecond accuracy.
5599 ///
5600 /// No guarantees are made about how frequently values change.
5601 /// Get information about this timer with `GetTimerInfo`.
5602 ///
5603 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetTime>
5604 ///
5605 /// # Safety
5606 /// all pointer parameters must not be dangling
5607 pub unsafe fn GetTime(&self, nanos_ptr: *mut jlong) -> jvmtiError {
5608 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jlong) -> jvmtiError>(138)(self.vtable, nanos_ptr) }
5609 }
5610
5611 /// Returns the number of processors available to the Java virtual machine.
5612 ///
5613 /// This value may change during a particular invocation of the virtual machine.
5614 /// Applications that are sensitive to the number of available processors should therefore occasionally poll this property.
5615 ///
5616 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetAvailableProcessors>
5617 ///
5618 /// # Safety
5619 /// all pointer parameters must not be dangling
5620 pub unsafe fn GetAvailableProcessors(&self, processor_count_ptr: *mut jint) -> jvmtiError {
5621 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jint) -> jvmtiError>(143)(self.vtable, processor_count_ptr) }
5622 }
5623
5624 /// This function can be used to cause instrumentation classes to be defined by the bootstrap class loader.
5625 ///
5626 /// See The Java™ Virtual Machine Specification, Chapter 5.3.1. After the bootstrap class loader unsuccessfully searches for a class,
5627 /// the specified platform-dependent search path segment will be searched as well.
5628 ///
5629 /// Only one segment may be specified in the segment.
5630 /// This function may be called multiple times to add multiple segments, the segments will be searched in the order that this function was called.
5631 ///
5632 /// In the `OnLoad` phase the function may be used to specify any platform-dependent search path segment to be searched after the bootstrap class loader unsuccessfully searches for a class.
5633 /// The segment is typically a directory or JAR file.
5634 ///
5635 /// In the live phase the segment may be used to specify any platform-dependent path to a JAR file.
5636 /// The agent should take care that the JAR file does not contain any classes or resources other than those to be defined by the bootstrap class loader for the purposes of instrumentation.
5637 /// The Java™ Virtual Machine Specification specifies that a subsequent attempt to resolve a symbolic reference
5638 /// that the Java virtual machine has previously unsuccessfully attempted to resolve always fails with the same error that was thrown as a result of the initial resolution attempt.
5639 /// Consequently, if the JAR file contains an entry that corresponds to a class for which the Java virtual machine has unsuccessfully attempted to resolve a reference,
5640 /// then subsequent attempts to resolve that reference will fail with the same error as the initial attempt.
5641 ///
5642 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#AddToSystemClassLoaderSearch>
5643 ///
5644 /// # Safety
5645 /// `segment` must be a rust string, or a valid zero terminated utf-8 string or null
5646 pub unsafe fn AddToBootstrapClassLoaderSearch(&self, segment: impl UseCString) -> jvmtiError {
5647 unsafe { segment.use_as_const_c_char(|segment| self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const c_char) -> jvmtiError>(148)(self.vtable, segment)) }
5648 }
5649
5650 /// This function can be used to cause instrumentation classes to be defined by the system class loader. See The Java™ Virtual Machine Specification, Chapter 5.3.2.
5651 ///
5652 /// After the class loader unsuccessfully searches for a class, the specified platform-dependent search path segment will be searched as well.
5653 /// Only one segment may be specified in the segment. This function may be called multiple times to add multiple segments, the segments will be searched in the order that this function was called.
5654 ///
5655 /// In the `OnLoad` phase the function may be used to specify any platform-dependent search path segment to be searched after the system class loader unsuccessfully searches for a class.
5656 /// The segment is typically a directory or JAR file.
5657 ///
5658 /// In the live phase the segment is a platform-dependent path to a JAR file to be searched after the system class loader unsuccessfully searches for a class.
5659 /// The agent should take care that the JAR file does not contain any classes or resources other than those to be defined by the system class loader for the purposes of instrumentation.
5660 ///
5661 /// In the live phase the system class loader supports adding a JAR file to be searched if the system class loader implements a method name appendToClassPathForInstrumentation
5662 /// which takes a single parameter of type java.lang.String. The method is not required to have public access.
5663 ///
5664 /// The Java™ Virtual Machine Specification specifies that a subsequent attempt to resolve a symbolic reference that the Java virtual machine has previously unsuccessfully attempted to resolve
5665 /// always fails with the same error that was thrown as a result of the initial resolution attempt.
5666 /// Consequently, if the JAR file contains an entry that corresponds to a class for which the Java virtual machine has unsuccessfully attempted to resolve a reference,
5667 /// then subsequent attempts to resolve that reference will fail with the same error as the initial attempt.
5668 ///
5669 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#AddToSystemClassLoaderSearch>
5670 ///
5671 /// # Safety
5672 /// `segment` must be a rust string, or a valid zero terminated utf-8 string or null
5673 pub unsafe fn AddToSystemClassLoaderSearch(&self, segment: impl UseCString) -> jvmtiError {
5674 unsafe { segment.use_as_const_c_char(|segment| self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const c_char) -> jvmtiError>(150)(self.vtable, segment)) }
5675 }
5676
5677 /// Provides access to system properties defined by and used by the VM.
5678 ///
5679 /// Properties set on the command-line are included.
5680 /// This allows getting and setting of these properties before the VM even begins executing bytecodes.
5681 /// Since this is a VM view of system properties, the set of available properties will usually be different than that in java.lang.System.getProperties.
5682 /// JNI method invocation may be used to access java.lang.System.getProperties.
5683 /// The set of properties may grow during execution.
5684 ///
5685 /// The list of VM system property keys which may be used with `GetSystemProperty` is returned.
5686 /// It is strongly recommended that virtual machines provide the following property keys:
5687 /// - java.vm.vendor
5688 /// - java.vm.version
5689 /// - java.vm.name
5690 /// - java.vm.info
5691 /// - java.library.path
5692 /// - java.class.path
5693 ///
5694 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetSystemProperties>
5695 ///
5696 /// # Safety
5697 /// all pointer parameters must not be dangling
5698 pub unsafe fn GetSystemProperties(&self, count_ptr: *mut jint, property_ptr: *mut *mut *mut c_char) -> jvmtiError {
5699 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jint, *mut *mut *mut c_char) -> jvmtiError>(129)(self.vtable, count_ptr, property_ptr) }
5700 }
5701
5702 /// Return a VM system property value given the property key.
5703 ///
5704 /// The function `GetSystemProperties` returns the set of property keys which may be used.
5705 /// The properties which can be retrieved may grow during execution.
5706 ///
5707 /// Since this is a VM view of system properties, the values of properties may differ from that returned by java.lang.System.getProperty(String).
5708 /// A typical VM might copy the values of the VM system properties into the Properties held by java.lang.System during the initialization of that class.
5709 /// Thereafter any changes to the VM system properties (with `SetSystemProperty`) or the java.lang.System system properties (with java.lang.System.setProperty(String,String))
5710 /// would cause the values to diverge.
5711 /// JNI method invocation may be used to access java.lang.System.getProperty(String).
5712 ///
5713 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetSystemProperty>
5714 ///
5715 /// # Safety
5716 /// `property` must be a rust string, a valid utf-8 zero terminated string or null.
5717 /// all pointer parameters must not be dangling
5718 pub unsafe fn GetSystemProperty(&self, property: impl UseCString, value_ptr: *mut *mut c_char) -> jvmtiError {
5719 unsafe {
5720 property.use_as_const_c_char(|property| {
5721 self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const c_char, *mut *mut c_char) -> jvmtiError>(130)(self.vtable, property, value_ptr)
5722 })
5723 }
5724 }
5725
5726 /// Set a VM system property value.
5727 ///
5728 /// The function `GetSystemProperties` returns the set of property keys, some of these may be settable. See `GetSystemProperty`.
5729 ///
5730 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetSystemProperty>
5731 ///
5732 /// # Safety
5733 /// `property` must be a rust string, a valid utf-8 zero terminated string or null.
5734 /// all pointer parameters must not be dangling
5735 pub unsafe fn SetSystemProperty(&self, property: impl UseCString, value_ptr: impl UseCString) -> jvmtiError {
5736 unsafe {
5737 property.use_as_const_c_char(|property| {
5738 value_ptr.use_as_const_c_char(|value_ptr| {
5739 self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const c_char, *const c_char) -> jvmtiError>(131)(self.vtable, property, value_ptr)
5740 })
5741 })
5742 }
5743 }
5744
5745 /// Shutdown a JVM TI connection created with JNI `GetEnv` (see JVM TI Environments).
5746 ///
5747 /// Dispose of any resources held by the environment.
5748 /// Threads suspended by this environment are not resumed by this call, this must be done explicitly by the agent.
5749 /// Memory allocated by this environment via calls to JVM TI functions is not released, this can be done explicitly by the agent by calling Deallocate.
5750 /// Raw monitors created by this environment are not destroyed, this can be done explicitly by the agent by calling `DestroyRawMonitor`.
5751 /// The state of threads waiting on raw monitors created by this environment are not affected.
5752 /// Any native method prefixes for this environment will be unset; the agent must remove any prefixed native methods before dispose is called.
5753 /// Any capabilities held by this environment are relinquished.
5754 /// Events enabled by this environment will no longer be sent, however event handlers currently running will continue to run.
5755 ///
5756 /// Caution must be exercised in the design of event handlers whose environment may be disposed and thus become invalid during their execution.
5757 /// This environment may not be used after this call. This call returns to the caller.
5758 ///
5759 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#DisposeEnvironment>
5760 ///
5761 /// # Safety
5762 /// The environment must not be used anymore after this call. Any call to any other function on this environment once this method is called is undefined behavior.
5763 pub unsafe fn DisposeEnvironment(&self) -> jvmtiError {
5764 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable) -> jvmtiError>(126)(self.vtable) }
5765 }
5766
5767 /// The VM stores a pointer value associated with each environment.
5768 ///
5769 /// This pointer value is called environment-local storage. This value is NULL unless set with this function.
5770 /// Agents can allocate memory in which they store environment specific information.
5771 /// By setting environment-local storage it can then be accessed with `GetEnvironmentLocalStorage`.
5772 /// Called by the agent to set the value of the JVM TI environment-local storage.
5773 /// JVM TI supplies to the agent a pointer-size environment-local storage that can be used to record per-environment information.
5774 ///
5775 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetEnvironmentLocalStorage>
5776 ///
5777 /// # Safety
5778 /// JVM implementation specific
5779 pub unsafe fn SetEnvironmentLocalStorage(&self, data: *const c_void) -> jvmtiError {
5780 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *const c_void) -> jvmtiError>(147)(self.vtable, data) }
5781 }
5782
5783 /// The VM stores a pointer value associated with each environment.
5784 ///
5785 /// This pointer value is called environment-local storage. This value is NULL unless set with this function.
5786 /// Agents can allocate memory in which they store environment specific information.
5787 /// By setting environment-local storage it can then be accessed with `GetEnvironmentLocalStorage`.
5788 /// Called by the agent to set the value of the JVM TI environment-local storage.
5789 /// JVM TI supplies to the agent a pointer-size environment-local storage that can be used to record per-environment information.
5790 ///
5791 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetEnvironmentLocalStorage>
5792 ///
5793 /// # Safety
5794 /// all pointer parameters must not be dangling
5795 pub unsafe fn GetEnvironmentLocalStorage(&self, data: *mut *mut c_void) -> jvmtiError {
5796 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut *mut c_void) -> jvmtiError>(146)(self.vtable, data) }
5797 }
5798
5799 /// Return the symbolic name for an error code.
5800 ///
5801 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetErrorName>
5802 ///
5803 /// # Safety
5804 /// all pointer parameters must not be dangling
5805 pub unsafe fn GetErrorName(&self, error: impl Into<jvmtiError>, name_ptr: *mut *mut c_char) -> jvmtiError {
5806 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jvmtiError, *mut *mut c_char) -> jvmtiError>(127)(self.vtable, error.into(), name_ptr) }
5807 }
5808
5809 /// Control verbose output.
5810 ///
5811 /// This is the output which typically is sent to stderr.
5812 ///
5813 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetVerboseFlag>
5814 ///
5815 /// # Safety
5816 /// jvm implementation specific
5817 pub unsafe fn SetVerboseFlag(&self, flag: jvmtiVerboseFlag, value: jboolean) -> jvmtiError {
5818 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jvmtiVerboseFlag, jboolean) -> jvmtiError>(149)(self.vtable, flag, value) }
5819 }
5820
5821 /// This function describes the representation of jlocation used in this VM.
5822 ///
5823 /// If the returned format is `JVMTI_JLOCATION_JVMBCI`, jlocations can be used as in indices into the array returned by `GetBytecodes`.
5824 ///
5825 /// Although the greatest functionality is achieved with location information referencing the virtual machine bytecode index,
5826 /// the definition of jlocation has intentionally been left unconstrained to allow VM implementations that do not have this information.
5827 ///
5828 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#GetJLocationFormat>
5829 ///
5830 /// # Safety
5831 /// all pointer parameters must not be dangling
5832 pub unsafe fn GetJLocationFormat(&self, format_ptr: *mut jvmtiJlocationFormat) -> jvmtiError {
5833 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, *mut jvmtiJlocationFormat) -> jvmtiError>(128)(self.vtable, format_ptr) }
5834 }
5835
5836 /// Generate a `SampledObjectAlloc` event when objects are allocated.
5837 ///
5838 /// Each thread keeps a counter of bytes allocated. The event will only be generated when that counter exceeds an average of `sampling_interval` since the last sample.
5839 /// Setting `sampling_interval` to 0 will cause an event to be generated by each allocation supported by the system once the new interval is taken into account.
5840 /// Note that updating the new sampling interval might take various number of allocations to provoke internal data structure updates.
5841 /// Therefore it is important to consider the sampling interval as an average.
5842 /// This includes the interval 0, where events might not be generated straight away for each allocation.
5843 ///
5844 /// See <https://docs.oracle.com/en/java/javase/24/docs/specs/jvmti.html#SetHeapSamplingInterval>
5845 ///
5846 /// # Safety
5847 /// all pointer parameters must not be dangling
5848 pub unsafe fn SetHeapSamplingInterval(&self, sampling_interval: jint) -> jvmtiError {
5849 unsafe { self.jvmti::<extern "system" fn(JVMTIEnvVTable, jint) -> jvmtiError>(155)(self.vtable, sampling_interval) }
5850 }
5851}
5852
5853#[derive(Debug, Copy, Clone)]
5854#[repr(transparent)]
5855pub struct jniNativeInterface(SyncMutPtr<*mut c_void>);
5856
5857impl From<jniNativeInterface> for *mut c_void {
5858 fn from(value: jniNativeInterface) -> Self {
5859 value.0.inner().cast()
5860 }
5861}
5862
5863impl jniNativeInterface {
5864 ///
5865 /// Returns uninitialized jniNativeInterface.
5866 /// The interface must be initialized with a call to `JVMTIEnv::GetJNIFunctionTable`
5867 /// before it can be used in any way.
5868 ///
5869 /// # Undefined behavior of uninitialized `jniNativeInterface`
5870 /// Calling any jvmti fn is ub.
5871 /// Calling any unsafe fn is ub.
5872 #[must_use]
5873 pub const fn new_uninit() -> Self {
5874 Self(SyncMutPtr::null())
5875 }
5876
5877 /// Constructs a new jniNativeInterface from a raw pointer.
5878 ///
5879 /// # Safety
5880 /// Unless the raw pointer was constructed by an invocation on `JVMTIEnv::GetJNIFunctionTable`
5881 /// then the using the resulting `jniNativeInterface` in any way is UB.
5882 #[must_use]
5883 pub const unsafe fn from_raw_ptr(ptr: *mut c_void) -> Self {
5884 Self(SyncMutPtr::new(ptr.cast()))
5885 }
5886
5887 ///
5888 /// Overwrites function in this `jniNativeInterface`
5889 ///
5890 /// # Safety
5891 /// if value is not a function with a matching signature/calling convention
5892 /// then putting the `jniNativeInterface` into use will trigger UB once that linkage is later used.
5893 ///
5894 /// # Example
5895 /// ```rust
5896 /// use jni_simple::*;
5897 ///
5898 /// extern "system" fn hooked_get_version(_env: JNIEnv) -> jint {
5899 /// println!("JNIEnv GetVersion was called!");
5900 /// JNI_VERSION_1_8
5901 /// }
5902 ///
5903 /// fn install_hook(env: JVMTIEnv) {
5904 /// unsafe {
5905 /// let mut iface = jniNativeInterface::new_uninit();
5906 /// assert_eq!(env.GetJNIFunctionTable(&mut iface), JVMTI_ERROR_NONE);
5907 /// iface.set(JNILinkage::GetVersion, hooked_get_version as _);
5908 /// assert_eq!(env.SetJNIFunctionTable(iface), JVMTI_ERROR_NONE);
5909 /// }
5910 /// }
5911 /// ```
5912 ///
5913 pub unsafe fn set(&self, linkage: impl AsJNILinkage, value: *mut c_void) {
5914 unsafe {
5915 self.0.add(linkage.linkage()).write_volatile(value);
5916 }
5917 }
5918
5919 ///
5920 /// Returns a function in this `jniNativeInterface`
5921 /// This is usually used to retrieve the unhooked original function from a `jniNativeInterface`
5922 ///
5923 /// # Safety
5924 /// The size of X must be usize (a function pointer).
5925 ///
5926 /// # Example
5927 /// This example illustrates hooking of the `GetVersion` function.
5928 /// The hooked function calls the original function and prints the result to stdout.
5929 /// ```rust
5930 /// use std::ffi::c_void;
5931 /// use std::ops::DerefMut;
5932 /// use std::sync::OnceLock;
5933 /// use jni_simple::*;
5934 ///
5935 /// static ORIGINAL_FUNCTIONS: OnceLock<jniNativeInterface> = OnceLock::new();
5936 ///
5937 /// extern "system" fn hooked_get_version(env: JNIEnv) -> jint {
5938 /// println!("JNIEnv GetVersion will be called!");
5939 /// let guard = ORIGINAL_FUNCTIONS.get().unwrap();
5940 /// let result = unsafe {
5941 /// guard.get::<extern "system" fn(*mut c_void) -> jint>(JNILinkage::GetVersion)(env.vtable())
5942 /// };
5943 ///
5944 /// println!("JNIEnv GetVersion returned {result}!");
5945 /// result
5946 /// }
5947 ///
5948 /// fn install_hook(env: JVMTIEnv) {
5949 /// unsafe {
5950 /// _= ORIGINAL_FUNCTIONS.get_or_init(|| {
5951 /// let mut iface = jniNativeInterface::new_uninit();
5952 /// assert_eq!(env.GetJNIFunctionTable(&mut iface), JVMTI_ERROR_NONE);
5953 /// iface
5954 /// });
5955 ///
5956 /// let mut iface = jniNativeInterface::new_uninit();
5957 /// assert_eq!(env.GetJNIFunctionTable(&mut iface), JVMTI_ERROR_NONE);
5958 /// iface.set(JNILinkage::GetVersion, hooked_get_version as _);
5959 /// assert_eq!(env.SetJNIFunctionTable(iface), JVMTI_ERROR_NONE);
5960 /// }
5961 /// }
5962 /// ```
5963 ///
5964 pub unsafe fn get<X>(&self, linkage: impl AsJNILinkage) -> X {
5965 unsafe { core::mem::transmute_copy(&self.0.add(linkage.linkage()).read_volatile()) }
5966 }
5967}
5968
5969/// Enum of all known jni linkage numbers
5970/// This is mostly useful for use with jvmti when hooking jvm functions.
5971#[derive(Debug, Copy, Clone, Ord, PartialOrd, PartialEq, Eq, Default)]
5972#[repr(usize)]
5973pub enum JNILinkage {
5974 #[default]
5975 GetVersion = 4,
5976
5977 DefineClass = 5,
5978 FindClass = 6,
5979
5980 FromReflectedMethod = 7,
5981 FromReflectedField = 8,
5982 ToReflectedMethod = 9,
5983
5984 GetSuperclass = 10,
5985 IsAssignableFrom = 11,
5986
5987 ToReflectedField = 12,
5988
5989 Throw = 13,
5990 ThrowNew = 14,
5991 ExceptionOccurred = 15,
5992 ExceptionDescribe = 16,
5993 ExceptionClear = 17,
5994 FatalError = 18,
5995
5996 PushLocalFrame = 19,
5997 PopLocalFrame = 20,
5998
5999 NewGlobalRef = 21,
6000 DeleteGlobalRef = 22,
6001 DeleteLocalRef = 23,
6002 IsSameObject = 24,
6003 NewLocalRef = 25,
6004 EnsureLocalCapacity = 26,
6005
6006 AllocObject = 27,
6007 NewObject = 28,
6008 NewObjectV = 29,
6009 NewObjectA = 30,
6010
6011 GetObjectClass = 31,
6012 IsInstanceOf = 32,
6013
6014 GetMethodID = 33,
6015
6016 CallObjectMethod = 34,
6017 CallObjectMethodV = 35,
6018 CallObjectMethodA = 36,
6019 CallBooleanMethod = 37,
6020 CallBooleanMethodV = 38,
6021 CallBooleanMethodA = 39,
6022 CallByteMethod = 40,
6023 CallByteMethodV = 41,
6024 CallByteMethodA = 42,
6025 CallCharMethod = 43,
6026 CallCharMethodV = 44,
6027 CallCharMethodA = 45,
6028 CallShortMethod = 46,
6029 CallShortMethodV = 47,
6030 CallShortMethodA = 48,
6031 CallIntMethod = 49,
6032 CallIntMethodV = 50,
6033 CallIntMethodA = 51,
6034 CallLongMethod = 52,
6035 CallLongMethodV = 53,
6036 CallLongMethodA = 54,
6037 CallFloatMethod = 55,
6038 CallFloatMethodV = 56,
6039 CallFloatMethodA = 57,
6040 CallDoubleMethod = 58,
6041 CallDoubleMethodV = 59,
6042 CallDoubleMethodA = 60,
6043 CallVoidMethod = 61,
6044 CallVoidMethodV = 62,
6045 CallVoidMethodA = 63,
6046
6047 CallNonvirtualObjectMethod = 64,
6048 CallNonvirtualObjectMethodV = 65,
6049 CallNonvirtualObjectMethodA = 66,
6050 CallNonvirtualBooleanMethod = 67,
6051 CallNonvirtualBooleanMethodV = 68,
6052 CallNonvirtualBooleanMethodA = 69,
6053 CallNonvirtualByteMethod = 70,
6054 CallNonvirtualByteMethodV = 71,
6055 CallNonvirtualByteMethodA = 72,
6056 CallNonvirtualCharMethod = 73,
6057 CallNonvirtualCharMethodV = 74,
6058 CallNonvirtualCharMethodA = 75,
6059 CallNonvirtualShortMethod = 76,
6060 CallNonvirtualShortMethodV = 77,
6061 CallNonvirtualShortMethodA = 78,
6062 CallNonvirtualIntMethod = 79,
6063 CallNonvirtualIntMethodV = 80,
6064 CallNonvirtualIntMethodA = 81,
6065 CallNonvirtualLongMethod = 82,
6066 CallNonvirtualLongMethodV = 83,
6067 CallNonvirtualLongMethodA = 84,
6068 CallNonvirtualFloatMethod = 85,
6069 CallNonvirtualFloatMethodV = 86,
6070 CallNonvirtualFloatMethodA = 87,
6071 CallNonvirtualDoubleMethod = 88,
6072 CallNonvirtualDoubleMethodV = 89,
6073 CallNonvirtualDoubleMethodA = 90,
6074 CallNonvirtualVoidMethod = 91,
6075 CallNonvirtualVoidMethodV = 92,
6076 CallNonvirtualVoidMethodA = 93,
6077
6078 GetFieldID = 94,
6079
6080 GetObjectField = 95,
6081 GetBooleanField = 96,
6082 GetByteField = 97,
6083 GetCharField = 98,
6084 GetShortField = 99,
6085 GetIntField = 100,
6086 GetLongField = 101,
6087 GetFloatField = 102,
6088 GetDoubleField = 103,
6089 SetObjectField = 104,
6090 SetBooleanField = 105,
6091 SetByteField = 106,
6092 SetCharField = 107,
6093 SetShortField = 108,
6094 SetIntField = 109,
6095 SetLongField = 110,
6096 SetFloatField = 111,
6097 SetDoubleField = 112,
6098
6099 GetStaticMethodID = 113,
6100
6101 CallStaticObjectMethod = 114,
6102 CallStaticObjectMethodV = 115,
6103 CallStaticObjectMethodA = 116,
6104 CallStaticBooleanMethod = 117,
6105 CallStaticBooleanMethodV = 118,
6106 CallStaticBooleanMethodA = 119,
6107 CallStaticByteMethod = 120,
6108 CallStaticByteMethodV = 121,
6109 CallStaticByteMethodA = 122,
6110 CallStaticCharMethod = 123,
6111 CallStaticCharMethodV = 124,
6112 CallStaticCharMethodA = 125,
6113 CallStaticShortMethod = 126,
6114 CallStaticShortMethodV = 127,
6115 CallStaticShortMethodA = 128,
6116 CallStaticIntMethod = 129,
6117 CallStaticIntMethodV = 130,
6118 CallStaticIntMethodA = 131,
6119 CallStaticLongMethod = 132,
6120 CallStaticLongMethodV = 133,
6121 CallStaticLongMethodA = 134,
6122 CallStaticFloatMethod = 135,
6123 CallStaticFloatMethodV = 136,
6124 CallStaticFloatMethodA = 137,
6125 CallStaticDoubleMethod = 138,
6126 CallStaticDoubleMethodV = 139,
6127 CallStaticDoubleMethodA = 140,
6128 CallStaticVoidMethod = 141,
6129 CallStaticVoidMethodV = 142,
6130 CallStaticVoidMethodA = 143,
6131
6132 GetStaticFieldID = 144,
6133
6134 GetStaticObjectField = 145,
6135 GetStaticBooleanField = 146,
6136 GetStaticByteField = 147,
6137 GetStaticCharField = 148,
6138 GetStaticShortField = 149,
6139 GetStaticIntField = 150,
6140 GetStaticLongField = 151,
6141 GetStaticFloatField = 152,
6142 GetStaticDoubleField = 153,
6143
6144 SetStaticObjectField = 154,
6145 SetStaticBooleanField = 155,
6146 SetStaticByteField = 156,
6147 SetStaticCharField = 157,
6148 SetStaticShortField = 158,
6149 SetStaticIntField = 159,
6150 SetStaticLongField = 160,
6151 SetStaticFloatField = 161,
6152 SetStaticDoubleField = 162,
6153
6154 NewString = 163,
6155
6156 GetStringLength = 164,
6157 GetStringChars = 165,
6158 ReleaseStringChars = 166,
6159
6160 NewStringUTF = 167,
6161 GetStringUTFLength = 168,
6162 GetStringUTFChars = 169,
6163 ReleaseStringUTFChars = 170,
6164
6165 GetArrayLength = 171,
6166
6167 NewObjectArray = 172,
6168 GetObjectArrayElement = 173,
6169 SetObjectArrayElement = 174,
6170
6171 NewBooleanArray = 175,
6172 NewByteArray = 176,
6173 NewCharArray = 177,
6174 NewShortArray = 178,
6175 NewIntArray = 179,
6176 NewLongArray = 180,
6177 NewFloatArray = 181,
6178 NewDoubleArray = 182,
6179
6180 GetBooleanArrayElements = 183,
6181 GetByteArrayElements = 184,
6182 GetCharArrayElements = 185,
6183 GetShortArrayElements = 186,
6184 GetIntArrayElements = 187,
6185 GetLongArrayElements = 188,
6186 GetFloatArrayElements = 189,
6187 GetDoubleArrayElements = 190,
6188
6189 ReleaseBooleanArrayElements = 191,
6190 ReleaseByteArrayElements = 192,
6191 ReleaseCharArrayElements = 193,
6192 ReleaseShortArrayElements = 194,
6193 ReleaseIntArrayElements = 195,
6194 ReleaseLongArrayElements = 196,
6195 ReleaseFloatArrayElements = 197,
6196 ReleaseDoubleArrayElements = 198,
6197
6198 GetBooleanArrayRegion = 199,
6199 GetByteArrayRegion = 200,
6200 GetCharArrayRegion = 201,
6201 GetShortArrayRegion = 202,
6202 GetIntArrayRegion = 203,
6203 GetLongArrayRegion = 204,
6204 GetFloatArrayRegion = 205,
6205 GetDoubleArrayRegion = 206,
6206 SetBooleanArrayRegion = 207,
6207 SetByteArrayRegion = 208,
6208 SetCharArrayRegion = 209,
6209 SetShortArrayRegion = 210,
6210 SetIntArrayRegion = 211,
6211 SetLongArrayRegion = 212,
6212 SetFloatArrayRegion = 213,
6213 SetDoubleArrayRegion = 214,
6214
6215 RegisterNatives = 215,
6216 UnregisterNatives = 216,
6217
6218 MonitorEnter = 217,
6219 MonitorExit = 218,
6220
6221 GetJavaVM = 219,
6222
6223 GetStringRegion = 220,
6224 GetStringUTFRegion = 221,
6225
6226 GetPrimitiveArrayCritical = 222,
6227 ReleasePrimitiveArrayCritical = 223,
6228
6229 GetStringCritical = 224,
6230 ReleaseStringCritical = 225,
6231
6232 NewWeakGlobalRef = 226,
6233 DeleteWeakGlobalRef = 227,
6234
6235 ExceptionCheck = 228,
6236
6237 NewDirectByteBuffer = 229,
6238 GetDirectBufferAddress = 230,
6239 GetDirectBufferCapacity = 231,
6240
6241 GetObjectRefType = 232,
6242
6243 GetModule = 233,
6244
6245 IsVirtualThread = 234,
6246
6247 GetStringUTFLengthAsLong = 235,
6248}
6249
6250impl From<JNILinkage> for usize {
6251 fn from(value: JNILinkage) -> Self {
6252 value as Self
6253 }
6254}
6255
6256pub trait AsJNILinkage: SealedAsJNILinkage {}
6257
6258impl SealedAsJNILinkage for JNILinkage {
6259 fn linkage(self) -> usize {
6260 self as usize
6261 }
6262}
6263
6264impl AsJNILinkage for JNILinkage {}
6265
6266impl SealedAsJNILinkage for usize {
6267 fn linkage(self) -> usize {
6268 self
6269 }
6270}
6271
6272impl AsJNILinkage for usize {}
6273
6274impl SealedAsJNILinkage for i32 {
6275 fn linkage(self) -> usize {
6276 // Negative linkages dont exist, if someone passes a negative linkage
6277 // then its ub anyways and all bets are off.
6278 usize::try_from(self).unwrap_or_default()
6279 }
6280}
6281
6282/// The compiler unless you specify a suffix will assume i32.
6283/// This just makes it a bit easier to not have to write 6usize.
6284impl AsJNILinkage for i32 {}
6285
6286/// Vtable of `JNIEnv` is passed like this.
6287type JNIEnvVTable = *mut jniNativeInterface;
6288
6289#[derive(Debug, Clone, Copy)]
6290#[repr(transparent)]
6291pub struct JNIEnv {
6292 /// The vtable that contains all the functions
6293 vtable: JNIEnvVTable,
6294}
6295
6296impl SealedEnvVTable for JNIEnv {
6297 fn can_jni() -> bool {
6298 true
6299 }
6300
6301 fn can_jvmti() -> bool {
6302 false
6303 }
6304}
6305
6306impl From<*mut c_void> for JNIEnv {
6307 fn from(value: *mut c_void) -> Self {
6308 Self { vtable: value.cast() }
6309 }
6310}
6311
6312impl JNINativeMethod {
6313 #[must_use]
6314 pub const fn new(name: *const c_char, signature: *const c_char, function_pointer: *const c_void) -> Self {
6315 Self {
6316 name,
6317 signature,
6318 fnPtr: function_pointer,
6319 }
6320 }
6321
6322 #[must_use]
6323 pub const fn name(&self) -> *const c_char {
6324 self.name
6325 }
6326
6327 #[must_use]
6328 pub const fn signature(&self) -> *const c_char {
6329 self.signature
6330 }
6331
6332 #[must_use]
6333 pub const fn fnPtr(&self) -> *const c_void {
6334 self.fnPtr
6335 }
6336}
6337
6338impl JavaVMAttachArgs {
6339 pub const fn new(version: jint, name: *const c_char, group: jobject) -> Self {
6340 Self { version, name, group }
6341 }
6342
6343 #[must_use]
6344 pub const fn version(&self) -> jint {
6345 self.version
6346 }
6347 #[must_use]
6348 pub const fn name(&self) -> *const c_char {
6349 self.name
6350 }
6351 #[must_use]
6352 pub const fn group(&self) -> jobject {
6353 self.group
6354 }
6355}
6356
6357/// Helper trait that converts rusts various strings into a zero terminated c string for use with a JNI method.
6358///
6359/// This trait is implemented for:
6360/// `&str`, `String`, `&String`,
6361/// `CString`, `CStr`, `*const c_char`,
6362/// `&OsStr`, `OsString`, `&OsString`,
6363/// `&[u8]`, `Vec<u8>`,
6364///
6365/// If the String contains the equivalent of a 0 byte then the string stops at the 0 byte ignoring the rest of the string.
6366/// Any non Unicode characters in `OsString` and its derivatives will be replaced with the Unicode replacement character by using to `to_str_lossy` fn.
6367/// Using non utf-8 binary data in the u8 slices/Vec will not be checked for validity before being converted into a *const `c_char`!
6368///
6369/// Using invalid inputs on any call to JNI will result in undefined behavior.
6370///
6371pub trait UseCString: private::SealedUseCString {}
6372
6373/// The buffer is copied unless it contains a 0 byte.<br>
6374/// Fast case: last element is 0.
6375impl UseCString for &str {}
6376
6377impl private::SealedUseCString for &str {
6378 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6379 self.as_bytes().use_as_const_c_char(func)
6380 }
6381}
6382
6383/// String is extended using `reserve_exact` if it doesnt contain a 0 element. <br>
6384/// Fastest case: last element is 0. <br>
6385/// Fast case: buffer has room for one more element.
6386impl UseCString for String {}
6387
6388impl private::SealedUseCString for String {
6389 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6390 self.into_bytes().use_as_const_c_char(func)
6391 }
6392}
6393
6394/// The buffer is copied unless it contains a 0 byte.<br>
6395/// Fast case: last element is 0.
6396impl UseCString for &String {}
6397
6398impl private::SealedUseCString for &String {
6399 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6400 self.as_bytes().use_as_const_c_char(func)
6401 }
6402}
6403
6404/// Passed to JNI as is.
6405impl UseCString for CString {}
6406
6407impl private::SealedUseCString for CString {
6408 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6409 func(self.as_ptr())
6410 }
6411}
6412
6413/// Passed to JNI as is.
6414impl UseCString for &CString {}
6415
6416impl private::SealedUseCString for &CString {
6417 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6418 func(self.as_ptr())
6419 }
6420}
6421
6422/// Passed to JNI as is.
6423impl UseCString for &CStr {}
6424
6425impl private::SealedUseCString for &CStr {
6426 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6427 func(self.as_ptr())
6428 }
6429}
6430
6431/// Passed as is to the JVM
6432/// # Safety
6433/// Must either be null or point to a 0 terminated string.<br><br>
6434impl UseCString for *const i8 {}
6435
6436impl private::SealedUseCString for *const i8 {
6437 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6438 #[cfg(feature = "asserts")]
6439 {
6440 if self.is_null() {
6441 return func(self.cast());
6442 }
6443
6444 //If we are called on a non 0 terminated pointer then all bets are off anyway.
6445 let mut size = 0usize;
6446 loop {
6447 unsafe {
6448 if self.add(size).read_volatile() == 0 {
6449 break;
6450 }
6451 size += 1;
6452 }
6453 }
6454
6455 unsafe {
6456 let to_check: &[u8] = core::slice::from_raw_parts(self.cast(), size);
6457 assert!(
6458 core::str::from_utf8(to_check).is_ok(),
6459 "use_as_const_c_char called on a non utf-8 *const i8. string was only checked until first 0 byte or end of string. data={to_check:?}"
6460 );
6461 }
6462 }
6463
6464 func(self.cast())
6465 }
6466}
6467
6468/// Passed as is to the JVM
6469/// # Safety
6470/// Must either be null or point to a 0 terminated string.<br><br>
6471impl UseCString for *const u8 {}
6472
6473impl private::SealedUseCString for *const u8 {
6474 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6475 #[cfg(feature = "asserts")]
6476 {
6477 if self.is_null() {
6478 return func(self.cast());
6479 }
6480
6481 //If we are called on a non 0 terminated pointer then all bets are off anyway.
6482 let mut size = 0usize;
6483 loop {
6484 unsafe {
6485 if self.add(size).read_volatile() == 0 {
6486 break;
6487 }
6488 size += 1;
6489 }
6490 }
6491
6492 unsafe {
6493 let to_check = core::slice::from_raw_parts(self, size);
6494 assert!(
6495 core::str::from_utf8(to_check).is_ok(),
6496 "use_as_const_c_char called on a non utf-8 *const u8. string was only checked until first 0 byte or end of string. data={to_check:?}"
6497 );
6498 }
6499 }
6500
6501 func(self.cast())
6502 }
6503}
6504
6505/// Passed as is to the JVM
6506/// # Safety
6507/// Must either be null or point to a 0 terminated string.<br><br>
6508impl UseCString for *mut i8 {}
6509
6510impl private::SealedUseCString for *mut i8 {
6511 fn use_as_const_c_char<X>(self, param: impl FnOnce(*const c_char) -> X) -> X {
6512 self.cast_const().use_as_const_c_char(param)
6513 }
6514}
6515
6516/// Passed as is to the JVM
6517/// # Safety
6518/// Must either be null or point to a 0 terminated string.<br><br>
6519impl UseCString for *mut u8 {}
6520
6521impl private::SealedUseCString for *mut u8 {
6522 fn use_as_const_c_char<X>(self, param: impl FnOnce(*const c_char) -> X) -> X {
6523 self.cast_const().use_as_const_c_char(param)
6524 }
6525}
6526
6527/// The buffer is copied unless it contains a 0 byte.<br>
6528/// Fast case: last element is 0.
6529impl UseCString for Cow<'_, str> {}
6530
6531impl private::SealedUseCString for Cow<'_, str> {
6532 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6533 self.as_ref().use_as_const_c_char(func)
6534 }
6535}
6536
6537/// The buffer is copied unless it contains a 0 byte.<br>
6538/// Fast case: last element is 0.
6539impl UseCString for &Cow<'_, str> {}
6540
6541impl private::SealedUseCString for &Cow<'_, str> {
6542 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6543 self.as_ref().use_as_const_c_char(func)
6544 }
6545}
6546
6547/// The `OsString` is transformed to a String by calling `to_string_lossy`
6548/// and then used just like a `Cow<'_, str>` would be used.
6549#[cfg(feature = "std")]
6550impl UseCString for std::ffi::OsString {}
6551
6552#[cfg(feature = "std")]
6553impl private::SealedUseCString for std::ffi::OsString {
6554 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6555 self.to_string_lossy().use_as_const_c_char(func)
6556 }
6557}
6558
6559/// The `OsString` is transformed to a String by calling `to_string_lossy`
6560/// and then used just like a `Cow<'_, str>` would be used.
6561#[cfg(feature = "std")]
6562impl UseCString for &std::ffi::OsString {}
6563
6564#[cfg(feature = "std")]
6565impl private::SealedUseCString for &std::ffi::OsString {
6566 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6567 self.to_string_lossy().use_as_const_c_char(func)
6568 }
6569}
6570
6571/// The `OsString` is transformed to a String by calling `to_string_lossy`
6572/// and then used just like a `Cow<'_, str>` would be used.
6573#[cfg(feature = "std")]
6574impl UseCString for &std::ffi::OsStr {}
6575
6576#[cfg(feature = "std")]
6577impl private::SealedUseCString for &std::ffi::OsStr {
6578 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6579 self.to_string_lossy().use_as_const_c_char(func)
6580 }
6581}
6582
6583/// Vec is extended using `reserve_exact` if it doesnt contain a 0 element. <br>
6584/// Fastest case: last element is 0. <br>
6585/// Fast case: buffer has room for one more element.
6586impl UseCString for Vec<u8> {}
6587
6588impl private::SealedUseCString for Vec<u8> {
6589 fn use_as_const_c_char<X>(mut self, func: impl FnOnce(*const c_char) -> X) -> X {
6590 #[cfg(feature = "asserts")]
6591 {
6592 //Check for valid UTF-8
6593 let len = self.iter().position(|r| *r == 0).unwrap_or(self.len());
6594 let to_check = &self[..len];
6595 assert!(
6596 core::str::from_utf8(to_check).is_ok(),
6597 "use_as_const_c_char called with non utf-8 string. string was only checked until first 0 byte or end of string. data={to_check:?}"
6598 );
6599 }
6600
6601 let Some(last) = self.last().copied() else {
6602 return func([0i8].as_ptr().cast()); //Edge case empty string.
6603 };
6604
6605 if last == 0 {
6606 return func(self.as_ptr().cast());
6607 }
6608
6609 if self.capacity() > self.len() {
6610 //We own the Vec, faster to push 0 in this case, no need to copy or check for intermittent bytes.
6611 self.push(0);
6612 return func(self.as_ptr().cast());
6613 }
6614
6615 for n in &self {
6616 if *n == 0 {
6617 return func(self.as_ptr().cast());
6618 }
6619 }
6620
6621 self.reserve_exact(1); //We know the Vec will be dropped at the end of the scope.
6622 self.push(0); //Oh well guess we will have to copy the Vec...
6623 func(self.as_ptr().cast())
6624 }
6625}
6626
6627/// The buffer is copied unless it contains a 0 byte.<br>
6628/// Fast case: last element is 0.
6629impl UseCString for &Vec<u8> {}
6630
6631impl private::SealedUseCString for &Vec<u8> {
6632 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6633 self.as_slice().use_as_const_c_char(func)
6634 }
6635}
6636
6637/// The buffer is copied unless it contains a 0 byte.<br>
6638/// Fast case: last element is 0.
6639impl UseCString for &[u8] {}
6640
6641impl private::SealedUseCString for &[u8] {
6642 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6643 #[cfg(feature = "asserts")]
6644 {
6645 //Check for valid UTF-8
6646 let len = self.iter().position(|r| *r == 0).unwrap_or(self.len());
6647 let to_check = &self[..len];
6648 assert!(
6649 core::str::from_utf8(to_check).is_ok(),
6650 "use_as_const_c_char called with non utf-8 string. string was only checked until first 0 byte or end of string. data={to_check:?}",
6651 );
6652 }
6653
6654 let Some(last) = self.last().copied() else {
6655 return func([0i8].as_ptr().cast()); //Edge case empty string/slice.
6656 };
6657
6658 // Fast case, last byte in slice is 0
6659 if last == 0 {
6660 //We get here if the caller appends \0 to their rust string literals.
6661 return func(self.as_ptr().cast());
6662 }
6663
6664 // Impl detail: CStr::from_bytes_until_nul
6665 // will iterate the string from beginning to end to look for 0 byte,
6666 // so checking if last byte is 0 byte makes sense, especially for longer strings.
6667 // We do not care if there is a second 0 byte already somewhere in the middle of the string.
6668 if let Ok(c_str) = CStr::from_bytes_until_nul(self) {
6669 return func(c_str.as_ptr());
6670 }
6671
6672 // There no 0 byte in the slice. We have to copy the slice, append a 0 byte and then call downstream.
6673 // This is the slowest path. Unfortunately all ordinary ""
6674 // rust strings get here unless the caller explicitly made sure to add \0 to the end.
6675 let mut vec = self.to_vec();
6676 vec.reserve_exact(1);
6677 vec.push(0);
6678 func(vec.as_ptr().cast())
6679 }
6680}
6681
6682/// Convenience implementation that transforms to a null pointer when used with JNI.
6683impl UseCString for () {}
6684
6685impl private::SealedUseCString for () {
6686 fn use_as_const_c_char<X>(self, func: impl FnOnce(*const c_char) -> X) -> X {
6687 func(null())
6688 }
6689}
6690
6691impl JNIEnv {
6692 ///
6693 /// Resolves the function pointer given its linkage index of the jni vtable.
6694 /// The indices are documented and guaranteed by the Oracle JVM Spec.
6695 ///
6696 #[inline(always)]
6697 unsafe fn jni<X>(&self, index: usize) -> X {
6698 unsafe {
6699 //We need the read_volatile because a java debugger may at any point in time exchange the jni function table at its convenience.
6700 core::mem::transmute_copy(&(self.vtable.read_volatile().0.add(index).read_volatile()))
6701 }
6702 }
6703
6704 ///
6705 /// Raw indexes the JNI vtable.
6706 /// This can be used to call future JNI methods that jni-simple in the used version is not aware of.
6707 /// It can also be used to call undocumented implementation specific jni functions,
6708 /// or functions defined in a native java debugger.
6709 ///
6710 /// 99% of programs do not need to use this function.
6711 /// Use this function as a last resort.
6712 ///
6713 /// # Generic Type X
6714 /// Almost always a "extern system" function signature.
6715 /// The first parameter is nearly universally a pointer to the raw vtable.
6716 ///
6717 /// # Safety
6718 /// This function is very unsafe. If index is too large, you cause UB due to out of bounds read.
6719 /// The actual size of the vtable cannot be known and is JVM implementation specific.
6720 ///
6721 /// If the generic type X is wrong for the given index then you either cause UB instantly depending
6722 /// on if your supplied X has the same size as `c_void` or not,
6723 /// or once you use the result.
6724 ///
6725 /// # Example
6726 /// This shows how to call the JNI Function `GetVersion` using the raw vtable call.
6727 /// ```rust
6728 /// use std::ffi::c_void;
6729 /// use jni_simple::*;
6730 ///
6731 /// fn some_func(env: JNIEnv) {
6732 /// unsafe {
6733 /// // The linkage index for GetVersion is 4. See oracle documentation for a list of linkage indexes as well as their signature.
6734 /// // The calling convention is the "system" calling convention by default.
6735 /// // This is the same as "C" on linux but on Windows 32 bit its different. See jni.h and rusts calling convention documentation.
6736 /// let version: jint = env.index_vtable::<extern "system" fn(*mut c_void) -> jint>(4)(env.vtable());
6737 /// }
6738 /// }
6739 ///
6740 /// ```
6741 ///
6742 pub unsafe fn index_vtable<X>(&self, index: impl AsJNILinkage) -> X {
6743 unsafe { self.jni::<X>(index.linkage()) }
6744 }
6745
6746 /// Returns the raw jni vtable.
6747 /// This is usefully in some rare situations, especially when used with the `index_vtable` function.
6748 #[must_use]
6749 pub const fn vtable(&self) -> *mut c_void {
6750 self.vtable.cast()
6751 }
6752
6753 ///
6754 /// Returns the version of the JNI interface.
6755 ///
6756 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetVersion>
6757 ///
6758 /// The returned value must be compared against a constant. (They start with `JNI_VERSION`_...)
6759 /// Not every java version has such a constant.
6760 /// Only java versions where a function in the JNI interface was added has one.
6761 ///
6762 ///
6763 /// # Panics
6764 /// if asserts feature is enabled and UB was detected
6765 ///
6766 /// # Safety
6767 ///
6768 /// Current thread must not be detached from JNI.
6769 ///
6770 /// Current thread does not hold a critical reference.
6771 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
6772 ///
6773 /// Current thread is not currently throwing a Java exception.
6774 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
6775 ///
6776 ///
6777 /// # Example
6778 /// ```rust
6779 /// use jni_simple::{*};
6780 ///
6781 /// unsafe fn is_at_least_java10(env: JNIEnv) -> bool {
6782 /// env.GetVersion() >= JNI_VERSION_10
6783 /// }
6784 /// ```
6785 ///
6786 #[must_use]
6787 pub unsafe fn GetVersion(&self) -> jint {
6788 unsafe {
6789 #[cfg(feature = "asserts")]
6790 {
6791 self.check_not_critical("GetVersion");
6792 self.check_no_exception("GetVersion");
6793 }
6794 self.jni::<extern "system" fn(JNIEnvVTable) -> jint>(4)(self.vtable)
6795 }
6796 }
6797
6798 ///
6799 /// Defines a class in the given classloader.
6800 ///
6801 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#DefineClass>
6802 ///
6803 /// # Arguments
6804 /// * `name` - name of the class
6805 /// * `classloader` - handle to the classloader java object. This can be null if the current JNI classloader should be used.
6806 /// * `data` - the binary content of the compiled java .class file.
6807 /// * `len` - the length of the data in bytes.
6808 ///
6809 /// # Returns
6810 /// A local ref handle to the java.lang.Class (jclass) object that was just defined.
6811 /// On error null is returned.
6812 ///
6813 /// # Throws Java Exception:
6814 /// * `ClassFormatError` - if the class data does not specify a valid class.
6815 /// * `ClassCircularityError` - if a class or interface would be its own superclass or superinterface.
6816 /// * `OutOfMemoryError` - if the system runs out of memory.
6817 /// * `SecurityException` - if the caller attempts to define a class in the "java" package tree.
6818 ///
6819 ///
6820 /// # Panics
6821 /// if asserts feature is enabled and UB was detected
6822 ///
6823 /// # Safety
6824 ///
6825 /// Current thread must not be detached from JNI.
6826 ///
6827 /// Current thread does not hold a critical reference.
6828 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
6829 ///
6830 /// Current thread is not currently throwing a Java exception.
6831 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
6832 ///
6833 /// The `classloader` handle must be a valid handle if it is not null.
6834 /// `name` must be a valid pointer to a 0 terminated utf-8 string. It must not be null.
6835 /// `data` must not be null.
6836 /// `len` must not be larger than the actual length of the data.
6837 /// `len` must not be negative.
6838 ///
6839 /// # Example
6840 /// ```rust
6841 /// use std::ffi::CString;
6842 /// use core::ptr::null_mut;
6843 /// use jni_simple::{*};
6844 ///
6845 /// unsafe fn define_main_class(env: JNIEnv) -> jclass {
6846 /// let class_blob = &[0u8]; // = include_bytes!("../my_java_project/src/main/java/org/example/Main.class");
6847 /// let name = CString::new("org/example/Main").unwrap();
6848 /// let class = env.DefineClass(name.as_ptr(), null_mut(), class_blob.as_ptr().cast(), class_blob.len() as i32);
6849 /// if env.ExceptionCheck() {
6850 /// env.ExceptionDescribe();
6851 /// panic!("Failed to load main class check stderr for an error");
6852 /// }
6853 /// if class.is_null() {
6854 /// panic!("Failed to load main class. JVM did not throw an exception!"); //Unlikely
6855 /// }
6856 /// class
6857 /// }
6858 /// ```
6859 ///
6860 pub unsafe fn DefineClass(&self, name: impl UseCString, classloader: jobject, data: *const jbyte, len: jsize) -> jclass {
6861 unsafe {
6862 name.use_as_const_c_char(|name| {
6863 #[cfg(feature = "asserts")]
6864 {
6865 self.check_not_critical("DefineClass");
6866 self.check_no_exception("DefineClass");
6867 assert!(!name.is_null(), "DefineClass name is null");
6868 self.check_is_classloader_or_null("DefineClass", classloader);
6869 assert!(!data.is_null(), "DefineClass data is null");
6870 assert!(len >= 0, "DefineClass len is negative {len}");
6871 }
6872
6873 self.jni::<extern "system" fn(JNIEnvVTable, *const c_char, jobject, *const jbyte, i32) -> jclass>(5)(self.vtable, name, classloader, data, len)
6874 })
6875 }
6876 }
6877
6878 ///
6879 /// Defines a class in the given classloader.
6880 ///
6881 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#DefineClass>
6882 ///
6883 /// # Arguments
6884 /// * `name` - name of the class
6885 /// * `classloader` - handle to the classloader java object. This can be null if the current JNI classloader should be used.
6886 /// * `data` - the binary content of the compiled java .class file.
6887 ///
6888 /// # Returns
6889 /// A local ref handle to the java.lang.Class (jclass) object that was just defined.
6890 /// On error null is returned.
6891 ///
6892 /// # Throws Java Exception:
6893 /// * `ClassFormatError` - if the class data does not specify a valid class.
6894 /// * `ClassCircularityError` - if a class or interface would be its own superclass or superinterface.
6895 /// * `OutOfMemoryError` - if the system runs out of memory.
6896 /// * `SecurityException` - if the caller attempts to define a class in the "java" package tree.
6897 ///
6898 ///
6899 /// # Panics
6900 /// if asserts feature is enabled and UB was detected
6901 ///
6902 /// # Safety
6903 ///
6904 /// Current thread must not be detached from JNI.
6905 ///
6906 /// Current thread does not hold a critical reference.
6907 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
6908 ///
6909 /// Current thread is not currently throwing a Java exception.
6910 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
6911 ///
6912 /// The `classloader` handle must be a valid handle if it is not null.
6913 /// `name` must be a valid pointer to a 0 terminated utf-8 string. It must not be null.
6914 ///
6915 /// # Example
6916 /// ```rust
6917 /// use std::ffi::CString;
6918 /// use core::ptr::null_mut;
6919 /// use jni_simple::{*};
6920 ///
6921 /// unsafe fn define_main_class(env: JNIEnv) -> jclass {
6922 /// let class_blob = &[0u8]; // = include_bytes!("../my_java_project/src/main/java/org/example/Main.class");
6923 /// let name = CString::new("org/example/Main").unwrap();
6924 /// let class = env.DefineClass_from_slice(name.as_ptr(), null_mut(), class_blob);
6925 /// if env.ExceptionCheck() {
6926 /// env.ExceptionDescribe();
6927 /// panic!("Failed to load main class check stderr for an error");
6928 /// }
6929 /// if class.is_null() {
6930 /// panic!("Failed to load main class. JVM did not throw an exception!"); //Unlikely
6931 /// }
6932 /// class
6933 /// }
6934 /// ```
6935 ///
6936 pub unsafe fn DefineClass_from_slice(&self, name: impl UseCString, classloader: jobject, data: impl AsRef<[u8]>) -> jclass {
6937 unsafe {
6938 let slice = data.as_ref();
6939 self.DefineClass(
6940 name,
6941 classloader,
6942 slice.as_ptr().cast::<jbyte>(),
6943 jsize::try_from(slice.len()).expect("data.len() > jsize::MAX"),
6944 )
6945 }
6946 }
6947
6948 ///
6949 /// Finds or loads a class.
6950 /// If the class was previously loaded by the current JNI Classloader then it is returned.
6951 /// If the class was not previously loaded then the current JNI Classloader will attempt to
6952 /// load it.
6953 ///
6954 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#FindClass>
6955 ///
6956 /// # Arguments
6957 /// * `name` - name of the class in jni notation (i.e: "java/lang/Object")
6958 ///
6959 /// # Returns
6960 /// A local ref handle to the java.lang.Class (jclass) object.
6961 /// On error null is returned.
6962 ///
6963 /// # Throws Java Exception:
6964 /// * `ClassFormatError` - if the class data does not specify a valid class.
6965 /// * `ClassCircularityError` - if a class or interface would be its own superclass or superinterface.
6966 /// * `OutOfMemoryError` - if the system runs out of memory.
6967 /// * `NoClassDefFoundError` - if no definition for a requested class or interface can be found.
6968 ///
6969 ///
6970 /// # Panics
6971 /// if asserts feature is enabled and UB was detected
6972 ///
6973 /// # Safety
6974 ///
6975 /// Current thread must not be detached from JNI.
6976 ///
6977 /// Current thread does not hold a critical reference.
6978 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
6979 ///
6980 /// Current thread is not currently throwing a Java exception.
6981 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
6982 ///
6983 /// `name` must be a valid pointer to a 0 terminated utf-8 string. It must not be null.
6984 ///
6985 /// # Example
6986 /// ```rust
6987 /// use std::ffi::CString;
6988 /// use jni_simple::{*};
6989 ///
6990 /// unsafe fn find_main_class(env: JNIEnv) -> jclass {
6991 /// let name = CString::new("org/example/Main").unwrap();
6992 /// let class = env.FindClass(name.as_ptr());
6993 /// if env.ExceptionCheck() {
6994 /// env.ExceptionDescribe();
6995 /// panic!("Failed to find main class check stderr for an error");
6996 /// }
6997 /// if class.is_null() {
6998 /// panic!("Failed to find main class. JVM did not throw an exception!"); //Unlikely
6999 /// }
7000 /// class
7001 /// }
7002 /// ```
7003 ///
7004 pub unsafe fn FindClass(&self, name: impl UseCString) -> jclass {
7005 unsafe {
7006 name.use_as_const_c_char(|name| {
7007 #[cfg(feature = "asserts")]
7008 {
7009 self.check_not_critical("FindClass");
7010 self.check_no_exception("FindClass");
7011 assert!(!name.is_null(), "FindClass name is null");
7012 }
7013 self.jni::<extern "system" fn(JNIEnvVTable, *const c_char) -> jclass>(6)(self.vtable, name)
7014 })
7015 }
7016 }
7017
7018 ///
7019 /// Gets the superclass of the class `class`.
7020 ///
7021 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetSuperclass>
7022 ///
7023 /// # Arguments
7024 /// * `class` - handle to a class object. must not be null.
7025 ///
7026 /// # Returns
7027 /// A local ref handle to the superclass or null.
7028 /// If `class` refers to java.lang.Object class then null is returned.
7029 /// If `class` refers to any Interface then null is returned.
7030 ///
7031 ///
7032 ///
7033 /// # Panics
7034 /// if asserts feature is enabled and UB was detected
7035 ///
7036 /// # Safety
7037 ///
7038 /// Current thread must not be detached from JNI.
7039 ///
7040 /// Current thread does not hold a critical reference.
7041 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7042 ///
7043 /// Current thread is not currently throwing a Java exception.
7044 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
7045 ///
7046 /// `class` must be a valid non-null handle to a class object.
7047 ///
7048 /// # Example
7049 /// ```rust
7050 /// use jni_simple::{*};
7051 ///
7052 /// unsafe fn has_parent(env: JNIEnv, class: jclass) -> bool {
7053 /// if class.is_null() {
7054 /// return false;
7055 /// }
7056 /// let local = env.NewLocalRef(class);
7057 /// let parent_or_null = env.GetSuperclass(local);
7058 /// env.DeleteLocalRef(local);
7059 /// if parent_or_null.is_null() {
7060 /// return false;
7061 /// }
7062 /// env.DeleteLocalRef(parent_or_null);
7063 /// true
7064 /// }
7065 /// ```
7066 ///
7067 pub unsafe fn GetSuperclass(&self, class: jclass) -> jclass {
7068 unsafe {
7069 #[cfg(feature = "asserts")]
7070 {
7071 self.check_not_critical("GetSuperclass");
7072 self.check_no_exception("GetSuperclass");
7073 self.check_is_class("GetSuperclass", class);
7074 }
7075 self.jni::<extern "system" fn(JNIEnvVTable, jclass) -> jclass>(10)(self.vtable, class)
7076 }
7077 }
7078
7079 ///
7080 /// Determines whether an object of clazz1 can be safely cast to clazz2.
7081 ///
7082 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#IsAssignableFrom>
7083 ///
7084 /// # Arguments
7085 /// * `class1` - handle to a class object. must not be null.
7086 /// * `class2` - handle to a class object. must not be null.
7087 ///
7088 /// # Returns
7089 /// true if either:
7090 /// * class1 and class2 refer to the same class.
7091 /// * class1 is a subclass of class2.
7092 /// * class1 has class2 as one of its interfaces.
7093 ///
7094 ///
7095 /// # Panics
7096 /// if asserts feature is enabled and UB was detected
7097 ///
7098 /// # Safety
7099 ///
7100 /// Current thread must not be detached from JNI.
7101 ///
7102 /// Current thread does not hold a critical reference.
7103 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7104 ///
7105 /// Current thread is not currently throwing a Java exception.
7106 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
7107 ///
7108 /// `class1` and `class2` must be valid non-null handles to class objects.
7109 ///
7110 /// # Example
7111 /// ```rust
7112 /// use jni_simple::{*};
7113 ///
7114 /// unsafe fn is_throwable_class(env: JNIEnv, class: jclass) -> bool {
7115 /// let throwable_class = env.FindClass("java/lang/Throwable");
7116 /// if throwable_class.is_null() {
7117 /// env.ExceptionDescribe();
7118 /// panic!("java/lang/Throwable not found! See stderr!");
7119 /// }
7120 /// let local = env.NewLocalRef(class);
7121 /// if local.is_null() {
7122 /// env.DeleteLocalRef(throwable_class);
7123 /// return false;
7124 /// }
7125 /// let result = env.IsAssignableFrom(local, throwable_class);
7126 /// env.DeleteLocalRef(local);
7127 /// env.DeleteLocalRef(throwable_class);
7128 /// result
7129 /// }
7130 /// ```
7131 ///
7132 pub unsafe fn IsAssignableFrom(&self, class1: jclass, class2: jclass) -> bool {
7133 unsafe {
7134 #[cfg(feature = "asserts")]
7135 {
7136 self.check_not_critical("IsAssignableFrom");
7137 self.check_no_exception("IsAssignableFrom");
7138 self.check_is_class("IsAssignableFrom", class1);
7139 self.check_is_class("IsAssignableFrom", class2);
7140 }
7141 self.jni::<extern "system" fn(JNIEnvVTable, jclass, jclass) -> jboolean>(11)(self.vtable, class1, class2).as_bool()
7142 }
7143 }
7144
7145 ///
7146 /// Throws a java.lang.Throwable. This is roughly equal to the throw keyword in Java.
7147 ///
7148 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Throw>
7149 ///
7150 /// # Arguments
7151 /// * `throwable` - handle to an object which is instanceof java.lang.Throwable. must not be null.
7152 ///
7153 /// # Returns
7154 /// `JNI_OK` on success. a negative value on failure.
7155 ///
7156 /// ## If `JNI_OK` was returned
7157 /// The JVM will be throwing an exception as a result of this call.
7158 ///
7159 /// When the current thread is throwing an exception you may only call the following JNI functions:
7160 /// * `ExceptionOccurred`
7161 /// * `ExceptionDescribe`
7162 /// * `ExceptionClear`
7163 /// * `ExceptionCheck`
7164 /// * `ReleaseStringChars`
7165 /// * `ReleaseStringUTFChars`
7166 /// * `ReleaseStringCritical`
7167 /// * `Release<Type>ArrayElements`
7168 /// * `ReleasePrimitiveArrayCritical`
7169 /// * `DeleteLocalRef`
7170 /// * `DeleteGlobalRef`
7171 /// * `DeleteWeakGlobalRef`
7172 /// * `MonitorExit`
7173 /// * `PushLocalFrame`
7174 /// * `PopLocalFrame`
7175 ///
7176 /// Calling any other JNI function is UB.
7177 ///
7178 ///
7179 ///
7180 /// # Panics
7181 /// if asserts feature is enabled and UB was detected
7182 ///
7183 /// # Safety
7184 ///
7185 /// Current thread must not be detached from JNI.
7186 ///
7187 /// Current thread does not hold a critical reference.
7188 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7189 ///
7190 /// Current thread is not currently throwing a Java exception.
7191 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
7192 ///
7193 /// `throwable` must be a valid non-null handle to an object which is instanceof java.lang.Throwable.
7194 ///
7195 /// # Example
7196 /// ```rust
7197 /// use jni_simple::{*};
7198 ///
7199 /// unsafe fn throw_null_pointer_exception(env: JNIEnv) {
7200 /// let npe_class = env.FindClass("java/lang/NullPointerException");
7201 /// if npe_class.is_null() {
7202 /// env.ExceptionDescribe();
7203 /// panic!("java/lang/NullPointerException not found!");
7204 /// }
7205 /// let npe_constructor = env.GetMethodID(npe_class, "<init>", "()V");
7206 /// if npe_constructor.is_null() {
7207 /// env.ExceptionDescribe();
7208 /// env.DeleteLocalRef(npe_class);
7209 /// panic!("java/lang/NullPointerException has no zero arg constructor!");
7210 /// }
7211 ///
7212 /// let npe_obj = env.NewObject0(npe_class, npe_constructor);
7213 /// env.DeleteLocalRef(npe_class);
7214 /// if npe_obj.is_null() {
7215 /// env.ExceptionDescribe();
7216 /// panic!("java/lang/NullPointerException failed to call zero arg constructor!");
7217 /// }
7218 /// env.Throw(npe_obj);
7219 /// env.DeleteLocalRef(npe_obj);
7220 /// }
7221 /// ```
7222 ///
7223 pub unsafe fn Throw(&self, throwable: jthrowable) -> jint {
7224 unsafe {
7225 #[cfg(feature = "asserts")]
7226 {
7227 self.check_not_critical("Throw");
7228 self.check_no_exception("Throw");
7229 assert!(!throwable.is_null(), "Throw throwable is null");
7230 }
7231 self.jni::<extern "system" fn(JNIEnvVTable, jthrowable) -> jint>(13)(self.vtable, throwable)
7232 }
7233 }
7234
7235 ///
7236 /// Throws a new instance `class`. This is roughly equal to `throw new ...` in Java.
7237 ///
7238 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ThrowNew>
7239 ///
7240 /// # Arguments
7241 /// * `class` - handle to a non-abstract class instances of which can be cast to java.lang.Throwable. Must not be null.
7242 /// * `message` - the exception message. Must be null or a pointer to a 0 terminated utf-8 string.
7243 ///
7244 /// # Returns
7245 /// `JNI_OK` on success. a negative value on failure.
7246 ///
7247 /// ## If `JNI_OK` was returned
7248 /// The JVM will be throwing an exception as a result of this call.
7249 ///
7250 /// When the current thread is throwing an exception you may only call the following JNI functions:
7251 /// * `ExceptionOccurred`
7252 /// * `ExceptionDescribe`
7253 /// * `ExceptionClear`
7254 /// * `ExceptionCheck`
7255 /// * `ReleaseStringChars`
7256 /// * `ReleaseStringUTFChars`
7257 /// * `ReleaseStringCritical`
7258 /// * `Release<Type>ArrayElements`
7259 /// * `ReleasePrimitiveArrayCritical`
7260 /// * `DeleteLocalRef`
7261 /// * `DeleteGlobalRef`
7262 /// * `DeleteWeakGlobalRef`
7263 /// * `MonitorExit`
7264 /// * `PushLocalFrame`
7265 /// * `PopLocalFrame`
7266 ///
7267 /// Calling any other JNI function is UB.
7268 ///
7269 /// # Throws Java Exception:
7270 /// * `NoSuchMethodError` if the class has no suitable constructor for the argument supplied. Note: the return value remains `JNI_OK`!
7271 /// - null `message`: no zero arg or one arg String constructor exists.
7272 /// - non-null `message`: no one arg String constructor exists.
7273 ///
7274 ///
7275 /// # Panics
7276 /// if asserts feature is enabled and UB was detected
7277 ///
7278 /// # Safety
7279 ///
7280 /// Current thread must not be detached from JNI.
7281 ///
7282 /// Current thread does not hold a critical reference.
7283 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7284 ///
7285 /// Current thread is not currently throwing a Java exception.
7286 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
7287 ///
7288 /// `class` must be a valid non-null handle to a class which is:
7289 /// * Not abstract
7290 /// * Is a descendant of java.lang.Throwable (instances can be cast to Throwable)
7291 ///
7292 /// `message` must be a pointer to a 0 terminated utf-8 string or null.
7293 ///
7294 /// # Example
7295 /// ```rust
7296 /// use std::ffi::CString;
7297 /// use core::ptr::null;
7298 /// use jni_simple::{*};
7299 ///
7300 /// unsafe fn throw_illegal_argument_exception(env: JNIEnv, message: Option<&str>) {
7301 /// let npe_class = env.FindClass("java/lang/IllegalArgumentException");
7302 /// if npe_class.is_null() {
7303 /// env.ExceptionDescribe();
7304 /// panic!("java/lang/IllegalArgumentException not found!");
7305 /// }
7306 /// match message {
7307 /// None => {
7308 /// env.ThrowNew(npe_class, ());
7309 /// }
7310 /// Some(message) => {
7311 /// let message = CString::new(message).expect("message contains 0 byte!");
7312 /// env.ThrowNew(npe_class, message.as_ptr());
7313 /// }
7314 /// }
7315 /// env.DeleteLocalRef(npe_class);
7316 /// }
7317 /// ```
7318 ///
7319 pub unsafe fn ThrowNew(&self, class: jclass, message: impl UseCString) -> jint {
7320 unsafe {
7321 message.use_as_const_c_char(|message| {
7322 #[cfg(feature = "asserts")]
7323 {
7324 self.check_not_critical("ThrowNew");
7325 self.check_no_exception("ThrowNew");
7326 self.check_is_exception_class("ThrowNew", class);
7327 self.check_is_not_abstract("ThrowNew", class);
7328 }
7329 self.jni::<extern "system" fn(JNIEnvVTable, jclass, *const c_char) -> jint>(14)(self.vtable, class, message)
7330 })
7331 }
7332 }
7333
7334 ///
7335 /// Returns a local reference to the exception currently being thrown.
7336 /// Calling this function does not clear the exception.
7337 /// It stays thrown until for example `ExceptionClear` is called.
7338 ///
7339 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ExceptionOccurred>
7340 ///
7341 /// # Returns
7342 /// A local ref to the throwable that is currently being thrown.
7343 /// null if no throwable is currently thrown.
7344 ///
7345 ///
7346 /// # Panics
7347 /// if asserts feature is enabled and UB was detected
7348 ///
7349 /// # Safety
7350 ///
7351 /// Current thread must not be detached from JNI.
7352 ///
7353 /// Current thread does not hold a critical reference.
7354 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7355 ///
7356 /// # Example
7357 /// ```rust
7358 /// use jni_simple::{*};
7359 ///
7360 ///
7361 /// unsafe fn test(env: JNIEnv) {
7362 /// let special_exception = env.FindClass("org/example/SuperSpecialException");
7363 /// if special_exception.is_null() {
7364 /// unimplemented!("handle class not found")
7365 /// }
7366 /// let my_class = env.FindClass("org/example/TestClass");
7367 /// if my_class.is_null() {
7368 /// unimplemented!("handle class not found")
7369 /// }
7370 /// let my_zero_arg_constructor = env.GetMethodID(my_class, "<init>", "()V");
7371 /// if my_zero_arg_constructor.is_null() {
7372 /// unimplemented!("handle no zero arg constructor")
7373 /// }
7374 /// let my_object = env.NewObject0(my_class, my_zero_arg_constructor);
7375 /// if env.ExceptionCheck() {
7376 /// let exception_object = env.ExceptionOccurred();
7377 /// env.ExceptionClear();
7378 /// if env.IsInstanceOf(exception_object, special_exception) {
7379 /// panic!("zero arg constructor threw SuperSpecialException!")
7380 /// }
7381 ///
7382 /// unimplemented!("handle other exceptions");
7383 /// }
7384 /// unimplemented!()
7385 /// }
7386 /// ```
7387 ///
7388 #[must_use]
7389 pub unsafe fn ExceptionOccurred(&self) -> jthrowable {
7390 unsafe {
7391 #[cfg(feature = "asserts")]
7392 {
7393 self.check_not_critical("ExceptionOccurred");
7394 }
7395 self.jni::<extern "system" fn(JNIEnvVTable) -> jthrowable>(15)(self.vtable)
7396 }
7397 }
7398
7399 ///
7400 /// Print the stacktrace and message currently thrown to STDOUT.
7401 /// A side effect of this function is that the exception is also cleared.
7402 /// This is roughly equivalent to calling `java.lang.Throwable#printStackTrace()` in java.
7403 ///
7404 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ExceptionDescribe>
7405 ///
7406 /// If no exception is currently thrown then this method is a no-op.
7407 ///
7408 ///
7409 /// # Panics
7410 /// if asserts feature is enabled and UB was detected
7411 ///
7412 /// # Safety
7413 ///
7414 /// Current thread must not be detached from JNI.
7415 ///
7416 /// Current thread does not hold a critical reference.
7417 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7418 ///
7419 /// # Example
7420 /// ```rust
7421 /// use jni_simple::{*};
7422 ///
7423 ///
7424 /// unsafe fn test(env: JNIEnv) {
7425 /// let my_class = env.FindClass("org/example/TestClass");
7426 /// if my_class.is_null() {
7427 /// env.ExceptionDescribe();
7428 /// panic!("Class not found check stderr");
7429 /// }
7430 /// unimplemented!()
7431 /// }
7432 /// ```
7433 ///
7434 pub unsafe fn ExceptionDescribe(&self) {
7435 unsafe {
7436 #[cfg(feature = "asserts")]
7437 {
7438 self.check_not_critical("ExceptionDescribe");
7439 }
7440 self.jni::<extern "system" fn(JNIEnvVTable)>(16)(self.vtable);
7441 }
7442 }
7443
7444 ///
7445 /// Print the stacktrace and message currently thrown to STDOUT.
7446 /// A side effect of this function is that the exception is also cleared.
7447 /// This is roughly equivalent to calling `java.lang.Throwable#printStackTrace()` in java.
7448 ///
7449 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ExceptionDescribe>
7450 ///
7451 /// If no exception is currently thrown then this method is a no-op.
7452 ///
7453 ///
7454 /// # Panics
7455 /// if asserts feature is enabled and UB was detected
7456 ///
7457 /// # Safety
7458 ///
7459 /// Current thread must not be detached from JNI.
7460 ///
7461 /// Current thread does not hold a critical reference.
7462 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7463 ///
7464 /// # Example
7465 /// ```rust
7466 /// use jni_simple::{*};
7467 ///
7468 ///
7469 /// unsafe fn test(env: JNIEnv) {
7470 /// let mut my_class = env.FindClass("org/example/TestClass");
7471 /// if my_class.is_null() {
7472 /// env.ExceptionClear();
7473 /// my_class = env.FindClass("org/example/FallbackClass");
7474 /// }
7475 /// unimplemented!()
7476 /// }
7477 /// ```
7478 ///
7479 pub unsafe fn ExceptionClear(&self) {
7480 unsafe {
7481 #[cfg(feature = "asserts")]
7482 {
7483 self.check_not_critical("ExceptionClear");
7484 }
7485 self.jni::<extern "system" fn(JNIEnvVTable)>(17)(self.vtable);
7486 }
7487 }
7488
7489 ///
7490 /// Raises a fatal error and does not expect the VM to recover. This function does not return.
7491 ///
7492 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#FatalError>
7493 ///
7494 /// # Arguments
7495 /// * `msg` - message that should be present in the error report. 0 terminated utf-8. Must not be null.
7496 ///
7497 ///
7498 /// # Panics
7499 /// if asserts feature is enabled and UB was detected
7500 ///
7501 /// # Safety
7502 ///
7503 /// Current thread must not be detached from JNI.
7504 ///
7505 /// `msg` must be a non-null pointer to a valid 0 terminated utf-8 string.
7506 ///
7507 pub unsafe fn FatalError(&self, msg: impl UseCString) -> ! {
7508 unsafe {
7509 msg.use_as_const_c_char(|msg| {
7510 #[cfg(feature = "asserts")]
7511 {
7512 assert!(!msg.is_null(), "FatalError msg is null");
7513 }
7514 self.jni::<extern "system" fn(JNIEnvVTable, *const c_char)>(18)(self.vtable, msg);
7515 unreachable!("FatalError");
7516 })
7517 }
7518 }
7519
7520 ///
7521 /// Checks if an exception is thrown on the current thread.
7522 ///
7523 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ExceptionCheck>
7524 ///
7525 /// # Returns
7526 /// true if an exception is thrown on the current thread, false otherwise.
7527 ///
7528 ///
7529 /// # Panics
7530 /// if asserts feature is enabled and UB was detected
7531 ///
7532 /// # Safety
7533 ///
7534 /// Current thread must not be detached from JNI.
7535 ///
7536 /// Current thread does not hold a critical reference.
7537 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7538 ///
7539 /// # Example
7540 /// ```rust
7541 /// use jni_simple::{*};
7542 ///
7543 ///
7544 /// unsafe fn test(env: JNIEnv) {
7545 /// let my_class = env.FindClass("org/example/TestClass");
7546 /// if my_class.is_null() {
7547 /// unimplemented!("handle class not found")
7548 /// }
7549 /// let my_zero_arg_constructor = env.GetMethodID(my_class, "<init>", "()V");
7550 /// if my_zero_arg_constructor.is_null() {
7551 /// unimplemented!("handle no zero arg constructor")
7552 /// }
7553 /// let my_object = env.NewObject0(my_class, my_zero_arg_constructor);
7554 /// if env.ExceptionCheck() {
7555 /// panic!("org/example/TestClass zero arg constructor threw an exception!");
7556 /// }
7557 /// unimplemented!()
7558 /// }
7559 /// ```
7560 ///
7561 #[must_use]
7562 pub unsafe fn ExceptionCheck(&self) -> bool {
7563 unsafe {
7564 #[cfg(feature = "asserts")]
7565 {
7566 self.check_not_critical("ExceptionCheck");
7567 }
7568 self.jni::<extern "system" fn(JNIEnvVTable) -> jboolean>(228)(self.vtable).as_bool()
7569 }
7570 }
7571
7572 ///
7573 /// Creates a new global reference from an existing reference.
7574 ///
7575 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewGlobalRef>
7576 ///
7577 /// # Arguments
7578 /// * `obj` - a valid reference or null.
7579 ///
7580 /// # Returns
7581 /// the newly created global reference or null.
7582 /// null is returned if:
7583 /// * the argument `obj` is null
7584 /// * the system ran out of memory
7585 /// * `obj` is a weak reference that has already been garbage collected.
7586 ///
7587 ///
7588 /// # Panics
7589 /// if asserts feature is enabled and UB was detected
7590 ///
7591 /// # Safety
7592 ///
7593 /// Current thread must not be detached from JNI.
7594 ///
7595 /// Current thread does not hold a critical reference.
7596 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7597 ///
7598 /// Current thread is not currently throwing a Java exception.
7599 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
7600 ///
7601 /// `obj` must not refer to a reference that has already been deleted by calling `DeleteLocalRef`, `DeleteGlobalRef`, `DeleteWeakGlobalRef`
7602 ///
7603 pub unsafe fn NewGlobalRef(&self, obj: jobject) -> jobject {
7604 unsafe {
7605 #[cfg(feature = "asserts")]
7606 {
7607 self.check_not_critical("NewGlobalRef");
7608 self.check_no_exception("NewGlobalRef");
7609 }
7610 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jobject>(21)(self.vtable, obj)
7611 }
7612 }
7613
7614 ///
7615 /// Deletes a global reference to an object allowing the garbage collector to free it if no more
7616 /// references to it exists.
7617 ///
7618 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#DeleteGlobalRef>
7619 ///
7620 /// # Arguments
7621 /// * `obj` - a valid non-null global reference.
7622 ///
7623 ///
7624 /// # Panics
7625 /// if asserts feature is enabled and UB was detected
7626 ///
7627 /// # Safety
7628 ///
7629 /// Current thread must not be detached from JNI.
7630 ///
7631 /// Current thread does not hold a critical reference.
7632 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7633 ///
7634 /// Current thread is not currently throwing a Java exception.
7635 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
7636 ///
7637 /// `obj` must not be null.
7638 /// `obj` must be a global reference.
7639 /// `obj` must not refer to an already deleted global reference. (Double free)
7640 ///
7641 pub unsafe fn DeleteGlobalRef(&self, obj: jobject) {
7642 unsafe {
7643 #[cfg(feature = "asserts")]
7644 {
7645 self.check_not_critical("DeleteGlobalRef");
7646 assert!(!obj.is_null(), "DeleteGlobalRef obj is null");
7647 match self.GetObjectRefType(obj) {
7648 jobjectRefType::JNIInvalidRefType => panic!("DeleteGlobalRef invalid non null reference"),
7649 jobjectRefType::JNILocalRefType => panic!("DeleteGlobalRef local reference passed"),
7650 jobjectRefType::JNIWeakGlobalRefType => panic!("DeleteGlobalRef weak global reference passed"),
7651 jobjectRefType::JNIGlobalRefType => {}
7652 }
7653 }
7654 self.jni::<extern "system" fn(JNIEnvVTable, jobject)>(22)(self.vtable, obj);
7655 }
7656 }
7657
7658 ///
7659 /// Deletes a local reference to an object allowing the garbage collector to free it if no more
7660 /// references to it exists.
7661 ///
7662 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#DeleteGlobalRef>
7663 ///
7664 /// # Arguments
7665 /// * `obj` - a valid non-null local reference.
7666 ///
7667 ///
7668 /// # Panics
7669 /// if asserts feature is enabled and UB was detected
7670 ///
7671 /// # Safety
7672 ///
7673 /// Current thread must not be detached from JNI.
7674 ///
7675 /// Current thread does not hold a critical reference.
7676 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7677 ///
7678 /// Current thread is not currently throwing a Java exception.
7679 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
7680 ///
7681 /// `obj` must not be null.
7682 /// `obj` must be a local reference.
7683 /// `obj` must not refer to an already deleted local reference. (Double free)
7684 ///
7685 pub unsafe fn DeleteLocalRef(&self, obj: jobject) {
7686 unsafe {
7687 #[cfg(feature = "asserts")]
7688 {
7689 self.check_not_critical("DeleteLocalRef");
7690 assert!(!obj.is_null(), "DeleteLocalRef obj is null");
7691 if !self.ExceptionCheck() {
7692 match self.GetObjectRefType(obj) {
7693 jobjectRefType::JNIInvalidRefType => panic!("DeleteLocalRef invalid non null reference"),
7694 jobjectRefType::JNILocalRefType => {}
7695 jobjectRefType::JNIGlobalRefType => panic!("DeleteLocalRef global reference passed"),
7696 jobjectRefType::JNIWeakGlobalRefType => panic!("DeleteLocalRef weak global reference passed"),
7697 }
7698 }
7699 }
7700 self.jni::<extern "system" fn(JNIEnvVTable, jobject)>(23)(self.vtable, obj);
7701 }
7702 }
7703
7704 ///
7705 /// The jvm guarantees that a native method can have at least 16 local references.
7706 /// Creating any more than 16 local references without calling this function is effectively UB.
7707 /// This function instructs the JVM to ensure that at least
7708 /// `capacity` amount of local references are available for allocation.
7709 /// This function can be called multiple times to increase the amount of required locals.
7710 ///
7711 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#EnsureLocalCapacity>
7712 ///
7713 ///
7714 /// # Arguments
7715 /// * `capacity` - amount of local references the jvm must provide. Must be larger than 0.
7716 ///
7717 /// # Returns
7718 /// 0 on success, negative value indicating the error.
7719 ///
7720 /// # Throws Java Exception
7721 /// * `OutOfMemoryError` - if the vm runs out of memory ensuring capacity. This is never the case when 0 is returned.
7722 ///
7723 ///
7724 /// # Panics
7725 /// if asserts feature is enabled and UB was detected
7726 ///
7727 /// # Safety
7728 ///
7729 /// Current thread must not be detached from JNI.
7730 ///
7731 /// Current thread does not hold a critical reference.
7732 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7733 ///
7734 /// Current thread is not currently throwing a Java exception.
7735 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
7736 ///
7737 /// `capacity` must not be 0 or negative.
7738 ///
7739 /// ## Observed UB when more locals are allocated than ensured
7740 /// This behavior depends heavily on the jvm used and the arguments used to start it. This list is incomplete
7741 /// * Heap/Stack corruption.
7742 /// * JVM calls `FatalError` and aborts the process.
7743 /// * JVM Functions that would return a local reference return null.
7744 /// * JVM simply allocates more locals than ensured. (starting the jvm with -verbose:jni will log this)
7745 ///
7746 #[must_use]
7747 pub unsafe fn EnsureLocalCapacity(&self, capacity: jint) -> jint {
7748 unsafe {
7749 #[cfg(feature = "asserts")]
7750 {
7751 self.check_not_critical("EnsureLocalCapacity");
7752 self.check_no_exception("EnsureLocalCapacity");
7753 assert!(capacity >= 0, "EnsureLocalCapacity capacity is negative");
7754 }
7755 self.jni::<extern "system" fn(JNIEnvVTable, jint) -> jint>(26)(self.vtable, capacity)
7756 }
7757 }
7758
7759 ///
7760 /// Creates a new local reference frame, in which at least a given number of local references can be created.
7761 /// Note that local references already created in previous local frames are still valid in the current local frame.
7762 /// This method should be called by code that is called from unknown code where it is not known if enough
7763 /// local capacity is available. This method is superior to just increasing the capacity by calling `EnsureLocalCapacity`
7764 /// because that requires at least a rough knowledge of how many locals the caller itself has used and still needs.
7765 ///
7766 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#PushLocalFrame>
7767 ///
7768 ///
7769 /// # Arguments
7770 /// * `capacity` - amount of local references the jvm must provide. Must be larger than 0.
7771 ///
7772 /// # Returns
7773 /// 0 on success, negative value indicating the error.
7774 ///
7775 /// # Throws Java Exception
7776 /// * `OutOfMemoryError` - if the vm runs out of memory ensuring capacity. This is never the case when 0 is returned.
7777 ///
7778 ///
7779 /// # Panics
7780 /// if asserts feature is enabled and UB was detected
7781 ///
7782 /// # Safety
7783 ///
7784 /// Current thread must not be detached from JNI.
7785 ///
7786 /// Current thread does not hold a critical reference.
7787 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7788 ///
7789 /// Current thread is not currently throwing a Java exception.
7790 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/design.html#java_exceptions>
7791 ///
7792 /// `capacity` must not be 0 or negative.
7793 ///
7794 /// returning back to java code without cleaning up all created local reference frames by calling `PopLocalFrame` is UB.
7795 ///
7796 /// ## Observed UB when more locals are allocated than ensured
7797 /// This behavior depends heavily on the jvm used and the arguments used to start it. This list is incomplete
7798 /// * Heap/Stack corruption.
7799 /// * JVM calls `FatalError` and aborts the process.
7800 /// * JVM Functions that would return a local reference return null.
7801 /// * JVM simply allocates more locals than ensured. (starting the jvm with -verbose:jni will log this)
7802 ///
7803 #[must_use]
7804 pub unsafe fn PushLocalFrame(&self, capacity: jint) -> jint {
7805 unsafe {
7806 #[cfg(feature = "asserts")]
7807 {
7808 self.check_not_critical("PushLocalFrame");
7809 }
7810 self.jni::<extern "system" fn(JNIEnvVTable, jint) -> jint>(19)(self.vtable, capacity)
7811 }
7812 }
7813
7814 ///
7815 /// Pops a local reference frame created with `PushLocalFrame`
7816 /// All local references created within this reference frame are freed automatically
7817 /// and are no longer valid when this call returns.
7818 ///
7819 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#PopLocalFrame>
7820 ///
7821 /// # Arguments
7822 /// * result - arbitrary jni reference that should be moved to the parent reference frame.
7823 /// this is similar to a "return" value and may be null if no such result is needed.
7824 /// the local reference this function returns is valid within the parent local reference frame.
7825 ///
7826 /// # Returns
7827 /// A valid local reference that points to the same object as the reference `result`. Is null if `result` is null.
7828 ///
7829 ///
7830 /// # Panics
7831 /// if asserts feature is enabled and UB was detected
7832 ///
7833 /// # Safety
7834 ///
7835 /// Current thread must not be detached from JNI.
7836 ///
7837 /// Current thread does not hold a critical reference.
7838 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7839 ///
7840 /// result must be a valid reference or null
7841 ///
7842 ///
7843 pub unsafe fn PopLocalFrame(&self, result: jobject) -> jobject {
7844 unsafe {
7845 #[cfg(feature = "asserts")]
7846 {
7847 self.check_not_critical("PopLocalFrame");
7848 self.check_ref_obj_permit_null("PopLocalFrame", result);
7849 }
7850 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jobject>(20)(self.vtable, result)
7851 }
7852 }
7853
7854 ///
7855 /// Creates a new local reference from the given jobject.
7856 ///
7857 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewLocalRef>
7858 ///
7859 /// # Arguments
7860 /// * obj - arbitrary valid jni reference or null
7861 ///
7862 /// # Returns
7863 /// A valid local reference that points to the same object as the reference `obj`. Is null if `obj` is null.
7864 ///
7865 ///
7866 /// # Panics
7867 /// if asserts feature is enabled and UB was detected
7868 ///
7869 /// # Safety
7870 ///
7871 /// Current thread must not be detached from JNI.
7872 ///
7873 /// Current thread must not be throwing an exception.
7874 ///
7875 /// Current thread does not hold a critical reference.
7876 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7877 ///
7878 /// `obj` must be a valid reference or null
7879 ///
7880 pub unsafe fn NewLocalRef(&self, obj: jobject) -> jobject {
7881 unsafe {
7882 #[cfg(feature = "asserts")]
7883 {
7884 self.check_not_critical("NewLocalRef");
7885 self.check_no_exception("NewLocalRef");
7886 self.check_ref_obj_permit_null("NewLocalRef", obj);
7887 }
7888 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jobject>(25)(self.vtable, obj)
7889 }
7890 }
7891
7892 ///
7893 /// Creates a new weak global reference from the given jobject.
7894 ///
7895 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewWeakGlobalRef>
7896 ///
7897 /// # Arguments
7898 /// * obj - arbitrary valid jni reference or null
7899 ///
7900 /// # Returns
7901 /// A valid local weak global reference that points to the same object as the reference `obj`. Is null if `obj` is null.
7902 ///
7903 /// # Throws Java Exception
7904 /// If the JVM runs out of memory, an `OutOfMemoryError` will be thrown.
7905 ///
7906 ///
7907 /// # Panics
7908 /// if asserts feature is enabled and UB was detected
7909 ///
7910 /// # Safety
7911 ///
7912 /// Current thread must not be detached from JNI.
7913 ///
7914 /// Current thread must not be throwing an exception.
7915 ///
7916 /// Current thread does not hold a critical reference.
7917 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7918 ///
7919 /// `obj` must be a valid reference or null
7920 ///
7921 pub unsafe fn NewWeakGlobalRef(&self, obj: jobject) -> jweak {
7922 unsafe {
7923 #[cfg(feature = "asserts")]
7924 {
7925 self.check_not_critical("NewWeakGlobalRef");
7926 self.check_no_exception("NewWeakGlobalRef");
7927 }
7928 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jweak>(226)(self.vtable, obj)
7929 }
7930 }
7931
7932 ///
7933 /// Deletes a weak global reference.
7934 ///
7935 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#DeleteWeakGlobalRef>
7936 ///
7937 /// # Arguments
7938 /// * obj - a weak global reference.
7939 /// * must not already be deleted.
7940 /// * must not be null.
7941 /// * If the referred obj has been garbage collected by the JVM already or not is irrelevant.
7942 ///
7943 /// # Returns
7944 /// A valid local weak global reference that points to the same object as the reference `obj`. Is null if `obj` is null.
7945 ///
7946 ///
7947 /// # Panics
7948 /// if asserts feature is enabled and UB was detected
7949 ///
7950 /// # Safety
7951 ///
7952 /// Current thread must not be detached from JNI.
7953 ///
7954 /// Current thread does not hold a critical reference.
7955 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
7956 ///
7957 /// `obj` must not be null and be a valid weak reference that has not yet been deleted.
7958 ///
7959 pub unsafe fn DeleteWeakGlobalRef(&self, obj: jweak) {
7960 unsafe {
7961 #[cfg(feature = "asserts")]
7962 {
7963 self.check_not_critical("DeleteWeakGlobalRef");
7964 assert!(!obj.is_null(), "DeleteWeakGlobalRef obj is null");
7965 if !self.ExceptionCheck() {
7966 match self.GetObjectRefType(obj) {
7967 jobjectRefType::JNIInvalidRefType => panic!("DeleteWeakGlobalRef invalid non null reference"),
7968 jobjectRefType::JNILocalRefType => panic!("DeleteWeakGlobalRef local reference passed"),
7969 jobjectRefType::JNIGlobalRefType => panic!("DeleteWeakGlobalRef strong global reference passed"),
7970 jobjectRefType::JNIWeakGlobalRefType => {}
7971 }
7972 }
7973 }
7974
7975 self.jni::<extern "system" fn(JNIEnvVTable, jobject)>(227)(self.vtable, obj);
7976 }
7977 }
7978
7979 ///
7980 /// Allocates a new direct instance of the given class without calling any constructor.
7981 ///
7982 /// Every field in the instance will be the JVM default value for the type.
7983 /// * Every numeric is 0,
7984 /// * Every reference/object is null,
7985 /// * Every boolean is false,
7986 /// * Every array is null
7987 ///
7988 /// This will also not perform default initialization of types so a field that is initialized like this in java:
7989 /// ```java
7990 /// private int x = 5;
7991 /// ```
7992 /// This field would not be 5 but be 0 in the instance returned by `AllocObject`.
7993 ///
7994 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#AllocObject>
7995 ///
7996 /// # Note
7997 /// Be aware that the created instance may be initially in a state that is invalid for the given java object.
7998 /// Any object constructed using `AllocObject` should be brought into a valid state by essentially performing duties similar to
7999 /// what the constructor of that object would do. Handling errors during the subsequent initialization process can
8000 /// be especially tricky concerning object finalization. As part of error handling the object will likely be freed which
8001 /// then causes the JVM may run the finalization implementation on the object that is from a java point of view in an invalid state.
8002 /// This might cause undefined behavior in the jvm, depending on what the finalization implementation of the object does.
8003 /// Future Java releases have commited to removing object finalization. This restriction is known to apply to java 21 and lower.
8004 ///
8005 /// Calling any java methods on or with the partially initialized object should be avoided,
8006 /// as the jvm may for example have made assumptions about not yet initialized final fields.
8007 /// How the jvm reacts to this is entirely dependent on which jvm implementation you use and how it was started.
8008 ///
8009 /// # Arguments
8010 /// * `clazz` - reference to a class.
8011 /// * must not be null
8012 /// * must be valid
8013 /// * must not be already garbage collected
8014 ///
8015 /// # Returns
8016 /// A local reference to the newly created object or null if the object could not be created.
8017 ///
8018 /// # Throws Java Exception
8019 /// * `OutOfMemoryError`
8020 /// * if the jvm runs out of memory.
8021 /// * `InstantiationException`
8022 /// * if the class is an interface or an abstract class.
8023 ///
8024 ///
8025 ///
8026 /// # Panics
8027 /// if asserts feature is enabled and UB was detected
8028 ///
8029 /// # Safety
8030 ///
8031 /// Current thread must not be detached from JNI.
8032 ///
8033 /// Current thread does not hold a critical reference.
8034 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8035 ///
8036 /// `clazz` must not be null and be a valid reference that has not yet been deleted or garbage collected.
8037 ///
8038 ///
8039 pub unsafe fn AllocObject(&self, clazz: jclass) -> jobject {
8040 unsafe {
8041 #[cfg(feature = "asserts")]
8042 {
8043 assert!(!clazz.is_null(), "AllocObject clazz is null");
8044 self.check_not_critical("AllocObject");
8045 self.check_no_exception("AllocObject");
8046 self.check_is_class("AllocObject", clazz);
8047 }
8048 self.jni::<extern "system" fn(JNIEnvVTable, jclass) -> jobject>(27)(self.vtable, clazz)
8049 }
8050 }
8051
8052 ///
8053 /// Allocates an object by calling a constructor.
8054 ///
8055 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewObject>
8056 ///
8057 ///
8058 /// # Arguments
8059 /// * `clazz` - reference to a class.
8060 /// * must not be null
8061 /// * must be valid
8062 /// * must not be already garbage collected
8063 ///
8064 /// * `constructor` - jmethodID of a constructor
8065 /// * must be a constructor (`<init>` method name)
8066 /// * must be a constructor of `clazz`
8067 ///
8068 /// * args - java method parameters
8069 /// * can be null for 0 arg constructors.
8070 /// * must be a valid pointer into a jtype array with at least the same length as the java method has parameters.
8071 /// * the parameters must be valid types.
8072 ///
8073 /// # Returns
8074 /// A local reference to the newly created object or null if the object could not be created.
8075 ///
8076 /// # Throws Java Exception
8077 /// * `OutOfMemoryError`
8078 /// * if the jvm runs out of memory.
8079 /// * `InstantiationException`
8080 /// * if the class is an interface or an abstract class.
8081 /// * Any exception thrown by the constructor
8082 ///
8083 ///
8084 /// # Panics
8085 /// if asserts feature is enabled and UB was detected
8086 ///
8087 /// # Safety
8088 ///
8089 /// Current thread must not be detached from JNI.
8090 ///
8091 /// Current thread does not hold a critical reference.
8092 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8093 ///
8094 /// `clazz` must not be null and be a valid reference that has not yet been deleted or garbage collected.
8095 ///
8096 /// `constructor` must be a valid non-static methodID of `clazz` that is a constructor.
8097 ///
8098 /// `args` must be valid, have enough length and contain valid parameters for the method.
8099 /// * for example calling a java constructor that needs a String as parameter, with an 'int' instead is UB.
8100 ///
8101 pub unsafe fn NewObjectA(&self, clazz: jclass, constructor: jmethodID, args: *const jtype) -> jobject {
8102 unsafe {
8103 #[cfg(feature = "asserts")]
8104 {
8105 self.check_not_critical("NewObjectA");
8106 self.check_no_exception("NewObjectA");
8107 assert!(!constructor.is_null(), "NewObjectA constructor is null");
8108 self.check_is_class("NewObjectA", clazz);
8109 //TODO check if constructor is actually constructor or just a normal method.
8110 //TODO check arguments match constructor
8111 }
8112 self.jni::<extern "system" fn(JNIEnvVTable, jclass, jmethodID, *const jtype) -> jobject>(30)(self.vtable, clazz, constructor, args)
8113 }
8114 }
8115
8116 ///
8117 /// Creates a new object instance by calling the zero arg constructor.
8118 ///
8119 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewObject>
8120 ///
8121 ///
8122 /// # Arguments
8123 /// * `clazz` - reference to a class.
8124 /// * must not be null
8125 /// * must be valid
8126 /// * must not be already garbage collected
8127 /// * `constructor` - jmethodID of a constructor
8128 /// * must be a constructor
8129 /// * must be a constructor of `clazz`
8130 /// * must have 0 args
8131 ///
8132 /// # Returns
8133 /// A local reference to the newly created object or null if the object could not be created.
8134 ///
8135 /// # Throws Java Exception
8136 /// * `OutOfMemoryError`
8137 /// * if the jvm runs out of memory.
8138 /// * `InstantiationException`
8139 /// * if the class is an interface or an abstract class.
8140 /// * Any exception thrown by the constructor
8141 ///
8142 ///
8143 /// # Panics
8144 /// if asserts feature is enabled and UB was detected
8145 ///
8146 /// # Safety
8147 ///
8148 /// Current thread must not be detached from JNI.
8149 ///
8150 /// Current thread does not hold a critical reference.
8151 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8152 ///
8153 /// `clazz` must not be null and be a valid reference that has not yet been deleted or garbage collected.
8154 ///
8155 /// `constructor` must be a valid non-static methodID of `clazz` that is a constructor.
8156 ///
8157 /// `constructor` must have 0 arguments.
8158 ///
8159 pub unsafe fn NewObject0(&self, clazz: jclass, constructor: jmethodID) -> jobject {
8160 unsafe {
8161 #[cfg(feature = "asserts")]
8162 {
8163 self.check_not_critical("NewObject0");
8164 self.check_no_exception("NewObject0");
8165 assert!(!constructor.is_null(), "NewObject0 constructor is null");
8166 self.check_is_class("NewObject0", clazz);
8167 //TODO check if constructor is actually constructor or just a normal method.
8168 //TODO check zero arg.
8169 }
8170 self.jni::<extern "C" fn(JNIEnvVTable, jclass, jmethodID) -> jobject>(28)(self.vtable, clazz, constructor)
8171 }
8172 }
8173
8174 ///
8175 /// Creates a new object instance by calling the one arg constructor.
8176 ///
8177 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewObject>
8178 ///
8179 ///
8180 /// # Arguments
8181 /// * `clazz` - reference to a class.
8182 /// * must not be null
8183 /// * must be valid
8184 /// * must not be already garbage collected
8185 ///
8186 /// * `constructor` - jmethodID of a constructor
8187 /// * must be a constructor
8188 /// * must be a constructor of `clazz`
8189 /// * must have 1 arg
8190 ///
8191 /// * `arg1` - the argument
8192 /// * must be of the exact type that the constructor needs to be called with.
8193 ///
8194 /// # Returns
8195 /// A local reference to the newly created object or null if the object could not be created.
8196 ///
8197 /// # Throws Java Exception
8198 /// * `OutOfMemoryError`
8199 /// * if the jvm runs out of memory.
8200 /// * `InstantiationException`
8201 /// * if the class is an interface or an abstract class.
8202 /// * Any exception thrown by the constructor
8203 ///
8204 ///
8205 /// # Panics
8206 /// if asserts feature is enabled and UB was detected
8207 ///
8208 /// # Safety
8209 ///
8210 /// Current thread must not be detached from JNI.
8211 ///
8212 /// Current thread does not hold a critical reference.
8213 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8214 ///
8215 /// `clazz` must not be null and be a valid reference that has not yet been deleted or garbage collected.
8216 ///
8217 /// `constructor` must be a valid non-static methodID of `clazz` that is a constructor.
8218 ///
8219 /// `constructor` must have 1 argument.
8220 ///
8221 /// `JType` of `arg1` must match the argument type of the java method exactly.
8222 /// * absolutely no coercion is performed. Not even between trivially coercible types such as for example jint->jlong.
8223 /// * ex: calling a constructor that expects a jlong with a jint is UB.
8224 ///
8225 pub unsafe fn NewObject1<A: JType>(&self, clazz: jclass, constructor: jmethodID, arg1: A) -> jobject {
8226 unsafe {
8227 #[cfg(feature = "asserts")]
8228 {
8229 self.check_not_critical("NewObject1");
8230 self.check_no_exception("NewObject1");
8231 assert!(!constructor.is_null(), "NewObject1 constructor is null");
8232 self.check_is_class("NewObject1", clazz);
8233 //TODO check if constructor is actually constructor or just a normal method.
8234 self.check_parameter_types_constructor("NewObject1", clazz, constructor, arg1, 0, 1);
8235 }
8236 self.jni::<extern "C" fn(JNIEnvVTable, jclass, jmethodID, ...) -> jobject>(28)(self.vtable, clazz, constructor, arg1)
8237 }
8238 }
8239
8240 ///
8241 /// Creates a new object instance by calling the two arg constructor.
8242 ///
8243 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewObject>
8244 ///
8245 ///
8246 /// # Arguments
8247 /// * `clazz` - reference to a class.
8248 /// * must not be null
8249 /// * must be valid
8250 /// * must not be already garbage collected
8251 ///
8252 /// * `constructor` - jmethodID of a constructor
8253 /// * must be a constructor
8254 /// * must be a constructor of `clazz`
8255 /// * must have 2 args
8256 /// * `arg1` & `arg2` - the arguments
8257 /// * must be of the exact type that the constructor needs to be called with.
8258 ///
8259 /// # Returns
8260 /// A local reference to the newly created object or null if the object could not be created.
8261 ///
8262 /// # Throws Java Exception
8263 /// * `OutOfMemoryError`
8264 /// * if the jvm runs out of memory.
8265 /// * `InstantiationException`
8266 /// * if the class is an interface or an abstract class.
8267 /// * Any exception thrown by the constructor
8268 ///
8269 ///
8270 /// # Panics
8271 /// if asserts feature is enabled and UB was detected
8272 ///
8273 /// # Safety
8274 ///
8275 /// Current thread must not be detached from JNI.
8276 ///
8277 /// Current thread does not hold a critical reference.
8278 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8279 ///
8280 /// `clazz` must not be null and be a valid reference that has not yet been deleted or garbage collected.
8281 ///
8282 /// `constructor` must be a valid non-static methodID of `clazz` that is a constructor.
8283 ///
8284 /// `constructor` must have 2 arguments.
8285 ///
8286 /// `JType` of `arg1` & `arg2` must match the argument type of the java method exactly.
8287 /// * absolutely no coercion is performed. Not even between trivially coercible types such as for example jint->jlong.
8288 /// * ex: calling a constructor that expects a jlong with a jint is UB.
8289 ///
8290 pub unsafe fn NewObject2<A: JType, B: JType>(&self, clazz: jclass, constructor: jmethodID, arg1: A, arg2: B) -> jobject {
8291 unsafe {
8292 #[cfg(feature = "asserts")]
8293 {
8294 self.check_not_critical("NewObject2");
8295 self.check_no_exception("NewObject2");
8296 assert!(!constructor.is_null(), "NewObject2 constructor is null");
8297 self.check_is_class("NewObject2", clazz);
8298 //TODO check if constructor is actually constructor or just a normal method.
8299 self.check_parameter_types_constructor("NewObject2", clazz, constructor, arg1, 0, 2);
8300 self.check_parameter_types_constructor("NewObject2", clazz, constructor, arg2, 1, 2);
8301 }
8302 self.jni::<extern "C" fn(JNIEnvVTable, jclass, jmethodID, ...) -> jobject>(28)(self.vtable, clazz, constructor, arg1, arg2)
8303 }
8304 }
8305
8306 ///
8307 /// Creates a new object instance by calling the three arg constructor.
8308 ///
8309 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewObject>
8310 ///
8311 ///
8312 /// # Arguments
8313 /// * `clazz` - reference to a class.
8314 /// * must not be null
8315 /// * must be valid
8316 /// * must not be already garbage collected
8317 ///
8318 /// * `constructor` - jmethodID of a constructor
8319 /// * must be a constructor (`<init>` method name)
8320 /// * must be a constructor of `clazz`
8321 /// * must have 3 args
8322 ///
8323 /// * `arg1` & `arg2` & `arg3` - the arguments
8324 /// * must be of the exact type that the constructor needs to be called with.
8325 ///
8326 /// # Returns
8327 /// A local reference to the newly created object or null if the object could not be created.
8328 ///
8329 /// # Throws Java Exception
8330 /// * `OutOfMemoryError`
8331 /// * if the jvm runs out of memory.
8332 /// * `InstantiationException`
8333 /// * if the class is an interface or an abstract class.
8334 /// * Any exception thrown by the constructor
8335 ///
8336 ///
8337 /// # Panics
8338 /// if asserts feature is enabled and UB was detected
8339 ///
8340 /// # Safety
8341 ///
8342 /// Current thread must not be detached from JNI.
8343 ///
8344 /// Current thread does not hold a critical reference.
8345 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8346 ///
8347 /// `clazz` must not be null and be a valid reference that has not yet been deleted or garbage collected.
8348 ///
8349 /// `constructor` must be a valid non-static methodID of `clazz` that is a constructor
8350 ///
8351 /// `constructor` must have 2 arguments.
8352 ///
8353 /// `JType` of `arg1` & `arg2` & `arg3` must match the argument type of the java method exactly.
8354 /// * absolutely no coercion is performed. Not even between trivially coercible types such as for example jint->jlong.
8355 /// * ex: calling a constructor that expects a jlong with a jint is UB.
8356 ///
8357 pub unsafe fn NewObject3<A: JType, B: JType, C: JType>(&self, clazz: jclass, constructor: jmethodID, arg1: A, arg2: B, arg3: C) -> jobject {
8358 unsafe {
8359 #[cfg(feature = "asserts")]
8360 {
8361 self.check_not_critical("NewObject3");
8362 self.check_no_exception("NewObject3");
8363 assert!(!constructor.is_null(), "NewObject3 constructor is null");
8364 self.check_is_class("NewObject3", clazz);
8365 //TODO check if constructor is actually constructor or just a normal method.
8366 self.check_parameter_types_constructor("NewObject3", clazz, constructor, arg1, 0, 3);
8367 self.check_parameter_types_constructor("NewObject3", clazz, constructor, arg2, 1, 3);
8368 self.check_parameter_types_constructor("NewObject3", clazz, constructor, arg3, 2, 3);
8369 }
8370 self.jni::<extern "C" fn(JNIEnvVTable, jclass, jmethodID, ...) -> jobject>(28)(self.vtable, clazz, constructor, arg1, arg2, arg3)
8371 }
8372 }
8373
8374 ///
8375 /// Gets the class of an object instance.
8376 ///
8377 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetObjectClass>
8378 ///
8379 ///
8380 /// # Arguments
8381 /// * `obj` - reference to a object.
8382 /// * must not be null
8383 /// * must be valid
8384 /// * must not be already garbage collected
8385 ///
8386 /// # Returns
8387 /// A local reference to the class of the object.
8388 ///
8389 ///
8390 /// # Panics
8391 /// if asserts feature is enabled and UB was detected
8392 ///
8393 /// # Safety
8394 ///
8395 /// Current thread must not be detached from JNI.
8396 ///
8397 /// Current thread must not be currently throwing an exception.
8398 ///
8399 /// Current thread does not hold a critical reference.
8400 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8401 ///
8402 /// `obj` must not be null and be a valid reference that has not yet been deleted or garbage collected.
8403 ///
8404 pub unsafe fn GetObjectClass(&self, obj: jobject) -> jclass {
8405 unsafe {
8406 #[cfg(feature = "asserts")]
8407 {
8408 self.check_not_critical("GetObjectClass");
8409 self.check_no_exception("GetObjectClass");
8410 self.check_ref_obj("GetObjectClass", obj);
8411 }
8412 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jobject>(31)(self.vtable, obj)
8413 }
8414 }
8415
8416 ///
8417 /// Gets the type of reference
8418 ///
8419 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetObjectRefType>
8420 ///
8421 ///
8422 /// # Arguments
8423 /// * `obj` - reference to an object.
8424 /// * must be valid or null
8425 ///
8426 /// # Returns
8427 /// The type of reference
8428 /// `JNIInvalidRefType` is returned for null inputs.
8429 ///
8430 ///
8431 /// # Panics
8432 /// if asserts feature is enabled and UB was detected
8433 ///
8434 /// # Safety
8435 ///
8436 /// Current thread must not be detached from JNI.
8437 ///
8438 /// Current thread must not be currently throwing an exception.
8439 ///
8440 /// Current thread does not hold a critical reference.
8441 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8442 ///
8443 /// `obj` must be a valid reference.
8444 ///
8445 /// Calling this fn with an obj that has already been manually deleted using `DeleteLocalRef` for example is UB.
8446 ///
8447 pub unsafe fn GetObjectRefType(&self, obj: jobject) -> jobjectRefType {
8448 unsafe {
8449 #[cfg(feature = "asserts")]
8450 {
8451 self.check_not_critical("GetObjectRefType");
8452 self.check_no_exception("GetObjectRefType");
8453 }
8454 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jobjectRefType>(232)(self.vtable, obj)
8455 }
8456 }
8457
8458 ///
8459 /// Checks if the obj is instanceof the given class
8460 ///
8461 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#IsInstanceOf>
8462 ///
8463 ///
8464 /// # Arguments
8465 /// * `obj` - reference to an object.
8466 /// * must be valid or null
8467 /// * must not be already garbage collected
8468 /// * `clazz` - reference to the class.
8469 /// * must be a valid reference to a class
8470 /// * must not be null
8471 /// * must not be already garbage collected
8472 ///
8473 /// # Returns
8474 /// true if `obj` is instanceof `clazz`, false otherwise
8475 /// if `obj` is null then this fn returns false for any `clazz` input
8476 ///
8477 ///
8478 /// # Panics
8479 /// if asserts feature is enabled and UB was detected
8480 ///
8481 /// # Safety
8482 ///
8483 /// Current thread must not be detached from JNI.
8484 ///
8485 /// Current thread must not be currently throwing an exception.
8486 ///
8487 /// Current thread does not hold a critical reference.
8488 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8489 ///
8490 /// `obj` must be null or a valid reference that is not already garbage collected.
8491 /// `clazz` must be a valid non-null reference to a class that is not already garbage collected.
8492 ///
8493 pub unsafe fn IsInstanceOf(&self, obj: jobject, clazz: jclass) -> bool {
8494 unsafe {
8495 #[cfg(feature = "asserts")]
8496 {
8497 self.check_not_critical("IsInstanceOf");
8498 self.check_no_exception("IsInstanceOf");
8499 self.check_is_class("IsInstanceOf", clazz);
8500 self.check_ref_obj_permit_null("IsInstanceOf", obj);
8501 }
8502 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jclass) -> jboolean>(32)(self.vtable, obj, clazz).as_bool()
8503 }
8504 }
8505
8506 ///
8507 /// this is the java == operator on 2 java objects.
8508 /// The opaque handles of the 2 objects could be different but refer to the same underlying object.
8509 /// This fn exists in order to be able to check this.
8510 ///
8511 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#IsSameObject>
8512 ///
8513 ///
8514 /// # Arguments
8515 /// * `obj1` - reference to an object.
8516 /// * must be valid or null
8517 /// * must not be already garbage collected
8518 /// * `obj2` - reference to the class.
8519 /// * must be valid or null
8520 /// * must not be already garbage collected
8521 ///
8522 /// # Returns
8523 /// true if `obj1` == `obj2`, false otherwise
8524 ///
8525 ///
8526 ///
8527 /// # Panics
8528 /// if asserts feature is enabled and UB was detected
8529 ///
8530 /// # Safety
8531 ///
8532 /// Current thread must not be detached from JNI.
8533 ///
8534 /// Current thread must not be currently throwing an exception.
8535 ///
8536 /// Current thread does not hold a critical reference.
8537 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8538 ///
8539 /// `obj1` must be null or a valid reference that is not already garbage collected.
8540 /// `obj2` must be null or a valid reference that is not already garbage collected.
8541 ///
8542 pub unsafe fn IsSameObject(&self, obj1: jobject, obj2: jobject) -> bool {
8543 unsafe {
8544 #[cfg(feature = "asserts")]
8545 {
8546 self.check_not_critical("IsSameObject");
8547 self.check_no_exception("IsSameObject");
8548 self.check_ref_obj_permit_null("IsSameObject obj1", obj1);
8549 self.check_ref_obj_permit_null("IsSameObject obj2", obj2);
8550 }
8551 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jobject) -> jboolean>(24)(self.vtable, obj1, obj2).as_bool()
8552 }
8553 }
8554
8555 ///
8556 /// Gets the field id of a non-static field
8557 ///
8558 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetFieldID>
8559 ///
8560 ///
8561 /// # Arguments
8562 /// * `clazz` - reference to the clazz where the field is declared in.
8563 /// * must be valid
8564 /// * must not be null
8565 /// * must not be already garbage collected
8566 /// * `name` - name of the field
8567 /// * must not be null
8568 /// * must be zero terminated utf-8
8569 /// * `sig` - jni signature of the field
8570 /// * must not be null
8571 /// * must be zero terminated utf-8
8572 ///
8573 /// # Returns
8574 /// A non-null field handle or null on error.
8575 /// The field handle can be assumed to be constant for the given class and must not be freed.
8576 /// It can also be safely shared with any thread or stored in a constant.
8577 ///
8578 /// # Throws Java Exception
8579 /// * `NoSuchFieldError` - field with the given name and sig doesnt exist in the class
8580 /// * `ExceptionInInitializerError` - Exception occurs in initializer of the class
8581 /// * `OutOfMemoryError` - if the jvm runs out of memory
8582 ///
8583 ///
8584 /// # Panics
8585 /// if asserts feature is enabled and UB was detected
8586 ///
8587 /// # Safety
8588 ///
8589 /// Current thread must not be detached from JNI.
8590 ///
8591 /// Current thread must not be currently throwing an exception.
8592 ///
8593 /// Current thread does not hold a critical reference.
8594 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8595 ///
8596 /// `clazz` must a valid reference to a class that is not already garbage collected.
8597 /// `name` must be non-null and zero terminated utf-8.
8598 /// `sig` must be non-null and zero terminated utf-8.
8599 ///
8600 pub unsafe fn GetFieldID(&self, clazz: jclass, name: impl UseCString, sig: impl UseCString) -> jfieldID {
8601 unsafe {
8602 name.use_as_const_c_char(|name| {
8603 sig.use_as_const_c_char(|sig| {
8604 #[cfg(feature = "asserts")]
8605 {
8606 self.check_not_critical("GetFieldID");
8607 self.check_no_exception("GetFieldID");
8608 assert!(!name.is_null(), "GetFieldID name is null");
8609 assert!(!sig.is_null(), "GetFieldID sig is null");
8610 self.check_is_class("GetFieldID", clazz);
8611 }
8612 self.jni::<extern "system" fn(JNIEnvVTable, jclass, *const c_char, *const c_char) -> jfieldID>(94)(self.vtable, clazz, name, sig)
8613 })
8614 })
8615 }
8616 }
8617
8618 ///
8619 /// Returns a local reference from a field in an object.
8620 ///
8621 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_type_Field_routines>
8622 ///
8623 ///
8624 /// # Arguments
8625 /// * `obj` - reference to the object the field is in
8626 /// * must be valid
8627 /// * must not be null
8628 /// * must not be already garbage collected
8629 /// * `fieldID` - the field to get
8630 /// * must be valid
8631 /// * must be a object field
8632 ///
8633 /// # Returns
8634 /// A local reference to the fields value or null if the field is null
8635 ///
8636 ///
8637 /// # Panics
8638 /// if asserts feature is enabled and UB was detected
8639 ///
8640 /// # Safety
8641 ///
8642 /// Current thread must not be detached from JNI.
8643 ///
8644 /// Current thread must not be currently throwing an exception.
8645 ///
8646 /// Current thread does not hold a critical reference.
8647 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8648 ///
8649 /// `obj` must a valid reference to the object that is not already garbage collected.
8650 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
8651 /// `fieldID` must not be from a static field
8652 /// `fieldID` must refer to a field that is an object and not a primitive.
8653 ///
8654 pub unsafe fn GetObjectField(&self, obj: jobject, fieldID: jfieldID) -> jobject {
8655 unsafe {
8656 #[cfg(feature = "asserts")]
8657 {
8658 self.check_not_critical("GetObjectField");
8659 self.check_no_exception("GetObjectField");
8660 self.check_field_type_object("GetObjectField", obj, fieldID, "object");
8661 }
8662 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jobject>(95)(self.vtable, obj, fieldID)
8663 }
8664 }
8665
8666 ///
8667 /// Returns a boolean field value
8668 ///
8669 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_type_Field_routines>
8670 ///
8671 ///
8672 /// # Arguments
8673 /// * `obj` - reference to the object the field is in
8674 /// * must be valid
8675 /// * must not be null
8676 /// * must not be already garbage collected
8677 /// * `fieldID` - the field to get
8678 /// * must be valid
8679 /// * must be a boolean field
8680 ///
8681 /// # Returns
8682 /// The boolean field value
8683 ///
8684 ///
8685 /// # Panics
8686 /// if asserts feature is enabled and UB was detected
8687 ///
8688 /// # Safety
8689 ///
8690 /// Current thread must not be detached from JNI.
8691 ///
8692 /// Current thread must not be currently throwing an exception.
8693 ///
8694 /// Current thread does not hold a critical reference.
8695 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8696 ///
8697 /// `obj` must a valid reference to the object that is not already garbage collected.
8698 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
8699 /// `fieldID` must not be from a static field
8700 /// `fieldID` must refer to a field that is a boolean and not something else.
8701 ///
8702 pub unsafe fn GetBooleanField(&self, obj: jobject, fieldID: jfieldID) -> bool {
8703 unsafe {
8704 #[cfg(feature = "asserts")]
8705 {
8706 self.check_not_critical("GetBooleanField");
8707 self.check_no_exception("GetBooleanField");
8708 self.check_field_type_object("GetBooleanField", obj, fieldID, "boolean");
8709 }
8710 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jboolean>(96)(self.vtable, obj, fieldID).as_bool()
8711 }
8712 }
8713
8714 ///
8715 /// Returns a byte field value
8716 ///
8717 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_type_Field_routines>
8718 ///
8719 ///
8720 /// # Arguments
8721 /// * `obj` - reference to the object the field is in
8722 /// * must be valid
8723 /// * must not be null
8724 /// * must not be already garbage collected
8725 /// * `fieldID` - the field to get
8726 /// * must be valid
8727 /// * must be a byte field
8728 ///
8729 /// # Returns
8730 /// The byte field value
8731 ///
8732 ///
8733 /// # Panics
8734 /// if asserts feature is enabled and UB was detected
8735 ///
8736 /// # Safety
8737 ///
8738 /// Current thread must not be detached from JNI.
8739 ///
8740 /// Current thread must not be currently throwing an exception.
8741 ///
8742 /// Current thread does not hold a critical reference.
8743 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8744 ///
8745 /// `obj` must a valid reference to the object that is not already garbage collected.
8746 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
8747 /// `fieldID` must not be from a static field
8748 /// `fieldID` must refer to a field that is a byte and not something else.
8749 ///
8750 pub unsafe fn GetByteField(&self, obj: jobject, fieldID: jfieldID) -> jbyte {
8751 unsafe {
8752 #[cfg(feature = "asserts")]
8753 {
8754 self.check_not_critical("GetByteField");
8755 self.check_no_exception("GetByteField");
8756 self.check_field_type_object("GetByteField", obj, fieldID, "byte");
8757 }
8758 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jbyte>(97)(self.vtable, obj, fieldID)
8759 }
8760 }
8761
8762 ///
8763 /// Returns a char field value
8764 ///
8765 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_type_Field_routines>
8766 ///
8767 ///
8768 /// # Arguments
8769 /// * `obj` - reference to the object the field is in
8770 /// * must be valid
8771 /// * must not be null
8772 /// * must not be already garbage collected
8773 /// * `fieldID` - the field to get
8774 /// * must be valid
8775 /// * must be a char field
8776 ///
8777 /// # Returns
8778 /// The char field value
8779 ///
8780 ///
8781 /// # Panics
8782 /// if asserts feature is enabled and UB was detected
8783 ///
8784 /// # Safety
8785 ///
8786 /// Current thread must not be detached from JNI.
8787 ///
8788 /// Current thread must not be currently throwing an exception.
8789 ///
8790 /// Current thread does not hold a critical reference.
8791 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8792 ///
8793 /// `obj` must a valid reference to the object that is not already garbage collected.
8794 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
8795 /// `fieldID` must not be from a static field
8796 /// `fieldID` must refer to a field that is a char and not something else.
8797 ///
8798 pub unsafe fn GetCharField(&self, obj: jobject, fieldID: jfieldID) -> jchar {
8799 unsafe {
8800 #[cfg(feature = "asserts")]
8801 {
8802 self.check_not_critical("GetCharField");
8803 self.check_no_exception("GetCharField");
8804 self.check_field_type_object("GetCharField", obj, fieldID, "char");
8805 }
8806 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jchar>(98)(self.vtable, obj, fieldID)
8807 }
8808 }
8809
8810 ///
8811 /// Returns a short field value
8812 ///
8813 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_type_Field_routines>
8814 ///
8815 ///
8816 /// # Arguments
8817 /// * `obj` - reference to the object the field is in
8818 /// * must be valid
8819 /// * must not be null
8820 /// * must not be already garbage collected
8821 /// * `fieldID` - the field to get
8822 /// * must be valid
8823 /// * must be a short field
8824 ///
8825 /// # Returns
8826 /// The short field value
8827 ///
8828 ///
8829 /// # Panics
8830 /// if asserts feature is enabled and UB was detected
8831 ///
8832 /// # Safety
8833 ///
8834 /// Current thread must not be detached from JNI.
8835 ///
8836 /// Current thread must not be currently throwing an exception.
8837 ///
8838 /// Current thread does not hold a critical reference.
8839 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8840 ///
8841 /// `obj` must a valid reference to the object that is not already garbage collected.
8842 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
8843 /// `fieldID` must not be from a static field
8844 /// `fieldID` must refer to a field that is a short and not something else.
8845 ///
8846 pub unsafe fn GetShortField(&self, obj: jobject, fieldID: jfieldID) -> jshort {
8847 unsafe {
8848 #[cfg(feature = "asserts")]
8849 {
8850 self.check_not_critical("GetShortField");
8851 self.check_no_exception("GetShortField");
8852 self.check_field_type_object("GetShortField", obj, fieldID, "short");
8853 }
8854 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jshort>(99)(self.vtable, obj, fieldID)
8855 }
8856 }
8857
8858 ///
8859 /// Returns a int field value
8860 ///
8861 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_type_Field_routines>
8862 ///
8863 ///
8864 /// # Arguments
8865 /// * `obj` - reference to the object the field is in
8866 /// * must be valid
8867 /// * must not be null
8868 /// * must not be already garbage collected
8869 /// * `fieldID` - the field to get
8870 /// * must be valid
8871 /// * must be a int field
8872 ///
8873 /// # Returns
8874 /// The int field value
8875 ///
8876 ///
8877 /// # Panics
8878 /// if asserts feature is enabled and UB was detected
8879 ///
8880 /// # Safety
8881 ///
8882 /// Current thread must not be detached from JNI.
8883 ///
8884 /// Current thread must not be currently throwing an exception.
8885 ///
8886 /// Current thread does not hold a critical reference.
8887 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8888 ///
8889 /// `obj` must a valid reference to the object that is not already garbage collected.
8890 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
8891 /// `fieldID` must not be from a static field
8892 /// `fieldID` must refer to a field that is a int and not something else.
8893 ///
8894 pub unsafe fn GetIntField(&self, obj: jobject, fieldID: jfieldID) -> jint {
8895 unsafe {
8896 #[cfg(feature = "asserts")]
8897 {
8898 self.check_not_critical("GetIntField");
8899 self.check_no_exception("GetIntField");
8900 self.check_field_type_object("GetIntField", obj, fieldID, "int");
8901 }
8902 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jint>(100)(self.vtable, obj, fieldID)
8903 }
8904 }
8905
8906 ///
8907 /// Returns a int field value
8908 ///
8909 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_type_Field_routines>
8910 ///
8911 ///
8912 /// # Arguments
8913 /// * `obj` - reference to the object the field is in
8914 /// * must be valid
8915 /// * must not be null
8916 /// * must not be already garbage collected
8917 /// * `fieldID` - the field to get
8918 /// * must be valid
8919 /// * must be a long field
8920 ///
8921 /// # Returns
8922 /// The long field value
8923 ///
8924 ///
8925 /// # Panics
8926 /// if asserts feature is enabled and UB was detected
8927 ///
8928 /// # Safety
8929 ///
8930 /// Current thread must not be detached from JNI.
8931 ///
8932 /// Current thread must not be currently throwing an exception.
8933 ///
8934 /// Current thread does not hold a critical reference.
8935 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8936 ///
8937 /// `obj` must a valid reference to the object that is not already garbage collected.
8938 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
8939 /// `fieldID` must not be from a static field
8940 /// `fieldID` must refer to a field that is a long and not something else.
8941 ///
8942 pub unsafe fn GetLongField(&self, obj: jobject, fieldID: jfieldID) -> jlong {
8943 unsafe {
8944 #[cfg(feature = "asserts")]
8945 {
8946 self.check_not_critical("GetLongField");
8947 self.check_no_exception("GetLongField");
8948 self.check_field_type_object("GetLongField", obj, fieldID, "long");
8949 }
8950 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jlong>(101)(self.vtable, obj, fieldID)
8951 }
8952 }
8953
8954 ///
8955 /// Returns a float field value
8956 ///
8957 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_type_Field_routines>
8958 ///
8959 ///
8960 /// # Arguments
8961 /// * `obj` - reference to the object the field is in
8962 /// * must be valid
8963 /// * must not be null
8964 /// * must not be already garbage collected
8965 /// * `fieldID` - the field to get
8966 /// * must be valid
8967 /// * must be a long field
8968 ///
8969 /// # Returns
8970 /// The float field value
8971 ///
8972 ///
8973 /// # Panics
8974 /// if asserts feature is enabled and UB was detected
8975 ///
8976 /// # Safety
8977 ///
8978 /// Current thread must not be detached from JNI.
8979 ///
8980 /// Current thread must not be currently throwing an exception.
8981 ///
8982 /// Current thread does not hold a critical reference.
8983 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
8984 ///
8985 /// `obj` must a valid reference to the object that is not already garbage collected.
8986 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
8987 /// `fieldID` must not be from a static field
8988 /// `fieldID` must refer to a field that is a float and not something else.
8989 ///
8990 pub unsafe fn GetFloatField(&self, obj: jobject, fieldID: jfieldID) -> jfloat {
8991 unsafe {
8992 #[cfg(feature = "asserts")]
8993 {
8994 self.check_not_critical("GetFloatField");
8995 self.check_no_exception("GetFloatField");
8996 self.check_field_type_object("GetFloatField", obj, fieldID, "float");
8997 }
8998 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jfloat>(102)(self.vtable, obj, fieldID)
8999 }
9000 }
9001
9002 ///
9003 /// Returns a double field value
9004 ///
9005 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_type_Field_routines>
9006 ///
9007 ///
9008 /// # Arguments
9009 /// * `obj` - reference to the object the field is in
9010 /// * must be valid
9011 /// * must not be null
9012 /// * must not be already garbage collected
9013 /// * `fieldID` - the field to get
9014 /// * must be valid
9015 /// * must be a double field
9016 ///
9017 /// # Returns
9018 /// The double field value
9019 ///
9020 ///
9021 /// # Panics
9022 /// if asserts feature is enabled and UB was detected
9023 ///
9024 /// # Safety
9025 ///
9026 /// Current thread must not be detached from JNI.
9027 ///
9028 /// Current thread must not be currently throwing an exception.
9029 ///
9030 /// Current thread does not hold a critical reference.
9031 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9032 ///
9033 /// `obj` must a valid reference to the object that is not already garbage collected.
9034 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
9035 /// `fieldID` must not be from a static field
9036 /// `fieldID` must refer to a field that is a double and not something else.
9037 ///
9038 pub unsafe fn GetDoubleField(&self, obj: jobject, fieldID: jfieldID) -> jdouble {
9039 unsafe {
9040 #[cfg(feature = "asserts")]
9041 {
9042 self.check_not_critical("GetDoubleField");
9043 self.check_no_exception("GetDoubleField");
9044 self.check_field_type_object("GetDoubleField", obj, fieldID, "double");
9045 }
9046 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jdouble>(103)(self.vtable, obj, fieldID)
9047 }
9048 }
9049
9050 ///
9051 /// Sets a object field to a given value
9052 ///
9053 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_type_Field_routines>
9054 ///
9055 /// # Arguments
9056 /// * `obj` - reference to the object the field is in
9057 /// * must be valid
9058 /// * must not be null
9059 /// * must not be already garbage collected
9060 ///
9061 /// * `fieldID` - the field to set
9062 /// * must be valid
9063 /// * must be a object field
9064 /// * must reside in the object `obj`
9065 ///
9066 /// * `value`
9067 /// * must be null or valid
9068 /// * must not be already garbage collected (if non-null)
9069 /// * must be assignable to the field type (if non-null)
9070 ///
9071 ///
9072 /// # Panics
9073 /// if asserts feature is enabled and UB was detected
9074 ///
9075 /// # Safety
9076 ///
9077 /// Current thread must not be detached from JNI.
9078 ///
9079 /// Current thread must not be currently throwing an exception.
9080 ///
9081 /// Current thread does not hold a critical reference.
9082 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9083 ///
9084 /// `obj` must be a valid reference to the object that is not already garbage collected.
9085 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
9086 /// `fieldID` must not be from a static field
9087 /// `fieldID` must refer to a field that is an object and not a primitive.
9088 /// `value` must be a valid reference to the object that is not already garbage collected or it must be null.
9089 /// `value` must be assignable to the field type (i.e. if it's a String field setting to an `ArrayList` for example is UB)
9090 ///
9091 pub unsafe fn SetObjectField(&self, obj: jobject, fieldID: jfieldID, value: jobject) {
9092 unsafe {
9093 #[cfg(feature = "asserts")]
9094 {
9095 self.check_not_critical("SetObjectField");
9096 self.check_no_exception("SetObjectField");
9097 self.check_field_type_object("SetObjectField", obj, fieldID, "object");
9098 self.check_ref_obj_permit_null("SetObjectField", value);
9099 }
9100 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jobject)>(104)(self.vtable, obj, fieldID, value);
9101 }
9102 }
9103
9104 ///
9105 /// Sets a boolean field to a given value
9106 ///
9107 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_type_Field_routines>
9108 ///
9109 /// # Arguments
9110 /// * `obj` - reference to the object the field is in
9111 /// * must be valid
9112 /// * must not be null
9113 /// * must not be already garbage collected
9114 ///
9115 /// * `fieldID` - the field to set
9116 /// * must be valid
9117 /// * must be a object field
9118 /// * must reside in the object `obj`
9119 ///
9120 /// * `value` - the value to set
9121 ///
9122 ///
9123 /// # Panics
9124 /// if asserts feature is enabled and UB was detected
9125 ///
9126 /// # Safety
9127 ///
9128 /// Current thread must not be detached from JNI.
9129 ///
9130 /// Current thread must not be currently throwing an exception.
9131 ///
9132 /// Current thread does not hold a critical reference.
9133 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9134 ///
9135 /// `obj` must be a valid reference to the object that is not already garbage collected.
9136 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
9137 /// `fieldID` must not be from a static field
9138 /// `fieldID` must refer to a field that is a boolean.
9139 ///
9140 pub unsafe fn SetBooleanField(&self, obj: jobject, fieldID: jfieldID, value: impl Into<jboolean>) {
9141 let value = value.into();
9142 unsafe {
9143 #[cfg(feature = "asserts")]
9144 {
9145 self.check_not_critical("SetBooleanField");
9146 self.check_no_exception("SetBooleanField");
9147 self.check_field_type_object("SetBooleanField", obj, fieldID, "boolean");
9148 assert!(!value.is_wide(), "SetBooleanField with wide boolean value");
9149 }
9150 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jboolean)>(105)(self.vtable, obj, fieldID, value);
9151 }
9152 }
9153
9154 ///
9155 /// Sets a byte field to a given value
9156 ///
9157 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_type_Field_routines>
9158 ///
9159 /// # Arguments
9160 /// * `obj` - reference to the object the field is in
9161 /// * must be valid
9162 /// * must not be null
9163 /// * must not be already garbage collected
9164 ///
9165 /// * `fieldID` - the field to set
9166 /// * must be valid
9167 /// * must be a object field
9168 /// * must reside in the object `obj`
9169 ///
9170 /// * `value` - the value to set
9171 ///
9172 ///
9173 /// # Panics
9174 /// if asserts feature is enabled and UB was detected
9175 ///
9176 /// # Safety
9177 ///
9178 /// Current thread must not be detached from JNI.
9179 ///
9180 /// Current thread must not be currently throwing an exception.
9181 ///
9182 /// Current thread does not hold a critical reference.
9183 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9184 ///
9185 /// `obj` must be a valid reference to the object that is not already garbage collected.
9186 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
9187 /// `fieldID` must not be from a static field
9188 /// `fieldID` must refer to a field that is a byte.
9189 ///
9190 pub unsafe fn SetByteField(&self, obj: jobject, fieldID: jfieldID, value: jbyte) {
9191 unsafe {
9192 #[cfg(feature = "asserts")]
9193 {
9194 self.check_not_critical("SetByteField");
9195 self.check_no_exception("SetByteField");
9196 self.check_field_type_object("SetByteField", obj, fieldID, "byte");
9197 }
9198 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jbyte)>(106)(self.vtable, obj, fieldID, value);
9199 }
9200 }
9201
9202 ///
9203 /// Sets a char field to a given value
9204 ///
9205 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_type_Field_routines>
9206 ///
9207 /// # Arguments
9208 /// * `obj` - reference to the object the field is in
9209 /// * must be valid
9210 /// * must not be null
9211 /// * must not be already garbage collected
9212 ///
9213 /// * `fieldID` - the field to set
9214 /// * must be valid
9215 /// * must be a object field
9216 /// * must reside in the object `obj`
9217 ///
9218 /// * `value` - the value to set
9219 ///
9220 ///
9221 /// # Panics
9222 /// if asserts feature is enabled and UB was detected
9223 ///
9224 /// # Safety
9225 ///
9226 /// Current thread must not be detached from JNI.
9227 ///
9228 /// Current thread must not be currently throwing an exception.
9229 ///
9230 /// Current thread does not hold a critical reference.
9231 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9232 ///
9233 /// `obj` must be a valid reference to the object that is not already garbage collected.
9234 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
9235 /// `fieldID` must not be from a static field
9236 /// `fieldID` must refer to a field that is a char.
9237 ///
9238 pub unsafe fn SetCharField(&self, obj: jobject, fieldID: jfieldID, value: jchar) {
9239 unsafe {
9240 #[cfg(feature = "asserts")]
9241 {
9242 self.check_not_critical("SetCharField");
9243 self.check_no_exception("SetCharField");
9244 self.check_field_type_object("SetCharField", obj, fieldID, "char");
9245 }
9246 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jchar)>(107)(self.vtable, obj, fieldID, value);
9247 }
9248 }
9249
9250 ///
9251 /// Sets a short field to a given value
9252 ///
9253 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_type_Field_routines>
9254 ///
9255 /// # Arguments
9256 /// * `obj` - reference to the object the field is in
9257 /// * must be valid
9258 /// * must not be null
9259 /// * must not be already garbage collected
9260 ///
9261 /// * `fieldID` - the field to set
9262 /// * must be valid
9263 /// * must be a object field
9264 /// * must reside in the object `obj`
9265 ///
9266 /// * `value` - the value to set
9267 ///
9268 ///
9269 /// # Panics
9270 /// if asserts feature is enabled and UB was detected
9271 ///
9272 /// # Safety
9273 ///
9274 /// Current thread must not be detached from JNI.
9275 ///
9276 /// Current thread must not be currently throwing an exception.
9277 ///
9278 /// Current thread does not hold a critical reference.
9279 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9280 ///
9281 /// `obj` must be a valid reference to the object that is not already garbage collected.
9282 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
9283 /// `fieldID` must not be from a static field
9284 /// `fieldID` must refer to a field that is a short.
9285 ///
9286 pub unsafe fn SetShortField(&self, obj: jobject, fieldID: jfieldID, value: jshort) {
9287 unsafe {
9288 #[cfg(feature = "asserts")]
9289 {
9290 self.check_not_critical("SetShortField");
9291 self.check_no_exception("SetShortField");
9292 self.check_field_type_object("SetShortField", obj, fieldID, "short");
9293 }
9294 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jshort)>(108)(self.vtable, obj, fieldID, value);
9295 }
9296 }
9297
9298 ///
9299 /// Sets a int field to a given value
9300 ///
9301 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_type_Field_routines>
9302 ///
9303 /// # Arguments
9304 /// * `obj` - reference to the object the field is in
9305 /// * must be valid
9306 /// * must not be null
9307 /// * must not be already garbage collected
9308 ///
9309 /// * `fieldID` - the field to set
9310 /// * must be valid
9311 /// * must be a object field
9312 /// * must reside in the object `obj`
9313 ///
9314 /// * `value` - the value to set
9315 ///
9316 ///
9317 /// # Panics
9318 /// if asserts feature is enabled and UB was detected
9319 ///
9320 /// # Safety
9321 ///
9322 /// Current thread must not be detached from JNI.
9323 ///
9324 /// Current thread must not be currently throwing an exception.
9325 ///
9326 /// Current thread does not hold a critical reference.
9327 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9328 ///
9329 /// `obj` must be a valid reference to the object that is not already garbage collected.
9330 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
9331 /// `fieldID` must not be from a static field
9332 /// `fieldID` must refer to a field that is a int.
9333 ///
9334 pub unsafe fn SetIntField(&self, obj: jobject, fieldID: jfieldID, value: jint) {
9335 unsafe {
9336 #[cfg(feature = "asserts")]
9337 {
9338 self.check_not_critical("SetIntField");
9339 self.check_no_exception("SetIntField");
9340 self.check_field_type_object("SetIntField", obj, fieldID, "int");
9341 }
9342 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jint)>(109)(self.vtable, obj, fieldID, value);
9343 }
9344 }
9345
9346 ///
9347 /// Sets a long field to a given value
9348 ///
9349 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_type_Field_routines>
9350 ///
9351 /// # Arguments
9352 /// * `obj` - reference to the object the field is in
9353 /// * must be valid
9354 /// * must not be null
9355 /// * must not be already garbage collected
9356 ///
9357 /// * `fieldID` - the field to set
9358 /// * must be valid
9359 /// * must be a object field
9360 /// * must reside in the object `obj`
9361 ///
9362 /// * `value` - the value to set
9363 ///
9364 ///
9365 /// # Panics
9366 /// if asserts feature is enabled and UB was detected
9367 ///
9368 /// # Safety
9369 ///
9370 /// Current thread must not be detached from JNI.
9371 ///
9372 /// Current thread must not be currently throwing an exception.
9373 ///
9374 /// Current thread does not hold a critical reference.
9375 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9376 ///
9377 /// `obj` must be a valid reference to the object that is not already garbage collected.
9378 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
9379 /// `fieldID` must not be from a static field
9380 /// `fieldID` must refer to a field that is a long.
9381 ///
9382 pub unsafe fn SetLongField(&self, obj: jobject, fieldID: jfieldID, value: jlong) {
9383 unsafe {
9384 #[cfg(feature = "asserts")]
9385 {
9386 self.check_not_critical("SetLongField");
9387 self.check_no_exception("SetLongField");
9388 self.check_field_type_object("SetLongField", obj, fieldID, "long");
9389 }
9390 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jlong)>(110)(self.vtable, obj, fieldID, value);
9391 }
9392 }
9393
9394 ///
9395 /// Sets a float field to a given value
9396 ///
9397 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_type_Field_routines>
9398 ///
9399 /// # Arguments
9400 /// * `obj` - reference to the object the field is in
9401 /// * must be valid
9402 /// * must not be null
9403 /// * must not be already garbage collected
9404 ///
9405 /// * `fieldID` - the field to set
9406 /// * must be valid
9407 /// * must be a object field
9408 /// * must reside in the object `obj`
9409 ///
9410 /// * `value` - the value to set
9411 ///
9412 ///
9413 /// # Panics
9414 /// if asserts feature is enabled and UB was detected
9415 ///
9416 /// # Safety
9417 ///
9418 /// Current thread must not be detached from JNI.
9419 ///
9420 /// Current thread must not be currently throwing an exception.
9421 ///
9422 /// Current thread does not hold a critical reference.
9423 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9424 ///
9425 /// `obj` must be a valid reference to the object that is not already garbage collected.
9426 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
9427 /// `fieldID` must not be from a static field
9428 /// `fieldID` must refer to a field that is a float.
9429 ///
9430 pub unsafe fn SetFloatField(&self, obj: jobject, fieldID: jfieldID, value: jfloat) {
9431 unsafe {
9432 #[cfg(feature = "asserts")]
9433 {
9434 self.check_not_critical("SetFloatField");
9435 self.check_no_exception("SetFloatField");
9436 self.check_field_type_object("SetFloatField", obj, fieldID, "float");
9437 }
9438 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jfloat)>(111)(self.vtable, obj, fieldID, value);
9439 }
9440 }
9441
9442 ///
9443 /// Sets a double field to a given value
9444 ///
9445 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_type_Field_routines>
9446 ///
9447 /// # Arguments
9448 /// * `obj` - reference to the object the field is in
9449 /// * must be valid
9450 /// * must not be null
9451 /// * must not be already garbage collected
9452 ///
9453 /// * `fieldID` - the field to set
9454 /// * must be valid
9455 /// * must be a object field
9456 /// * must reside in the object `obj`
9457 ///
9458 /// * `value` - the value to set
9459 ///
9460 ///
9461 /// # Panics
9462 /// if asserts feature is enabled and UB was detected
9463 ///
9464 /// # Safety
9465 ///
9466 /// Current thread must not be detached from JNI.
9467 ///
9468 /// Current thread must not be currently throwing an exception.
9469 ///
9470 /// Current thread does not hold a critical reference.
9471 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9472 ///
9473 /// `obj` must be a valid reference to the object that is not already garbage collected.
9474 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
9475 /// `fieldID` must not be from a static field
9476 /// `fieldID` must refer to a field that is a double.
9477 ///
9478 pub unsafe fn SetDoubleField(&self, obj: jobject, fieldID: jfieldID, value: jdouble) {
9479 unsafe {
9480 #[cfg(feature = "asserts")]
9481 {
9482 self.check_not_critical("SetDoubleField");
9483 self.check_no_exception("SetDoubleField");
9484 self.check_field_type_object("SetDoubleField", obj, fieldID, "double");
9485 }
9486 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jdouble)>(112)(self.vtable, obj, fieldID, value);
9487 }
9488 }
9489
9490 ///
9491 /// Gets the method id of a non-static method
9492 ///
9493 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetMethodID>
9494 ///
9495 ///
9496 /// # Arguments
9497 /// * `clazz` - reference to the clazz where the field is declared in.
9498 /// * must be valid
9499 /// * must not be null
9500 /// * must not be already garbage collected
9501 /// * `name` - name of the method
9502 /// * must not be null
9503 /// * must be zero terminated utf-8
9504 /// * `sig` - jni signature of the method
9505 /// * must not be null
9506 /// * must be zero terminated utf-8
9507 ///
9508 /// # Returns
9509 /// A non-null field handle or null on error.
9510 /// The field handle can be assumed to be constant for the given class and must not be freed.
9511 /// It can also be safely shared with any thread or stored in a constant.
9512 ///
9513 /// # Throws Java Exception
9514 /// * `NoSuchMethodError` - method with the given name and sig doesn't exist in the class
9515 /// * `ExceptionInInitializerError` - Exception occurs in initializer of the class
9516 /// * `OutOfMemoryError` - if the jvm runs out of memory
9517 ///
9518 ///
9519 /// # Panics
9520 /// if asserts feature is enabled and UB was detected
9521 ///
9522 /// # Safety
9523 ///
9524 /// Current thread must not be detached from JNI.
9525 ///
9526 /// Current thread must not be currently throwing an exception.
9527 ///
9528 /// Current thread does not hold a critical reference.
9529 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9530 ///
9531 /// `clazz` must a valid reference to a class that is not already garbage collected.
9532 /// `name` must be non-null and zero terminated utf-8.
9533 /// `sig` must be non-null and zero terminated utf-8.
9534 ///
9535 pub unsafe fn GetMethodID(&self, class: jclass, name: impl UseCString, sig: impl UseCString) -> jmethodID {
9536 unsafe {
9537 name.use_as_const_c_char(|name| {
9538 sig.use_as_const_c_char(|sig| {
9539 #[cfg(feature = "asserts")]
9540 {
9541 self.check_not_critical("GetMethodID");
9542 self.check_no_exception("GetMethodID");
9543 assert!(!name.is_null(), "GetMethodID name is null");
9544 assert!(!sig.is_null(), "GetMethodID sig is null");
9545 self.check_is_class("GetMethodID", class);
9546 }
9547 self.jni::<extern "system" fn(JNIEnvVTable, jobject, *const c_char, *const c_char) -> jmethodID>(33)(self.vtable, class, name, sig)
9548 })
9549 })
9550 }
9551 }
9552
9553 ///
9554 /// Calls a non-static java method that returns void
9555 ///
9556 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
9557 ///
9558 ///
9559 /// # Arguments
9560 /// * `obj` - which object the method should be called on
9561 /// * must be valid
9562 /// * must not be null
9563 /// * must not be already garbage collected
9564 ///
9565 /// * `methodID` - method id of the method
9566 /// * must not be null
9567 /// * must be valid
9568 /// * must not be a static
9569 /// * must actually be a method of `obj`
9570 ///
9571 /// * `args` - argument pointer
9572 /// * can be null if the method has no arguments
9573 /// * must not be null otherwise and point to the exact number of arguments the method expects
9574 ///
9575 /// # Throws Java Exception
9576 /// * Whatever the method threw
9577 ///
9578 ///
9579 /// # Panics
9580 /// if asserts feature is enabled and UB was detected
9581 ///
9582 /// # Safety
9583 ///
9584 /// Current thread must not be detached from JNI.
9585 ///
9586 /// Current thread must not be currently throwing an exception.
9587 ///
9588 /// Current thread does not hold a critical reference.
9589 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9590 ///
9591 /// `obj` must a valid and not already garbage collected.
9592 /// `methodID` must be valid, non-static and actually be a method of `obj` and return void
9593 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
9594 /// `args` union must contain types that match the java methods parameters.
9595 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
9596 ///
9597 pub unsafe fn CallVoidMethodA(&self, obj: jobject, methodID: jmethodID, args: *const jtype) {
9598 unsafe {
9599 #[cfg(feature = "asserts")]
9600 {
9601 self.check_not_critical("CallVoidMethodA");
9602 self.check_no_exception("CallVoidMethodA");
9603 self.check_return_type_object("CallVoidMethodA", obj, methodID, "void");
9604 }
9605 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype)>(63)(self.vtable, obj, methodID, args);
9606 }
9607 }
9608
9609 ///
9610 /// Calls a non-static java method that has 0 arguments and returns void
9611 ///
9612 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
9613 ///
9614 ///
9615 /// # Arguments
9616 /// * `obj` - which object the method should be called on
9617 /// * must be valid
9618 /// * must not be null
9619 /// * must not be already garbage collected
9620 ///
9621 /// * `methodID` - method id of the method
9622 /// * must not be null
9623 /// * must be valid
9624 /// * must not be a static
9625 /// * must actually be a method of `obj`
9626 /// * must refer to a method with 0 arguments
9627 ///
9628 /// # Throws Java Exception
9629 /// * Whatever the method threw
9630 ///
9631 ///
9632 /// # Panics
9633 /// if asserts feature is enabled and UB was detected
9634 ///
9635 /// # Safety
9636 ///
9637 /// Current thread must not be detached from JNI.
9638 ///
9639 /// Current thread must not be currently throwing an exception.
9640 ///
9641 /// Current thread does not hold a critical reference.
9642 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9643 ///
9644 /// `obj` must a valid and not already garbage collected.
9645 /// `methodID` must be valid, non-static and actually be a method of `obj`, return void and have no parameters
9646 ///
9647 pub unsafe fn CallVoidMethod0(&self, obj: jobject, methodID: jmethodID) {
9648 unsafe {
9649 #[cfg(feature = "asserts")]
9650 {
9651 self.check_not_critical("CallVoidMethod");
9652 self.check_no_exception("CallVoidMethod");
9653 self.check_return_type_object("CallVoidMethod", obj, methodID, "void");
9654 }
9655 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID)>(61)(self.vtable, obj, methodID);
9656 }
9657 }
9658
9659 ///
9660 /// Calls a non-static java method that has 1 arguments and returns void
9661 ///
9662 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
9663 ///
9664 ///
9665 /// # Arguments
9666 /// * `obj` - which object the method should be called on
9667 /// * must be valid
9668 /// * must not be null
9669 /// * must not be already garbage collected
9670 ///
9671 /// * `methodID` - method id of the method
9672 /// * must not be null
9673 /// * must be valid
9674 /// * must not be a static
9675 /// * must actually be a method of `obj`
9676 /// * must refer to a method with 1 arguments
9677 ///
9678 /// # Throws Java Exception
9679 /// * Whatever the method threw
9680 ///
9681 ///
9682 /// # Panics
9683 /// if asserts feature is enabled and UB was detected
9684 ///
9685 /// # Safety
9686 ///
9687 /// Current thread must not be detached from JNI.
9688 ///
9689 /// Current thread must not be currently throwing an exception.
9690 ///
9691 /// Current thread does not hold a critical reference.
9692 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9693 ///
9694 /// `obj` must a valid and not already garbage collected.
9695 /// `methodID` must be valid, non-static and actually be a method of `obj`, return void and have 1 arguments
9696 ///
9697 pub unsafe fn CallVoidMethod1<A: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A) {
9698 unsafe {
9699 #[cfg(feature = "asserts")]
9700 {
9701 self.check_not_critical("CallVoidMethod");
9702 self.check_no_exception("CallVoidMethod");
9703 self.check_return_type_object("CallVoidMethod", obj, methodID, "void");
9704 self.check_parameter_types_object("CallVoidMethod", obj, methodID, arg1, 0, 1);
9705 }
9706 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...)>(61)(self.vtable, obj, methodID, arg1);
9707 }
9708 }
9709
9710 ///
9711 /// Calls a non-static java method that has 2 arguments and returns void
9712 ///
9713 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
9714 ///
9715 ///
9716 /// # Arguments
9717 /// * `obj` - which object the method should be called on
9718 /// * must be valid
9719 /// * must not be null
9720 /// * must not be already garbage collected
9721 ///
9722 /// * `methodID` - method id of the method
9723 /// * must not be null
9724 /// * must be valid
9725 /// * must not be a static
9726 /// * must actually be a method of `obj`
9727 /// * must refer to a method with 2 arguments
9728 ///
9729 /// # Throws Java Exception
9730 /// * Whatever the method threw
9731 ///
9732 ///
9733 /// # Panics
9734 /// if asserts feature is enabled and UB was detected
9735 ///
9736 /// # Safety
9737 ///
9738 /// Current thread must not be detached from JNI.
9739 ///
9740 /// Current thread must not be currently throwing an exception.
9741 ///
9742 /// Current thread does not hold a critical reference.
9743 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9744 ///
9745 /// `obj` must a valid and not already garbage collected.
9746 /// `methodID` must be valid, non-static and actually be a method of `obj`, return void and have 2 arguments
9747 ///
9748 pub unsafe fn CallVoidMethod2<A: JType, B: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B) {
9749 unsafe {
9750 #[cfg(feature = "asserts")]
9751 {
9752 self.check_not_critical("CallVoidMethod");
9753 self.check_no_exception("CallVoidMethod");
9754 self.check_return_type_object("CallVoidMethod", obj, methodID, "void");
9755 self.check_parameter_types_object("CallVoidMethod", obj, methodID, arg1, 0, 2);
9756 self.check_parameter_types_object("CallVoidMethod", obj, methodID, arg2, 1, 2);
9757 }
9758 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...)>(61)(self.vtable, obj, methodID, arg1, arg2);
9759 }
9760 }
9761
9762 ///
9763 /// Calls a non-static java method that has 3 arguments and returns void
9764 ///
9765 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
9766 ///
9767 ///
9768 /// # Arguments
9769 /// * `obj` - which object the method should be called on
9770 /// * must be valid
9771 /// * must not be null
9772 /// * must not be already garbage collected
9773 ///
9774 /// * `methodID` - method id of the method
9775 /// * must not be null
9776 /// * must be valid
9777 /// * must not be a static
9778 /// * must actually be a method of `obj`
9779 /// * must refer to a method with 3 arguments
9780 ///
9781 /// # Throws Java Exception
9782 /// * Whatever the method threw
9783 ///
9784 ///
9785 /// # Panics
9786 /// if asserts feature is enabled and UB was detected
9787 ///
9788 /// # Safety
9789 ///
9790 /// Current thread must not be detached from JNI.
9791 ///
9792 /// Current thread must not be currently throwing an exception.
9793 ///
9794 /// Current thread does not hold a critical reference.
9795 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9796 ///
9797 /// `obj` must a valid and not already garbage collected.
9798 /// `methodID` must be valid, non-static and actually be a method of `obj`, return void and have 3 arguments
9799 ///
9800 pub unsafe fn CallVoidMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B, arg3: C) {
9801 unsafe {
9802 #[cfg(feature = "asserts")]
9803 {
9804 self.check_not_critical("CallVoidMethod");
9805 self.check_no_exception("CallVoidMethod");
9806 self.check_return_type_object("CallVoidMethod", obj, methodID, "void");
9807 self.check_parameter_types_object("CallVoidMethod", obj, methodID, arg1, 0, 3);
9808 self.check_parameter_types_object("CallVoidMethod", obj, methodID, arg2, 1, 3);
9809 self.check_parameter_types_object("CallVoidMethod", obj, methodID, arg3, 2, 3);
9810 }
9811 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...)>(61)(self.vtable, obj, methodID, arg1, arg2, arg3);
9812 }
9813 }
9814
9815 ///
9816 /// Calls a non-static java method that returns an object
9817 ///
9818 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
9819 ///
9820 ///
9821 /// # Arguments
9822 /// * `obj` - which object the method should be called on
9823 /// * must be valid
9824 /// * must not be null
9825 /// * must not be already garbage collected
9826 ///
9827 /// * `methodID` - method id of the method
9828 /// * must not be null
9829 /// * must be valid
9830 /// * must not be a static
9831 /// * must actually be a method of `obj`
9832 ///
9833 /// * `args` - argument pointer
9834 /// * can be null if the method has no arguments
9835 /// * must not be null otherwise and point to the exact number of arguments the method expects
9836 ///
9837 /// # Returns
9838 /// Whatever the method returned or null if it threw
9839 ///
9840 /// # Throws Java Exception
9841 /// * Whatever the method threw
9842 ///
9843 ///
9844 /// # Panics
9845 /// if asserts feature is enabled and UB was detected
9846 ///
9847 /// # Safety
9848 ///
9849 /// Current thread must not be detached from JNI.
9850 ///
9851 /// Current thread must not be currently throwing an exception.
9852 ///
9853 /// Current thread does not hold a critical reference.
9854 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9855 ///
9856 /// `obj` must a valid and not already garbage collected.
9857 /// `methodID` must be valid, non-static and actually be a method of `obj` and return an object
9858 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
9859 /// `args` union must contain types that match the java methods parameters.
9860 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
9861 ///
9862 pub unsafe fn CallObjectMethodA(&self, obj: jobject, methodID: jmethodID, args: *const jtype) -> jobject {
9863 unsafe {
9864 #[cfg(feature = "asserts")]
9865 {
9866 self.check_not_critical("CallObjectMethodA");
9867 self.check_no_exception("CallObjectMethodA");
9868 self.check_return_type_object("CallObjectMethodA", obj, methodID, "object");
9869 }
9870 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, obj, methodID, args)
9871 }
9872 }
9873
9874 ///
9875 /// Calls a non-static java method that has 0 arguments and returns an object
9876 ///
9877 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
9878 ///
9879 ///
9880 /// # Arguments
9881 /// * `obj` - which object the method should be called on
9882 /// * must be valid
9883 /// * must not be null
9884 /// * must not be already garbage collected
9885 ///
9886 /// * `methodID` - method id of the method
9887 /// * must not be null
9888 /// * must be valid
9889 /// * must not be a static
9890 /// * must actually be a method of `obj`
9891 /// * must refer to a method with 0 arguments
9892 ///
9893 /// # Returns
9894 /// Whatever the method returned or null if it threw
9895 ///
9896 /// # Throws Java Exception
9897 /// * Whatever the method threw
9898 ///
9899 ///
9900 /// # Panics
9901 /// if asserts feature is enabled and UB was detected
9902 ///
9903 /// # Safety
9904 ///
9905 /// Current thread must not be detached from JNI.
9906 ///
9907 /// Current thread must not be currently throwing an exception.
9908 ///
9909 /// Current thread does not hold a critical reference.
9910 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9911 ///
9912 /// `obj` must a valid and not already garbage collected.
9913 /// `methodID` must be valid, non-static and actually be a method of `obj`, return an object and have no parameters
9914 ///
9915 pub unsafe fn CallObjectMethod0(&self, obj: jobject, methodID: jmethodID) -> jobject {
9916 unsafe {
9917 #[cfg(feature = "asserts")]
9918 {
9919 self.check_not_critical("CallObjectMethod");
9920 self.check_no_exception("CallObjectMethod");
9921 self.check_return_type_object("CallObjectMethod", obj, methodID, "object");
9922 }
9923 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jobject>(34)(self.vtable, obj, methodID)
9924 }
9925 }
9926
9927 ///
9928 /// Calls a non-static java method that has 1 arguments and returns an object
9929 ///
9930 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
9931 ///
9932 ///
9933 /// # Arguments
9934 /// * `obj` - which object the method should be called on
9935 /// * must be valid
9936 /// * must not be null
9937 /// * must not be already garbage collected
9938 ///
9939 /// * `methodID` - method id of the method
9940 /// * must not be null
9941 /// * must be valid
9942 /// * must not be a static
9943 /// * must actually be a method of `obj`
9944 /// * must refer to a method with 1 arguments
9945 ///
9946 /// # Returns
9947 /// Whatever the method returned or null if it threw
9948 ///
9949 /// # Throws Java Exception
9950 /// * Whatever the method threw
9951 ///
9952 ///
9953 /// # Panics
9954 /// if asserts feature is enabled and UB was detected
9955 ///
9956 /// # Safety
9957 ///
9958 /// Current thread must not be detached from JNI.
9959 ///
9960 /// Current thread must not be currently throwing an exception.
9961 ///
9962 /// Current thread does not hold a critical reference.
9963 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
9964 ///
9965 /// `obj` must a valid and not already garbage collected.
9966 /// `methodID` must be valid, non-static and actually be a method of `obj`, return an object and have 1 arguments
9967 ///
9968 pub unsafe fn CallObjectMethod1<A: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A) -> jobject {
9969 unsafe {
9970 #[cfg(feature = "asserts")]
9971 {
9972 self.check_not_critical("CallObjectMethod");
9973 self.check_no_exception("CallObjectMethod");
9974 self.check_return_type_object("CallObjectMethod", obj, methodID, "object");
9975 self.check_parameter_types_object("CallObjectMethod", obj, methodID, arg1, 0, 1);
9976 }
9977 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jobject>(34)(self.vtable, obj, methodID, arg1)
9978 }
9979 }
9980
9981 ///
9982 /// Calls a non-static java method that has 2 arguments and returns an object
9983 ///
9984 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
9985 ///
9986 ///
9987 /// # Arguments
9988 /// * `obj` - which object the method should be called on
9989 /// * must be valid
9990 /// * must not be null
9991 /// * must not be already garbage collected
9992 ///
9993 /// * `methodID` - method id of the method
9994 /// * must not be null
9995 /// * must be valid
9996 /// * must not be a static
9997 /// * must actually be a method of `obj`
9998 /// * must refer to a method with 2 arguments
9999 ///
10000 /// # Returns
10001 /// Whatever the method returned or null if it threw
10002 ///
10003 /// # Throws Java Exception
10004 /// * Whatever the method threw
10005 ///
10006 ///
10007 /// # Panics
10008 /// if asserts feature is enabled and UB was detected
10009 ///
10010 /// # Safety
10011 ///
10012 /// Current thread must not be detached from JNI.
10013 ///
10014 /// Current thread must not be currently throwing an exception.
10015 ///
10016 /// Current thread does not hold a critical reference.
10017 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10018 ///
10019 /// `obj` must a valid and not already garbage collected.
10020 /// `methodID` must be valid, non-static and actually be a method of `obj`, return an object and have 2 arguments
10021 ///
10022 pub unsafe fn CallObjectMethod2<A: JType, B: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B) -> jobject {
10023 unsafe {
10024 #[cfg(feature = "asserts")]
10025 {
10026 self.check_not_critical("CallObjectMethod");
10027 self.check_no_exception("CallObjectMethod");
10028 self.check_return_type_object("CallObjectMethod", obj, methodID, "object");
10029 self.check_parameter_types_object("CallObjectMethod", obj, methodID, arg1, 0, 2);
10030 self.check_parameter_types_object("CallObjectMethod", obj, methodID, arg2, 1, 2);
10031 }
10032 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jobject>(34)(self.vtable, obj, methodID, arg1, arg2)
10033 }
10034 }
10035
10036 ///
10037 /// Calls a non-static java method that has 3 arguments and returns an object
10038 ///
10039 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10040 ///
10041 ///
10042 /// # Arguments
10043 /// * `obj` - which object the method should be called on
10044 /// * must be valid
10045 /// * must not be null
10046 /// * must not be already garbage collected
10047 ///
10048 /// * `methodID` - method id of the method
10049 /// * must not be null
10050 /// * must be valid
10051 /// * must not be a static
10052 /// * must actually be a method of `obj`
10053 /// * must refer to a method with 3 arguments
10054 ///
10055 /// # Returns
10056 /// Whatever the method returned or null if it threw
10057 ///
10058 /// # Throws Java Exception
10059 /// * Whatever the method threw
10060 ///
10061 ///
10062 /// # Panics
10063 /// if asserts feature is enabled and UB was detected
10064 ///
10065 /// # Safety
10066 ///
10067 /// Current thread must not be detached from JNI.
10068 ///
10069 /// Current thread must not be currently throwing an exception.
10070 ///
10071 /// Current thread does not hold a critical reference.
10072 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10073 ///
10074 /// `obj` must a valid and not already garbage collected.
10075 /// `methodID` must be valid, non-static and actually be a method of `obj`, return an object and have 3 arguments
10076 ///
10077 pub unsafe fn CallObjectMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jobject {
10078 unsafe {
10079 #[cfg(feature = "asserts")]
10080 {
10081 self.check_not_critical("CallObjectMethod");
10082 self.check_no_exception("CallObjectMethod");
10083 self.check_return_type_object("CallObjectMethod", obj, methodID, "object");
10084 self.check_parameter_types_object("CallObjectMethod", obj, methodID, arg1, 0, 3);
10085 self.check_parameter_types_object("CallObjectMethod", obj, methodID, arg2, 1, 3);
10086 self.check_parameter_types_object("CallObjectMethod", obj, methodID, arg3, 2, 3);
10087 }
10088 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jobject>(34)(self.vtable, obj, methodID, arg1, arg2, arg3)
10089 }
10090 }
10091
10092 ///
10093 /// Calls a non-static java method that returns a boolean
10094 ///
10095 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10096 ///
10097 ///
10098 /// # Arguments
10099 /// * `obj` - which object the method should be called on
10100 /// * must be valid
10101 /// * must not be null
10102 /// * must not be already garbage collected
10103 ///
10104 /// * `methodID` - method id of the method
10105 /// * must not be null
10106 /// * must be valid
10107 /// * must not be a static
10108 /// * must actually be a method of `obj`
10109 ///
10110 /// * `args` - argument pointer
10111 /// * can be null if the method has no arguments
10112 /// * must not be null otherwise and point to the exact number of arguments the method expects
10113 ///
10114 /// # Returns
10115 /// Whatever the method returned or false if it threw
10116 ///
10117 /// # Throws Java Exception
10118 /// * Whatever the method threw
10119 ///
10120 ///
10121 /// # Panics
10122 /// if asserts feature is enabled and UB was detected
10123 ///
10124 /// # Safety
10125 ///
10126 /// Current thread must not be detached from JNI.
10127 ///
10128 /// Current thread must not be currently throwing an exception.
10129 ///
10130 /// Current thread does not hold a critical reference.
10131 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10132 ///
10133 /// `obj` must a valid and not already garbage collected.
10134 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a boolean
10135 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
10136 /// `args` union must contain types that match the java methods parameters.
10137 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
10138 ///
10139 pub unsafe fn CallBooleanMethodA(&self, obj: jobject, methodID: jmethodID, args: *const jtype) -> bool {
10140 unsafe {
10141 #[cfg(feature = "asserts")]
10142 {
10143 self.check_not_critical("CallBooleanMethodA");
10144 self.check_no_exception("CallBooleanMethodA");
10145 self.check_return_type_object("CallBooleanMethodA", obj, methodID, "boolean");
10146 }
10147 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jboolean>(39)(self.vtable, obj, methodID, args).as_bool()
10148 }
10149 }
10150
10151 ///
10152 /// Calls a non-static java method that has 0 arguments and returns boolean
10153 ///
10154 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10155 ///
10156 ///
10157 /// # Arguments
10158 /// * `obj` - which object the method should be called on
10159 /// * must be valid
10160 /// * must not be null
10161 /// * must not be already garbage collected
10162 ///
10163 /// * `methodID` - method id of the method
10164 /// * must not be null
10165 /// * must be valid
10166 /// * must not be a static
10167 /// * must actually be a method of `obj`
10168 /// * must refer to a method with 0 arguments
10169 ///
10170 /// # Returns
10171 /// Whatever the method returned or false if it threw
10172 ///
10173 /// # Throws Java Exception
10174 /// * Whatever the method threw
10175 ///
10176 ///
10177 /// # Panics
10178 /// if asserts feature is enabled and UB was detected
10179 ///
10180 /// # Safety
10181 ///
10182 /// Current thread must not be detached from JNI.
10183 ///
10184 /// Current thread must not be currently throwing an exception.
10185 ///
10186 /// Current thread does not hold a critical reference.
10187 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10188 ///
10189 /// `obj` must a valid and not already garbage collected.
10190 /// `methodID` must be valid, non-static and actually be a method of `obj`, return boolean and have no parameters
10191 ///
10192 pub unsafe fn CallBooleanMethod0(&self, obj: jobject, methodID: jmethodID) -> bool {
10193 unsafe {
10194 #[cfg(feature = "asserts")]
10195 {
10196 self.check_not_critical("CallBooleanMethod");
10197 self.check_no_exception("CallBooleanMethod");
10198 self.check_return_type_object("CallBooleanMethod", obj, methodID, "boolean");
10199 }
10200 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jboolean>(37)(self.vtable, obj, methodID).as_bool()
10201 }
10202 }
10203
10204 ///
10205 /// Calls a non-static java method that has 1 arguments and returns boolean
10206 ///
10207 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10208 ///
10209 ///
10210 /// # Arguments
10211 /// * `obj` - which object the method should be called on
10212 /// * must be valid
10213 /// * must not be null
10214 /// * must not be already garbage collected
10215 ///
10216 /// * `methodID` - method id of the method
10217 /// * must not be null
10218 /// * must be valid
10219 /// * must not be a static
10220 /// * must actually be a method of `obj`
10221 /// * must refer to a method with 1 arguments
10222 ///
10223 /// # Returns
10224 /// Whatever the method returned or false if it threw
10225 ///
10226 /// # Throws Java Exception
10227 /// * Whatever the method threw
10228 ///
10229 ///
10230 /// # Panics
10231 /// if asserts feature is enabled and UB was detected
10232 ///
10233 /// # Safety
10234 ///
10235 /// Current thread must not be detached from JNI.
10236 ///
10237 /// Current thread must not be currently throwing an exception.
10238 ///
10239 /// Current thread does not hold a critical reference.
10240 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10241 ///
10242 /// `obj` must a valid and not already garbage collected.
10243 /// `methodID` must be valid, non-static and actually be a method of `obj`, return boolean and have 1 parameter
10244 /// The parameter types must exactly match the java method parameters.
10245 ///
10246 pub unsafe fn CallBooleanMethod1<A: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A) -> bool {
10247 unsafe {
10248 #[cfg(feature = "asserts")]
10249 {
10250 self.check_not_critical("CallBooleanMethod");
10251 self.check_no_exception("CallBooleanMethod");
10252 self.check_return_type_object("CallBooleanMethod", obj, methodID, "boolean");
10253 self.check_parameter_types_object("CallBooleanMethod", obj, methodID, arg1, 0, 1);
10254 }
10255 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jboolean>(37)(self.vtable, obj, methodID, arg1).as_bool()
10256 }
10257 }
10258
10259 ///
10260 /// Calls a non-static java method that has 2 arguments and returns boolean
10261 ///
10262 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10263 ///
10264 ///
10265 /// # Arguments
10266 /// * `obj` - which object the method should be called on
10267 /// * must be valid
10268 /// * must not be null
10269 /// * must not be already garbage collected
10270 ///
10271 /// * `methodID` - method id of the method
10272 /// * must not be null
10273 /// * must be valid
10274 /// * must not be a static
10275 /// * must actually be a method of `obj`
10276 /// * must refer to a method with 2 arguments
10277 ///
10278 /// # Returns
10279 /// Whatever the method returned or false if it threw
10280 ///
10281 /// # Throws Java Exception
10282 /// * Whatever the method threw
10283 ///
10284 ///
10285 /// # Panics
10286 /// if asserts feature is enabled and UB was detected
10287 ///
10288 /// # Safety
10289 ///
10290 /// Current thread must not be detached from JNI.
10291 ///
10292 /// Current thread must not be currently throwing an exception.
10293 ///
10294 /// Current thread does not hold a critical reference.
10295 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10296 ///
10297 /// `obj` must a valid and not already garbage collected.
10298 /// `methodID` must be valid, non-static and actually be a method of `obj`, return boolean and have 2 parameter
10299 /// The parameter types must exactly match the java method parameters.
10300 ///
10301 pub unsafe fn CallBooleanMethod2<A: JType, B: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B) -> bool {
10302 unsafe {
10303 #[cfg(feature = "asserts")]
10304 {
10305 self.check_not_critical("CallBooleanMethod");
10306 self.check_no_exception("CallBooleanMethod");
10307 self.check_return_type_object("CallBooleanMethod", obj, methodID, "boolean");
10308 self.check_parameter_types_object("CallBooleanMethod", obj, methodID, arg1, 0, 2);
10309 self.check_parameter_types_object("CallBooleanMethod", obj, methodID, arg2, 1, 2);
10310 }
10311 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jboolean>(37)(self.vtable, obj, methodID, arg1, arg2).as_bool()
10312 }
10313 }
10314
10315 ///
10316 /// Calls a non-static java method that has 3 arguments and returns boolean
10317 ///
10318 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10319 ///
10320 ///
10321 /// # Arguments
10322 /// * `obj` - which object the method should be called on
10323 /// * must be valid
10324 /// * must not be null
10325 /// * must not be already garbage collected
10326 ///
10327 /// * `methodID` - method id of the method
10328 /// * must not be null
10329 /// * must be valid
10330 /// * must not be a static
10331 /// * must actually be a method of `obj`
10332 /// * must refer to a method with 3 arguments
10333 ///
10334 /// # Returns
10335 /// Whatever the method returned or false if it threw
10336 ///
10337 /// # Throws Java Exception
10338 /// * Whatever the method threw
10339 ///
10340 ///
10341 /// # Panics
10342 /// if asserts feature is enabled and UB was detected
10343 ///
10344 /// # Safety
10345 ///
10346 /// Current thread must not be detached from JNI.
10347 ///
10348 /// Current thread must not be currently throwing an exception.
10349 ///
10350 /// Current thread does not hold a critical reference.
10351 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10352 ///
10353 /// `obj` must a valid and not already garbage collected.
10354 /// `methodID` must be valid, non-static and actually be a method of `obj`, return boolean and have 3 parameter
10355 /// The parameter types must exactly match the java method parameters.
10356 ///
10357 pub unsafe fn CallBooleanMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> bool {
10358 unsafe {
10359 #[cfg(feature = "asserts")]
10360 {
10361 self.check_not_critical("CallBooleanMethod");
10362 self.check_no_exception("CallBooleanMethod");
10363 self.check_return_type_object("CallBooleanMethod", obj, methodID, "boolean");
10364 self.check_parameter_types_object("CallBooleanMethod", obj, methodID, arg1, 0, 3);
10365 self.check_parameter_types_object("CallBooleanMethod", obj, methodID, arg2, 1, 3);
10366 self.check_parameter_types_object("CallBooleanMethod", obj, methodID, arg3, 2, 3);
10367 }
10368 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jboolean>(37)(self.vtable, obj, methodID, arg1, arg2, arg3).as_bool()
10369 }
10370 }
10371
10372 ///
10373 /// Calls a non-static java method that returns a byte
10374 ///
10375 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10376 ///
10377 ///
10378 /// # Arguments
10379 /// * `obj` - which object the method should be called on
10380 /// * must be valid
10381 /// * must not be null
10382 /// * must not be already garbage collected
10383 ///
10384 /// * `methodID` - method id of the method
10385 /// * must not be null
10386 /// * must be valid
10387 /// * must not be a static
10388 /// * must actually be a method of `obj`
10389 ///
10390 /// * `args` - argument pointer
10391 /// * can be null if the method has no arguments
10392 /// * must not be null otherwise and point to the exact number of arguments the method expects
10393 ///
10394 /// # Returns
10395 /// Whatever the method returned or 0 if it threw
10396 ///
10397 /// # Throws Java Exception
10398 /// * Whatever the method threw
10399 ///
10400 ///
10401 /// # Panics
10402 /// if asserts feature is enabled and UB was detected
10403 ///
10404 /// # Safety
10405 ///
10406 /// Current thread must not be detached from JNI.
10407 ///
10408 /// Current thread must not be currently throwing an exception.
10409 ///
10410 /// Current thread does not hold a critical reference.
10411 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10412 ///
10413 /// `obj` must a valid and not already garbage collected.
10414 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a byte
10415 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
10416 /// `args` union must contain types that match the java methods parameters.
10417 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
10418 ///
10419 pub unsafe fn CallByteMethodA(&self, obj: jobject, methodID: jmethodID, args: *const jtype) -> jbyte {
10420 unsafe {
10421 #[cfg(feature = "asserts")]
10422 {
10423 self.check_not_critical("CallByteMethodA");
10424 self.check_no_exception("CallByteMethodA");
10425 self.check_return_type_object("CallByteMethodA", obj, methodID, "byte");
10426 }
10427 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jbyte>(42)(self.vtable, obj, methodID, args)
10428 }
10429 }
10430
10431 ///
10432 /// Calls a non-static java method that has 0 arguments and returns byte
10433 ///
10434 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10435 ///
10436 ///
10437 /// # Arguments
10438 /// * `obj` - which object the method should be called on
10439 /// * must be valid
10440 /// * must not be null
10441 /// * must not be already garbage collected
10442 ///
10443 /// * `methodID` - method id of the method
10444 /// * must not be null
10445 /// * must be valid
10446 /// * must not be a static
10447 /// * must actually be a method of `obj`
10448 /// * must refer to a method with 0 arguments
10449 ///
10450 /// # Returns
10451 /// Whatever the method returned or 0 if it threw
10452 ///
10453 /// # Throws Java Exception
10454 /// * Whatever the method threw
10455 ///
10456 ///
10457 /// # Panics
10458 /// if asserts feature is enabled and UB was detected
10459 ///
10460 /// # Safety
10461 ///
10462 /// Current thread must not be detached from JNI.
10463 ///
10464 /// Current thread must not be currently throwing an exception.
10465 ///
10466 /// Current thread does not hold a critical reference.
10467 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10468 ///
10469 /// `obj` must a valid and not already garbage collected.
10470 /// `methodID` must be valid, non-static and actually be a method of `obj`, return byte and have no parameters
10471 ///
10472 pub unsafe fn CallByteMethod0(&self, obj: jobject, methodID: jmethodID) -> jbyte {
10473 unsafe {
10474 #[cfg(feature = "asserts")]
10475 {
10476 self.check_not_critical("CallByteMethod0");
10477 self.check_no_exception("CallByteMethod0");
10478 self.check_return_type_object("CallByteMethod0", obj, methodID, "byte");
10479 }
10480 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jbyte>(40)(self.vtable, obj, methodID)
10481 }
10482 }
10483
10484 ///
10485 /// Calls a non-static java method that has 1 arguments and returns byte
10486 ///
10487 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10488 ///
10489 ///
10490 /// # Arguments
10491 /// * `obj` - which object the method should be called on
10492 /// * must be valid
10493 /// * must not be null
10494 /// * must not be already garbage collected
10495 ///
10496 /// * `methodID` - method id of the method
10497 /// * must not be null
10498 /// * must be valid
10499 /// * must not be a static
10500 /// * must actually be a method of `obj`
10501 /// * must refer to a method with 1 arguments
10502 ///
10503 /// # Returns
10504 /// Whatever the method returned or 0 if it threw
10505 ///
10506 /// # Throws Java Exception
10507 /// * Whatever the method threw
10508 ///
10509 ///
10510 /// # Panics
10511 /// if asserts feature is enabled and UB was detected
10512 ///
10513 /// # Safety
10514 ///
10515 /// Current thread must not be detached from JNI.
10516 ///
10517 /// Current thread must not be currently throwing an exception.
10518 ///
10519 /// Current thread does not hold a critical reference.
10520 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10521 ///
10522 /// `obj` must a valid and not already garbage collected.
10523 /// `methodID` must be valid, non-static and actually be a method of `obj`, return byte and have 1 parameter
10524 /// The parameter types must exactly match the java method parameters.
10525 ///
10526 pub unsafe fn CallByteMethod1<A: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A) -> jbyte {
10527 unsafe {
10528 #[cfg(feature = "asserts")]
10529 {
10530 self.check_not_critical("CallByteMethod1");
10531 self.check_no_exception("CallByteMethod1");
10532 self.check_return_type_object("CallByteMethod1", obj, methodID, "byte");
10533 self.check_parameter_types_object("CallByteMethod1", obj, methodID, arg1, 0, 1);
10534 }
10535 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jbyte>(40)(self.vtable, obj, methodID, arg1)
10536 }
10537 }
10538
10539 ///
10540 /// Calls a non-static java method that has 2 arguments and returns byte
10541 ///
10542 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10543 ///
10544 ///
10545 /// # Arguments
10546 /// * `obj` - which object the method should be called on
10547 /// * must be valid
10548 /// * must not be null
10549 /// * must not be already garbage collected
10550 ///
10551 /// * `methodID` - method id of the method
10552 /// * must not be null
10553 /// * must be valid
10554 /// * must not be a static
10555 /// * must actually be a method of `obj`
10556 /// * must refer to a method with 2 arguments
10557 ///
10558 /// # Returns
10559 /// Whatever the method returned or 0 if it threw
10560 ///
10561 /// # Throws Java Exception
10562 /// * Whatever the method threw
10563 ///
10564 ///
10565 /// # Panics
10566 /// if asserts feature is enabled and UB was detected
10567 ///
10568 /// # Safety
10569 ///
10570 /// Current thread must not be detached from JNI.
10571 ///
10572 /// Current thread must not be currently throwing an exception.
10573 ///
10574 /// Current thread does not hold a critical reference.
10575 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10576 ///
10577 /// `obj` must a valid and not already garbage collected.
10578 /// `methodID` must be valid, non-static and actually be a method of `obj`, return byte and have 2 parameter
10579 /// The parameter types must exactly match the java method parameters.
10580 ///
10581 pub unsafe fn CallByteMethod2<A: JType, B: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B) -> jbyte {
10582 unsafe {
10583 #[cfg(feature = "asserts")]
10584 {
10585 self.check_not_critical("CallByteMethod2");
10586 self.check_no_exception("CallByteMethod2");
10587 self.check_return_type_object("CallByteMethod2", obj, methodID, "byte");
10588 self.check_parameter_types_object("CallByteMethod2", obj, methodID, arg1, 0, 2);
10589 self.check_parameter_types_object("CallByteMethod2", obj, methodID, arg2, 1, 2);
10590 }
10591 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jbyte>(40)(self.vtable, obj, methodID, arg1, arg2)
10592 }
10593 }
10594
10595 ///
10596 /// Calls a non-static java method that has 3 arguments and returns byte
10597 ///
10598 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10599 ///
10600 ///
10601 /// # Arguments
10602 /// * `obj` - which object the method should be called on
10603 /// * must be valid
10604 /// * must not be null
10605 /// * must not be already garbage collected
10606 ///
10607 /// * `methodID` - method id of the method
10608 /// * must not be null
10609 /// * must be valid
10610 /// * must not be a static
10611 /// * must actually be a method of `obj`
10612 /// * must refer to a method with 3 arguments
10613 ///
10614 /// # Returns
10615 /// Whatever the method returned or 0 if it threw
10616 ///
10617 /// # Throws Java Exception
10618 /// * Whatever the method threw
10619 ///
10620 ///
10621 /// # Panics
10622 /// if asserts feature is enabled and UB was detected
10623 ///
10624 /// # Safety
10625 ///
10626 /// Current thread must not be detached from JNI.
10627 ///
10628 /// Current thread must not be currently throwing an exception.
10629 ///
10630 /// Current thread does not hold a critical reference.
10631 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10632 ///
10633 /// `obj` must a valid and not already garbage collected.
10634 /// `methodID` must be valid, non-static and actually be a method of `obj`, return byte and have 3 parameter
10635 /// The parameter types must exactly match the java method parameters.
10636 ///
10637 pub unsafe fn CallByteMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jbyte {
10638 unsafe {
10639 #[cfg(feature = "asserts")]
10640 {
10641 self.check_not_critical("CallByteMethod3");
10642 self.check_no_exception("CallByteMethod3");
10643 self.check_return_type_object("CallByteMethod3", obj, methodID, "byte");
10644 self.check_parameter_types_object("CallByteMethod3", obj, methodID, arg1, 0, 3);
10645 self.check_parameter_types_object("CallByteMethod3", obj, methodID, arg2, 1, 3);
10646 self.check_parameter_types_object("CallByteMethod3", obj, methodID, arg3, 2, 3);
10647 }
10648 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jbyte>(40)(self.vtable, obj, methodID, arg1, arg2, arg3)
10649 }
10650 }
10651
10652 ///
10653 /// Calls a non-static java method that returns a char
10654 ///
10655 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10656 ///
10657 ///
10658 /// # Arguments
10659 /// * `obj` - which object the method should be called on
10660 /// * must be valid
10661 /// * must not be null
10662 /// * must not be already garbage collected
10663 ///
10664 /// * `methodID` - method id of the method
10665 /// * must not be null
10666 /// * must be valid
10667 /// * must not be a static
10668 /// * must actually be a method of `obj`
10669 ///
10670 /// * `args` - argument pointer
10671 /// * can be null if the method has no arguments
10672 /// * must not be null otherwise and point to the exact number of arguments the method expects
10673 ///
10674 /// # Returns
10675 /// Whatever the method returned or 0 if it threw
10676 ///
10677 /// # Throws Java Exception
10678 /// * Whatever the method threw
10679 ///
10680 ///
10681 /// # Panics
10682 /// if asserts feature is enabled and UB was detected
10683 ///
10684 /// # Safety
10685 ///
10686 /// Current thread must not be detached from JNI.
10687 ///
10688 /// Current thread must not be currently throwing an exception.
10689 ///
10690 /// Current thread does not hold a critical reference.
10691 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10692 ///
10693 /// `obj` must a valid and not already garbage collected.
10694 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a char
10695 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
10696 /// `args` union must contain types that match the java methods parameters.
10697 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
10698 ///
10699 pub unsafe fn CallCharMethodA(&self, obj: jobject, methodID: jmethodID, args: *const jtype) -> jchar {
10700 unsafe {
10701 #[cfg(feature = "asserts")]
10702 {
10703 self.check_not_critical("CallCharMethodA");
10704 self.check_no_exception("CallCharMethodA");
10705 self.check_return_type_object("CallCharMethodA", obj, methodID, "char");
10706 }
10707 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jchar>(45)(self.vtable, obj, methodID, args)
10708 }
10709 }
10710
10711 ///
10712 /// Calls a non-static java method that has 0 arguments and returns char
10713 ///
10714 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10715 ///
10716 ///
10717 /// # Arguments
10718 /// * `obj` - which object the method should be called on
10719 /// * must be valid
10720 /// * must not be null
10721 /// * must not be already garbage collected
10722 ///
10723 /// * `methodID` - method id of the method
10724 /// * must not be null
10725 /// * must be valid
10726 /// * must not be a static
10727 /// * must actually be a method of `obj`
10728 /// * must refer to a method with 0 arguments
10729 ///
10730 /// # Returns
10731 /// Whatever the method returned or 0 if it threw
10732 ///
10733 /// # Throws Java Exception
10734 /// * Whatever the method threw
10735 ///
10736 ///
10737 /// # Panics
10738 /// if asserts feature is enabled and UB was detected
10739 ///
10740 /// # Safety
10741 ///
10742 /// Current thread must not be detached from JNI.
10743 ///
10744 /// Current thread must not be currently throwing an exception.
10745 ///
10746 /// Current thread does not hold a critical reference.
10747 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10748 ///
10749 /// `obj` must a valid and not already garbage collected.
10750 /// `methodID` must be valid, non-static and actually be a method of `obj`, return char and have no parameters
10751 ///
10752 pub unsafe fn CallCharMethod0(&self, obj: jobject, methodID: jmethodID) -> jchar {
10753 unsafe {
10754 #[cfg(feature = "asserts")]
10755 {
10756 self.check_not_critical("CallCharMethod");
10757 self.check_no_exception("CallCharMethod");
10758 self.check_return_type_object("CallCharMethod", obj, methodID, "char");
10759 }
10760 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jchar>(43)(self.vtable, obj, methodID)
10761 }
10762 }
10763
10764 ///
10765 /// Calls a non-static java method that has 1 arguments and returns char
10766 ///
10767 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10768 ///
10769 ///
10770 /// # Arguments
10771 /// * `obj` - which object the method should be called on
10772 /// * must be valid
10773 /// * must not be null
10774 /// * must not be already garbage collected
10775 ///
10776 /// * `methodID` - method id of the method
10777 /// * must not be null
10778 /// * must be valid
10779 /// * must not be a static
10780 /// * must actually be a method of `obj`
10781 /// * must refer to a method with 1 arguments
10782 ///
10783 /// # Returns
10784 /// Whatever the method returned or 0 if it threw
10785 ///
10786 /// # Throws Java Exception
10787 /// * Whatever the method threw
10788 ///
10789 ///
10790 /// # Panics
10791 /// if asserts feature is enabled and UB was detected
10792 ///
10793 /// # Safety
10794 ///
10795 /// Current thread must not be detached from JNI.
10796 ///
10797 /// Current thread must not be currently throwing an exception.
10798 ///
10799 /// Current thread does not hold a critical reference.
10800 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10801 ///
10802 /// `obj` must a valid and not already garbage collected.
10803 /// `methodID` must be valid, non-static and actually be a method of `obj`, return char and have 1 parameter
10804 /// The parameter types must exactly match the java method parameters.
10805 ///
10806 pub unsafe fn CallCharMethod1<A: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A) -> jchar {
10807 unsafe {
10808 #[cfg(feature = "asserts")]
10809 {
10810 self.check_not_critical("CallCharMethod");
10811 self.check_no_exception("CallCharMethod");
10812 self.check_return_type_object("CallCharMethod", obj, methodID, "char");
10813 self.check_parameter_types_object("CallCharMethod", obj, methodID, arg1, 0, 1);
10814 }
10815 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jchar>(43)(self.vtable, obj, methodID, arg1)
10816 }
10817 }
10818
10819 ///
10820 /// Calls a non-static java method that has 2 arguments and returns char
10821 ///
10822 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10823 ///
10824 ///
10825 /// # Arguments
10826 /// * `obj` - which object the method should be called on
10827 /// * must be valid
10828 /// * must not be null
10829 /// * must not be already garbage collected
10830 ///
10831 /// * `methodID` - method id of the method
10832 /// * must not be null
10833 /// * must be valid
10834 /// * must not be a static
10835 /// * must actually be a method of `obj`
10836 /// * must refer to a method with 2 arguments
10837 ///
10838 /// # Returns
10839 /// Whatever the method returned or 0 if it threw
10840 ///
10841 /// # Throws Java Exception
10842 /// * Whatever the method threw
10843 ///
10844 ///
10845 /// # Panics
10846 /// if asserts feature is enabled and UB was detected
10847 ///
10848 /// # Safety
10849 ///
10850 /// Current thread must not be detached from JNI.
10851 ///
10852 /// Current thread must not be currently throwing an exception.
10853 ///
10854 /// Current thread does not hold a critical reference.
10855 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10856 ///
10857 /// `obj` must a valid and not already garbage collected.
10858 /// `methodID` must be valid, non-static and actually be a method of `obj`, return char and have 2 parameter
10859 /// The parameter types must exactly match the java method parameters.
10860 ///
10861 pub unsafe fn CallCharMethod2<A: JType, B: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B) -> jchar {
10862 unsafe {
10863 #[cfg(feature = "asserts")]
10864 {
10865 self.check_not_critical("CallCharMethod");
10866 self.check_no_exception("CallCharMethod");
10867 self.check_return_type_object("CallCharMethod", obj, methodID, "char");
10868 self.check_parameter_types_object("CallCharMethod", obj, methodID, arg1, 0, 2);
10869 self.check_parameter_types_object("CallCharMethod", obj, methodID, arg2, 1, 2);
10870 }
10871 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jchar>(43)(self.vtable, obj, methodID, arg1, arg2)
10872 }
10873 }
10874
10875 ///
10876 /// Calls a non-static java method that has 3 arguments and returns char
10877 ///
10878 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10879 ///
10880 ///
10881 /// # Arguments
10882 /// * `obj` - which object the method should be called on
10883 /// * must be valid
10884 /// * must not be null
10885 /// * must not be already garbage collected
10886 ///
10887 /// * `methodID` - method id of the method
10888 /// * must not be null
10889 /// * must be valid
10890 /// * must not be a static
10891 /// * must actually be a method of `obj`
10892 /// * must refer to a method with 3 arguments
10893 ///
10894 /// # Returns
10895 /// Whatever the method returned or 0 if it threw
10896 ///
10897 /// # Throws Java Exception
10898 /// * Whatever the method threw
10899 ///
10900 ///
10901 /// # Panics
10902 /// if asserts feature is enabled and UB was detected
10903 ///
10904 /// # Safety
10905 ///
10906 /// Current thread must not be detached from JNI.
10907 ///
10908 /// Current thread must not be currently throwing an exception.
10909 ///
10910 /// Current thread does not hold a critical reference.
10911 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10912 ///
10913 /// `obj` must a valid and not already garbage collected.
10914 /// `methodID` must be valid, non-static and actually be a method of `obj`, return char and have 3 parameter
10915 /// The parameter types must exactly match the java method parameters.
10916 ///
10917 pub unsafe fn CallCharMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jchar {
10918 unsafe {
10919 #[cfg(feature = "asserts")]
10920 {
10921 self.check_not_critical("CallCharMethod");
10922 self.check_no_exception("CallCharMethod");
10923 self.check_return_type_object("CallCharMethod", obj, methodID, "char");
10924 self.check_parameter_types_object("CallCharMethod", obj, methodID, arg1, 0, 3);
10925 self.check_parameter_types_object("CallCharMethod", obj, methodID, arg2, 1, 3);
10926 self.check_parameter_types_object("CallCharMethod", obj, methodID, arg3, 2, 3);
10927 }
10928 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jchar>(43)(self.vtable, obj, methodID, arg1, arg2, arg3)
10929 }
10930 }
10931
10932 ///
10933 /// Calls a non-static java method that returns a short
10934 ///
10935 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10936 ///
10937 ///
10938 /// # Arguments
10939 /// * `obj` - which object the method should be called on
10940 /// * must be valid
10941 /// * must not be null
10942 /// * must not be already garbage collected
10943 ///
10944 /// * `methodID` - method id of the method
10945 /// * must not be null
10946 /// * must be valid
10947 /// * must not be a static
10948 /// * must actually be a method of `obj`
10949 ///
10950 /// * `args` - argument pointer
10951 /// * can be null if the method has no arguments
10952 /// * must not be null otherwise and point to the exact number of arguments the method expects
10953 ///
10954 /// # Returns
10955 /// Whatever the method returned or 0 if it threw
10956 ///
10957 /// # Throws Java Exception
10958 /// * Whatever the method threw
10959 ///
10960 ///
10961 /// # Panics
10962 /// if asserts feature is enabled and UB was detected
10963 ///
10964 /// # Safety
10965 ///
10966 /// Current thread must not be detached from JNI.
10967 ///
10968 /// Current thread must not be currently throwing an exception.
10969 ///
10970 /// Current thread does not hold a critical reference.
10971 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
10972 ///
10973 /// `obj` must a valid and not already garbage collected.
10974 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a short
10975 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
10976 /// `args` union must contain types that match the java methods parameters.
10977 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
10978 ///
10979 pub unsafe fn CallShortMethodA(&self, obj: jobject, methodID: jmethodID, args: *const jtype) -> jshort {
10980 unsafe {
10981 #[cfg(feature = "asserts")]
10982 {
10983 self.check_not_critical("CallShortMethodA");
10984 self.check_no_exception("CallShortMethodA");
10985 self.check_return_type_object("CallShortMethodA", obj, methodID, "short");
10986 }
10987 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jshort>(48)(self.vtable, obj, methodID, args)
10988 }
10989 }
10990
10991 ///
10992 /// Calls a non-static java method that has 0 arguments and returns short
10993 ///
10994 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
10995 ///
10996 ///
10997 /// # Arguments
10998 /// * `obj` - which object the method should be called on
10999 /// * must be valid
11000 /// * must not be null
11001 /// * must not be already garbage collected
11002 ///
11003 /// * `methodID` - method id of the method
11004 /// * must not be null
11005 /// * must be valid
11006 /// * must not be a static
11007 /// * must actually be a method of `obj`
11008 /// * must refer to a method with 0 arguments
11009 ///
11010 /// # Returns
11011 /// Whatever the method returned or 0 if it threw
11012 ///
11013 /// # Throws Java Exception
11014 /// * Whatever the method threw
11015 ///
11016 ///
11017 /// # Panics
11018 /// if asserts feature is enabled and UB was detected
11019 ///
11020 /// # Safety
11021 ///
11022 /// Current thread must not be detached from JNI.
11023 ///
11024 /// Current thread must not be currently throwing an exception.
11025 ///
11026 /// Current thread does not hold a critical reference.
11027 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11028 ///
11029 /// `obj` must a valid and not already garbage collected.
11030 /// `methodID` must be valid, non-static and actually be a method of `obj`, return short and have no parameters
11031 ///
11032 pub unsafe fn CallShortMethod0(&self, obj: jobject, methodID: jmethodID) -> jshort {
11033 unsafe {
11034 #[cfg(feature = "asserts")]
11035 {
11036 self.check_not_critical("CallShortMethod");
11037 self.check_no_exception("CallShortMethod");
11038 self.check_return_type_object("CallShortMethod", obj, methodID, "short");
11039 }
11040 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jshort>(46)(self.vtable, obj, methodID)
11041 }
11042 }
11043
11044 ///
11045 /// Calls a non-static java method that has 1 arguments and returns short
11046 ///
11047 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11048 ///
11049 ///
11050 /// # Arguments
11051 /// * `obj` - which object the method should be called on
11052 /// * must be valid
11053 /// * must not be null
11054 /// * must not be already garbage collected
11055 ///
11056 /// * `methodID` - method id of the method
11057 /// * must not be null
11058 /// * must be valid
11059 /// * must not be a static
11060 /// * must actually be a method of `obj`
11061 /// * must refer to a method with 1 arguments
11062 ///
11063 /// # Returns
11064 /// Whatever the method returned or 0 if it threw
11065 ///
11066 /// # Throws Java Exception
11067 /// * Whatever the method threw
11068 ///
11069 ///
11070 /// # Panics
11071 /// if asserts feature is enabled and UB was detected
11072 ///
11073 /// # Safety
11074 ///
11075 /// Current thread must not be detached from JNI.
11076 ///
11077 /// Current thread must not be currently throwing an exception.
11078 ///
11079 /// Current thread does not hold a critical reference.
11080 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11081 ///
11082 /// `obj` must a valid and not already garbage collected.
11083 /// `methodID` must be valid, non-static and actually be a method of `obj`, return short and have 1 parameter
11084 /// The parameter types must exactly match the java method parameters.
11085 ///
11086 pub unsafe fn CallShortMethod1<A: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A) -> jshort {
11087 unsafe {
11088 #[cfg(feature = "asserts")]
11089 {
11090 self.check_not_critical("CallShortMethod");
11091 self.check_no_exception("CallShortMethod");
11092 self.check_return_type_object("CallShortMethod", obj, methodID, "short");
11093 self.check_parameter_types_object("CallShortMethod", obj, methodID, arg1, 0, 1);
11094 }
11095 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jshort>(46)(self.vtable, obj, methodID, arg1)
11096 }
11097 }
11098
11099 ///
11100 /// Calls a non-static java method that has 2 arguments and returns short
11101 ///
11102 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11103 ///
11104 ///
11105 /// # Arguments
11106 /// * `obj` - which object the method should be called on
11107 /// * must be valid
11108 /// * must not be null
11109 /// * must not be already garbage collected
11110 ///
11111 /// * `methodID` - method id of the method
11112 /// * must not be null
11113 /// * must be valid
11114 /// * must not be a static
11115 /// * must actually be a method of `obj`
11116 /// * must refer to a method with 2 arguments
11117 ///
11118 /// # Returns
11119 /// Whatever the method returned or 0 if it threw
11120 ///
11121 /// # Throws Java Exception
11122 /// * Whatever the method threw
11123 ///
11124 ///
11125 /// # Panics
11126 /// if asserts feature is enabled and UB was detected
11127 ///
11128 /// # Safety
11129 ///
11130 /// Current thread must not be detached from JNI.
11131 ///
11132 /// Current thread must not be currently throwing an exception.
11133 ///
11134 /// Current thread does not hold a critical reference.
11135 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11136 ///
11137 /// `obj` must a valid and not already garbage collected.
11138 /// `methodID` must be valid, non-static and actually be a method of `obj`, return short and have 2 parameter
11139 /// The parameter types must exactly match the java method parameters.
11140 ///
11141 pub unsafe fn CallShortMethod2<A: JType, B: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B) -> jshort {
11142 unsafe {
11143 #[cfg(feature = "asserts")]
11144 {
11145 self.check_not_critical("CallShortMethod");
11146 self.check_no_exception("CallShortMethod");
11147 self.check_return_type_object("CallShortMethod", obj, methodID, "short");
11148 self.check_parameter_types_object("CallShortMethod", obj, methodID, arg1, 0, 2);
11149 self.check_parameter_types_object("CallShortMethod", obj, methodID, arg2, 1, 2);
11150 }
11151 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jshort>(46)(self.vtable, obj, methodID, arg1, arg2)
11152 }
11153 }
11154
11155 ///
11156 /// Calls a non-static java method that has 3 arguments and returns short
11157 ///
11158 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11159 ///
11160 ///
11161 /// # Arguments
11162 /// * `obj` - which object the method should be called on
11163 /// * must be valid
11164 /// * must not be null
11165 /// * must not be already garbage collected
11166 ///
11167 /// * `methodID` - method id of the method
11168 /// * must not be null
11169 /// * must be valid
11170 /// * must not be a static
11171 /// * must actually be a method of `obj`
11172 /// * must refer to a method with 3 arguments
11173 ///
11174 /// # Returns
11175 /// Whatever the method returned or 0 if it threw
11176 ///
11177 /// # Throws Java Exception
11178 /// * Whatever the method threw
11179 ///
11180 ///
11181 /// # Panics
11182 /// if asserts feature is enabled and UB was detected
11183 ///
11184 /// # Safety
11185 ///
11186 /// Current thread must not be detached from JNI.
11187 ///
11188 /// Current thread must not be currently throwing an exception.
11189 ///
11190 /// Current thread does not hold a critical reference.
11191 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11192 ///
11193 /// `obj` must a valid and not already garbage collected.
11194 /// `methodID` must be valid, non-static and actually be a method of `obj`, return short and have 3 parameter
11195 /// The parameter types must exactly match the java method parameters.
11196 ///
11197 pub unsafe fn CallShortMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jshort {
11198 unsafe {
11199 #[cfg(feature = "asserts")]
11200 {
11201 self.check_not_critical("CallShortMethod");
11202 self.check_no_exception("CallShortMethod");
11203 self.check_return_type_object("CallShortMethod", obj, methodID, "short");
11204 self.check_parameter_types_object("CallShortMethod", obj, methodID, arg1, 0, 3);
11205 self.check_parameter_types_object("CallShortMethod", obj, methodID, arg2, 1, 3);
11206 self.check_parameter_types_object("CallShortMethod", obj, methodID, arg3, 2, 3);
11207 }
11208 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jshort>(46)(self.vtable, obj, methodID, arg1, arg2, arg3)
11209 }
11210 }
11211
11212 ///
11213 /// Calls a non-static java method that returns a int
11214 ///
11215 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11216 ///
11217 ///
11218 /// # Arguments
11219 /// * `obj` - which object the method should be called on
11220 /// * must be valid
11221 /// * must not be null
11222 /// * must not be already garbage collected
11223 ///
11224 /// * `methodID` - method id of the method
11225 /// * must not be null
11226 /// * must be valid
11227 /// * must not be a static
11228 /// * must actually be a method of `obj`
11229 ///
11230 /// * `args` - argument pointer
11231 /// * can be null if the method has no arguments
11232 /// * must not be null otherwise and point to the exact number of arguments the method expects
11233 ///
11234 /// # Returns
11235 /// Whatever the method returned or 0 if it threw
11236 ///
11237 /// # Throws Java Exception
11238 /// * Whatever the method threw
11239 ///
11240 ///
11241 /// # Panics
11242 /// if asserts feature is enabled and UB was detected
11243 ///
11244 /// # Safety
11245 ///
11246 /// Current thread must not be detached from JNI.
11247 ///
11248 /// Current thread must not be currently throwing an exception.
11249 ///
11250 /// Current thread does not hold a critical reference.
11251 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11252 ///
11253 /// `obj` must a valid and not already garbage collected.
11254 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a int
11255 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
11256 /// `args` union must contain types that match the java methods parameters.
11257 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
11258 ///
11259 pub unsafe fn CallIntMethodA(&self, obj: jobject, methodID: jmethodID, args: *const jtype) -> jint {
11260 unsafe {
11261 #[cfg(feature = "asserts")]
11262 {
11263 self.check_not_critical("CallIntMethodA");
11264 self.check_no_exception("CallIntMethodA");
11265 self.check_return_type_object("CallIntMethodA", obj, methodID, "int");
11266 }
11267 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jint>(51)(self.vtable, obj, methodID, args)
11268 }
11269 }
11270
11271 ///
11272 /// Calls a non-static java method that has 0 arguments and returns int
11273 ///
11274 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11275 ///
11276 ///
11277 /// # Arguments
11278 /// * `obj` - which object the method should be called on
11279 /// * must be valid
11280 /// * must not be null
11281 /// * must not be already garbage collected
11282 ///
11283 /// * `methodID` - method id of the method
11284 /// * must not be null
11285 /// * must be valid
11286 /// * must not be a static
11287 /// * must actually be a method of `obj`
11288 /// * must refer to a method with 0 arguments
11289 ///
11290 /// # Returns
11291 /// Whatever the method returned or 0 if it threw
11292 ///
11293 /// # Throws Java Exception
11294 /// * Whatever the method threw
11295 ///
11296 ///
11297 /// # Panics
11298 /// if asserts feature is enabled and UB was detected
11299 ///
11300 /// # Safety
11301 ///
11302 /// Current thread must not be detached from JNI.
11303 ///
11304 /// Current thread must not be currently throwing an exception.
11305 ///
11306 /// Current thread does not hold a critical reference.
11307 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11308 ///
11309 /// `obj` must a valid and not already garbage collected.
11310 /// `methodID` must be valid, non-static and actually be a method of `obj`, return int and have no parameters
11311 ///
11312 pub unsafe fn CallIntMethod0(&self, obj: jobject, methodID: jmethodID) -> jint {
11313 unsafe {
11314 #[cfg(feature = "asserts")]
11315 {
11316 self.check_not_critical("CallIntMethod");
11317 self.check_no_exception("CallIntMethod");
11318 self.check_return_type_object("CallIntMethod", obj, methodID, "int");
11319 }
11320 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jint>(49)(self.vtable, obj, methodID)
11321 }
11322 }
11323
11324 ///
11325 /// Calls a non-static java method that has 1 arguments and returns int
11326 ///
11327 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11328 ///
11329 ///
11330 /// # Arguments
11331 /// * `obj` - which object the method should be called on
11332 /// * must be valid
11333 /// * must not be null
11334 /// * must not be already garbage collected
11335 ///
11336 /// * `methodID` - method id of the method
11337 /// * must not be null
11338 /// * must be valid
11339 /// * must not be a static
11340 /// * must actually be a method of `obj`
11341 /// * must refer to a method with 1 arguments
11342 ///
11343 /// # Returns
11344 /// Whatever the method returned or 0 if it threw
11345 ///
11346 /// # Throws Java Exception
11347 /// * Whatever the method threw
11348 ///
11349 ///
11350 /// # Panics
11351 /// if asserts feature is enabled and UB was detected
11352 ///
11353 /// # Safety
11354 ///
11355 /// Current thread must not be detached from JNI.
11356 ///
11357 /// Current thread must not be currently throwing an exception.
11358 ///
11359 /// Current thread does not hold a critical reference.
11360 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11361 ///
11362 /// `obj` must a valid and not already garbage collected.
11363 /// `methodID` must be valid, non-static and actually be a method of `obj`, return int and have 1 parameter
11364 /// The parameter types must exactly match the java method parameters.
11365 ///
11366 pub unsafe fn CallIntMethod1<A: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A) -> jint {
11367 unsafe {
11368 #[cfg(feature = "asserts")]
11369 {
11370 self.check_not_critical("CallIntMethod");
11371 self.check_no_exception("CallIntMethod");
11372 self.check_return_type_object("CallIntMethod", obj, methodID, "int");
11373 self.check_parameter_types_object("CallIntMethod", obj, methodID, arg1, 0, 1);
11374 }
11375 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jint>(49)(self.vtable, obj, methodID, arg1)
11376 }
11377 }
11378
11379 ///
11380 /// Calls a non-static java method that has 2 arguments and returns int
11381 ///
11382 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11383 ///
11384 ///
11385 /// # Arguments
11386 /// * `obj` - which object the method should be called on
11387 /// * must be valid
11388 /// * must not be null
11389 /// * must not be already garbage collected
11390 ///
11391 /// * `methodID` - method id of the method
11392 /// * must not be null
11393 /// * must be valid
11394 /// * must not be a static
11395 /// * must actually be a method of `obj`
11396 /// * must refer to a method with 2 arguments
11397 ///
11398 /// # Returns
11399 /// Whatever the method returned or 0 if it threw
11400 ///
11401 /// # Throws Java Exception
11402 /// * Whatever the method threw
11403 ///
11404 ///
11405 /// # Panics
11406 /// if asserts feature is enabled and UB was detected
11407 ///
11408 /// # Safety
11409 ///
11410 /// Current thread must not be detached from JNI.
11411 ///
11412 /// Current thread must not be currently throwing an exception.
11413 ///
11414 /// Current thread does not hold a critical reference.
11415 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11416 ///
11417 /// `obj` must a valid and not already garbage collected.
11418 /// `methodID` must be valid, non-static and actually be a method of `obj`, return int and have 2 parameter
11419 /// The parameter types must exactly match the java method parameters.
11420 ///
11421 pub unsafe fn CallIntMethod2<A: JType, B: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B) -> jint {
11422 unsafe {
11423 #[cfg(feature = "asserts")]
11424 {
11425 self.check_not_critical("CallIntMethod");
11426 self.check_no_exception("CallIntMethod");
11427 self.check_return_type_object("CallIntMethod", obj, methodID, "int");
11428 self.check_parameter_types_object("CallIntMethod", obj, methodID, arg1, 0, 2);
11429 self.check_parameter_types_object("CallIntMethod", obj, methodID, arg2, 1, 2);
11430 }
11431 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jint>(49)(self.vtable, obj, methodID, arg1, arg2)
11432 }
11433 }
11434
11435 ///
11436 /// Calls a non-static java method that has 3 arguments and returns int
11437 ///
11438 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11439 ///
11440 ///
11441 /// # Arguments
11442 /// * `obj` - which object the method should be called on
11443 /// * must be valid
11444 /// * must not be null
11445 /// * must not be already garbage collected
11446 /// * `methodID` - method id of the method
11447 /// * must not be null
11448 /// * must be valid
11449 /// * must not be a static
11450 /// * must actually be a method of `obj`
11451 /// * must refer to a method with 3 arguments
11452 ///
11453 /// # Returns
11454 /// Whatever the method returned or 0 if it threw
11455 ///
11456 /// # Throws Java Exception
11457 /// * Whatever the method threw
11458 ///
11459 ///
11460 /// # Panics
11461 /// if asserts feature is enabled and UB was detected
11462 ///
11463 /// # Safety
11464 ///
11465 /// Current thread must not be detached from JNI.
11466 ///
11467 /// Current thread must not be currently throwing an exception.
11468 ///
11469 /// Current thread does not hold a critical reference.
11470 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11471 ///
11472 /// `obj` must a valid and not already garbage collected.
11473 /// `methodID` must be valid, non-static and actually be a method of `obj`, return int and have 3 parameter
11474 /// The parameter types must exactly match the java method parameters.
11475 ///
11476 pub unsafe fn CallIntMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jint {
11477 unsafe {
11478 #[cfg(feature = "asserts")]
11479 {
11480 self.check_not_critical("CallIntMethod");
11481 self.check_no_exception("CallIntMethod");
11482 self.check_return_type_object("CallIntMethod", obj, methodID, "int");
11483 self.check_parameter_types_object("CallIntMethod", obj, methodID, arg1, 0, 3);
11484 self.check_parameter_types_object("CallIntMethod", obj, methodID, arg2, 1, 3);
11485 self.check_parameter_types_object("CallIntMethod", obj, methodID, arg3, 2, 3);
11486 }
11487 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jint>(49)(self.vtable, obj, methodID, arg1, arg2, arg3)
11488 }
11489 }
11490
11491 ///
11492 /// Calls a non-static java method that returns a long
11493 ///
11494 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11495 ///
11496 ///
11497 /// # Arguments
11498 /// * `obj` - which object the method should be called on
11499 /// * must be valid
11500 /// * must not be null
11501 /// * must not be already garbage collected
11502 /// * `methodID` - method id of the method
11503 /// * must not be null
11504 /// * must be valid
11505 /// * must not be a static
11506 /// * must actually be a method of `obj`
11507 /// * `args` - argument pointer
11508 /// * can be null if the method has no arguments
11509 /// * must not be null otherwise and point to the exact number of arguments the method expects
11510 ///
11511 /// # Returns
11512 /// Whatever the method returned or 0 if it threw
11513 ///
11514 /// # Throws Java Exception
11515 /// * Whatever the method threw
11516 ///
11517 ///
11518 /// # Panics
11519 /// if asserts feature is enabled and UB was detected
11520 ///
11521 /// # Safety
11522 ///
11523 /// Current thread must not be detached from JNI.
11524 ///
11525 /// Current thread must not be currently throwing an exception.
11526 ///
11527 /// Current thread does not hold a critical reference.
11528 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11529 ///
11530 /// `obj` must a valid and not already garbage collected.
11531 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a long
11532 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
11533 /// `args` union must contain types that match the java methods parameters.
11534 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
11535 ///
11536 pub unsafe fn CallLongMethodA(&self, obj: jobject, methodID: jmethodID, args: *const jtype) -> jlong {
11537 unsafe {
11538 #[cfg(feature = "asserts")]
11539 {
11540 self.check_not_critical("CallLongMethodA");
11541 self.check_no_exception("CallLongMethodA");
11542 self.check_return_type_object("CallLongMethodA", obj, methodID, "long");
11543 }
11544 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jlong>(54)(self.vtable, obj, methodID, args)
11545 }
11546 }
11547
11548 ///
11549 /// Calls a non-static java method that has 0 arguments and returns long
11550 ///
11551 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11552 ///
11553 ///
11554 /// # Arguments
11555 /// * `obj` - which object the method should be called on
11556 /// * must be valid
11557 /// * must not be null
11558 /// * must not be already garbage collected
11559 /// * `methodID` - method id of the method
11560 /// * must not be null
11561 /// * must be valid
11562 /// * must not be a static
11563 /// * must actually be a method of `obj`
11564 /// * must refer to a method with 0 arguments
11565 ///
11566 /// # Returns
11567 /// Whatever the method returned or 0 if it threw
11568 ///
11569 /// # Throws Java Exception
11570 /// * Whatever the method threw
11571 ///
11572 ///
11573 /// # Panics
11574 /// if asserts feature is enabled and UB was detected
11575 ///
11576 /// # Safety
11577 ///
11578 /// Current thread must not be detached from JNI.
11579 ///
11580 /// Current thread must not be currently throwing an exception.
11581 ///
11582 /// Current thread does not hold a critical reference.
11583 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11584 ///
11585 /// `obj` must a valid and not already garbage collected.
11586 /// `methodID` must be valid, non-static and actually be a method of `obj`, return long and have no parameters
11587 ///
11588 pub unsafe fn CallLongMethod0(&self, obj: jobject, methodID: jmethodID) -> jlong {
11589 unsafe {
11590 #[cfg(feature = "asserts")]
11591 {
11592 self.check_not_critical("CallLongMethod");
11593 self.check_no_exception("CallLongMethod");
11594 self.check_return_type_object("CallLongMethod", obj, methodID, "long");
11595 }
11596 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jlong>(52)(self.vtable, obj, methodID)
11597 }
11598 }
11599
11600 ///
11601 /// Calls a non-static java method that has 1 arguments and returns long
11602 ///
11603 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11604 ///
11605 ///
11606 /// # Arguments
11607 /// * `obj` - which object the method should be called on
11608 /// * must be valid
11609 /// * must not be null
11610 /// * must not be already garbage collected
11611 /// * `methodID` - method id of the method
11612 /// * must not be null
11613 /// * must be valid
11614 /// * must not be a static
11615 /// * must actually be a method of `obj`
11616 /// * must refer to a method with 1 arguments
11617 ///
11618 /// # Returns
11619 /// Whatever the method returned or 0 if it threw
11620 ///
11621 /// # Throws Java Exception
11622 /// * Whatever the method threw
11623 ///
11624 ///
11625 /// # Panics
11626 /// if asserts feature is enabled and UB was detected
11627 ///
11628 /// # Safety
11629 ///
11630 /// Current thread must not be detached from JNI.
11631 ///
11632 /// Current thread must not be currently throwing an exception.
11633 ///
11634 /// Current thread does not hold a critical reference.
11635 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11636 ///
11637 /// `obj` must a valid and not already garbage collected.
11638 /// `methodID` must be valid, non-static and actually be a method of `obj`, return long and have 1 parameter
11639 /// The parameter types must exactly match the java method parameters.
11640 ///
11641 pub unsafe fn CallLongMethod1<A: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A) -> jlong {
11642 unsafe {
11643 #[cfg(feature = "asserts")]
11644 {
11645 self.check_not_critical("CallLongMethod");
11646 self.check_no_exception("CallLongMethod");
11647 self.check_return_type_object("CallLongMethod", obj, methodID, "long");
11648 self.check_parameter_types_object("CallLongMethod", obj, methodID, arg1, 0, 1);
11649 }
11650 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jlong>(52)(self.vtable, obj, methodID, arg1)
11651 }
11652 }
11653
11654 ///
11655 /// Calls a non-static java method that has 2 arguments and returns long
11656 ///
11657 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11658 ///
11659 ///
11660 /// # Arguments
11661 /// * `obj` - which object the method should be called on
11662 /// * must be valid
11663 /// * must not be null
11664 /// * must not be already garbage collected
11665 /// * `methodID` - method id of the method
11666 /// * must not be null
11667 /// * must be valid
11668 /// * must not be a static
11669 /// * must actually be a method of `obj`
11670 /// * must refer to a method with 2 arguments
11671 ///
11672 /// # Returns
11673 /// Whatever the method returned or 0 if it threw
11674 ///
11675 /// # Throws Java Exception
11676 /// * Whatever the method threw
11677 ///
11678 ///
11679 /// # Panics
11680 /// if asserts feature is enabled and UB was detected
11681 ///
11682 /// # Safety
11683 ///
11684 /// Current thread must not be detached from JNI.
11685 ///
11686 /// Current thread must not be currently throwing an exception.
11687 ///
11688 /// Current thread does not hold a critical reference.
11689 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11690 ///
11691 /// `obj` must a valid and not already garbage collected.
11692 /// `methodID` must be valid, non-static and actually be a method of `obj`, return long and have 2 parameter
11693 /// The parameter types must exactly match the java method parameters.
11694 ///
11695 pub unsafe fn CallLongMethod2<A: JType, B: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B) -> jlong {
11696 unsafe {
11697 #[cfg(feature = "asserts")]
11698 {
11699 self.check_not_critical("CallLongMethod");
11700 self.check_no_exception("CallLongMethod");
11701 self.check_return_type_object("CallLongMethod", obj, methodID, "long");
11702 self.check_parameter_types_object("CallLongMethod", obj, methodID, arg1, 0, 2);
11703 self.check_parameter_types_object("CallLongMethod", obj, methodID, arg2, 1, 2);
11704 }
11705 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jlong>(52)(self.vtable, obj, methodID, arg1, arg2)
11706 }
11707 }
11708
11709 ///
11710 /// Calls a non-static java method that has 3 arguments and returns long
11711 ///
11712 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11713 ///
11714 ///
11715 /// # Arguments
11716 /// * `obj` - which object the method should be called on
11717 /// * must be valid
11718 /// * must not be null
11719 /// * must not be already garbage collected
11720 /// * `methodID` - method id of the method
11721 /// * must not be null
11722 /// * must be valid
11723 /// * must not be a static
11724 /// * must actually be a method of `obj`
11725 /// * must refer to a method with 3 arguments
11726 ///
11727 /// # Returns
11728 /// Whatever the method returned or 0 if it threw
11729 ///
11730 /// # Throws Java Exception
11731 /// * Whatever the method threw
11732 ///
11733 ///
11734 /// # Panics
11735 /// if asserts feature is enabled and UB was detected
11736 ///
11737 /// # Safety
11738 ///
11739 /// Current thread must not be detached from JNI.
11740 ///
11741 /// Current thread must not be currently throwing an exception.
11742 ///
11743 /// Current thread does not hold a critical reference.
11744 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11745 ///
11746 /// `obj` must a valid and not already garbage collected.
11747 /// `methodID` must be valid, non-static and actually be a method of `obj`, return long and have 3 parameter
11748 /// The parameter types must exactly match the java method parameters.
11749 ///
11750 pub unsafe fn CallLongMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jlong {
11751 unsafe {
11752 #[cfg(feature = "asserts")]
11753 {
11754 self.check_not_critical("CallLongMethod");
11755 self.check_no_exception("CallLongMethod");
11756 self.check_return_type_object("CallLongMethod", obj, methodID, "long");
11757 self.check_parameter_types_object("CallLongMethod", obj, methodID, arg1, 0, 3);
11758 self.check_parameter_types_object("CallLongMethod", obj, methodID, arg2, 1, 3);
11759 self.check_parameter_types_object("CallLongMethod", obj, methodID, arg3, 2, 3);
11760 }
11761 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jlong>(52)(self.vtable, obj, methodID, arg1, arg2, arg3)
11762 }
11763 }
11764
11765 ///
11766 /// Calls a non-static java method that returns a float
11767 ///
11768 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11769 ///
11770 ///
11771 /// # Arguments
11772 /// * `obj` - which object the method should be called on
11773 /// * must be valid
11774 /// * must not be null
11775 /// * must not be already garbage collected
11776 /// * `methodID` - method id of the method
11777 /// * must not be null
11778 /// * must be valid
11779 /// * must not be a static
11780 /// * must actually be a method of `obj`
11781 /// * `args` - argument pointer
11782 /// * can be null if the method has no arguments
11783 /// * must not be null otherwise and point to the exact number of arguments the method expects
11784 ///
11785 /// # Returns
11786 /// Whatever the method returned or 0 if it threw
11787 ///
11788 /// # Throws Java Exception
11789 /// * Whatever the method threw
11790 ///
11791 ///
11792 /// # Panics
11793 /// if asserts feature is enabled and UB was detected
11794 ///
11795 /// # Safety
11796 ///
11797 /// Current thread must not be detached from JNI.
11798 ///
11799 /// Current thread must not be currently throwing an exception.
11800 ///
11801 /// Current thread does not hold a critical reference.
11802 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11803 ///
11804 /// `obj` must a valid and not already garbage collected.
11805 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a float
11806 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
11807 /// `args` union must contain types that match the java methods parameters.
11808 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
11809 ///
11810 pub unsafe fn CallFloatMethodA(&self, obj: jobject, methodID: jmethodID, args: *const jtype) -> jfloat {
11811 unsafe {
11812 #[cfg(feature = "asserts")]
11813 {
11814 self.check_not_critical("CallFloatMethodA");
11815 self.check_no_exception("CallFloatMethodA");
11816 self.check_return_type_object("CallFloatMethodA", obj, methodID, "float");
11817 }
11818 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jfloat>(57)(self.vtable, obj, methodID, args)
11819 }
11820 }
11821
11822 ///
11823 /// Calls a non-static java method that has 0 arguments and returns float
11824 ///
11825 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11826 ///
11827 ///
11828 /// # Arguments
11829 /// * `obj` - which object the method should be called on
11830 /// * must be valid
11831 /// * must not be null
11832 /// * must not be already garbage collected
11833 /// * `methodID` - method id of the method
11834 /// * must not be null
11835 /// * must be valid
11836 /// * must not be a static
11837 /// * must actually be a method of `obj`
11838 /// * must refer to a method with 0 arguments
11839 ///
11840 /// # Returns
11841 /// Whatever the method returned or 0 if it threw
11842 ///
11843 /// # Throws Java Exception
11844 /// * Whatever the method threw
11845 ///
11846 ///
11847 /// # Panics
11848 /// if asserts feature is enabled and UB was detected
11849 ///
11850 /// # Safety
11851 ///
11852 /// Current thread must not be detached from JNI.
11853 ///
11854 /// Current thread must not be currently throwing an exception.
11855 ///
11856 /// Current thread does not hold a critical reference.
11857 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11858 ///
11859 /// `obj` must a valid and not already garbage collected.
11860 /// `methodID` must be valid, non-static and actually be a method of `obj`, return float and have no parameters
11861 ///
11862 pub unsafe fn CallFloatMethod0(&self, obj: jobject, methodID: jmethodID) -> jfloat {
11863 unsafe {
11864 #[cfg(feature = "asserts")]
11865 {
11866 self.check_not_critical("CallFloatMethod");
11867 self.check_no_exception("CallFloatMethod");
11868 self.check_return_type_object("CallFloatMethod", obj, methodID, "float");
11869 }
11870 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jfloat>(55)(self.vtable, obj, methodID)
11871 }
11872 }
11873
11874 ///
11875 /// Calls a non-static java method that has 1 arguments and returns float
11876 ///
11877 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11878 ///
11879 ///
11880 /// # Arguments
11881 /// * `obj` - which object the method should be called on
11882 /// * must be valid
11883 /// * must not be null
11884 /// * must not be already garbage collected
11885 /// * `methodID` - method id of the method
11886 /// * must not be null
11887 /// * must be valid
11888 /// * must not be a static
11889 /// * must actually be a method of `obj`
11890 /// * must refer to a method with 1 arguments
11891 ///
11892 /// # Returns
11893 /// Whatever the method returned or 0 if it threw
11894 ///
11895 /// # Throws Java Exception
11896 /// * Whatever the method threw
11897 ///
11898 ///
11899 /// # Panics
11900 /// if asserts feature is enabled and UB was detected
11901 ///
11902 /// # Safety
11903 ///
11904 /// Current thread must not be detached from JNI.
11905 ///
11906 /// Current thread must not be currently throwing an exception.
11907 ///
11908 /// Current thread does not hold a critical reference.
11909 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11910 ///
11911 /// `obj` must a valid and not already garbage collected.
11912 /// `methodID` must be valid, non-static and actually be a method of `obj`, return float and have 1 parameter
11913 /// The parameter types must exactly match the java method parameters.
11914 ///
11915 pub unsafe fn CallFloatMethod1<A: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A) -> jfloat {
11916 unsafe {
11917 #[cfg(feature = "asserts")]
11918 {
11919 self.check_not_critical("CallFloatMethod");
11920 self.check_no_exception("CallFloatMethod");
11921 self.check_return_type_object("CallFloatMethod", obj, methodID, "float");
11922 self.check_parameter_types_object("CallFloatMethod", obj, methodID, arg1, 0, 1);
11923 }
11924 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jfloat>(55)(self.vtable, obj, methodID, arg1)
11925 }
11926 }
11927
11928 ///
11929 /// Calls a non-static java method that has 2 arguments and returns float
11930 ///
11931 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11932 ///
11933 ///
11934 /// # Arguments
11935 /// * `obj` - which object the method should be called on
11936 /// * must be valid
11937 /// * must not be null
11938 /// * must not be already garbage collected
11939 /// * `methodID` - method id of the method
11940 /// * must not be null
11941 /// * must be valid
11942 /// * must not be a static
11943 /// * must actually be a method of `obj`
11944 /// * must refer to a method with 2 arguments
11945 ///
11946 /// # Returns
11947 /// Whatever the method returned or 0 if it threw
11948 ///
11949 /// # Throws Java Exception
11950 /// * Whatever the method threw
11951 ///
11952 ///
11953 /// # Panics
11954 /// if asserts feature is enabled and UB was detected
11955 ///
11956 /// # Safety
11957 ///
11958 /// Current thread must not be detached from JNI.
11959 ///
11960 /// Current thread must not be currently throwing an exception.
11961 ///
11962 /// Current thread does not hold a critical reference.
11963 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
11964 ///
11965 /// `obj` must a valid and not already garbage collected.
11966 /// `methodID` must be valid, non-static and actually be a method of `obj`, return float and have 2 parameter
11967 /// The parameter types must exactly match the java method parameters.
11968 ///
11969 pub unsafe fn CallFloatMethod2<A: JType, B: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B) -> jfloat {
11970 unsafe {
11971 #[cfg(feature = "asserts")]
11972 {
11973 self.check_not_critical("CallFloatMethod");
11974 self.check_no_exception("CallFloatMethod");
11975 self.check_return_type_object("CallFloatMethod", obj, methodID, "float");
11976 self.check_parameter_types_object("CallFloatMethod", obj, methodID, arg1, 0, 2);
11977 self.check_parameter_types_object("CallFloatMethod", obj, methodID, arg2, 1, 2);
11978 }
11979 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jfloat>(55)(self.vtable, obj, methodID, arg1, arg2)
11980 }
11981 }
11982
11983 ///
11984 /// Calls a non-static java method that has 3 arguments and returns float
11985 ///
11986 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
11987 ///
11988 ///
11989 /// # Arguments
11990 /// * `obj` - which object the method should be called on
11991 /// * must be valid
11992 /// * must not be null
11993 /// * must not be already garbage collected
11994 /// * `methodID` - method id of the method
11995 /// * must not be null
11996 /// * must be valid
11997 /// * must not be a static
11998 /// * must actually be a method of `obj`
11999 /// * must refer to a method with 3 arguments
12000 ///
12001 /// # Returns
12002 /// Whatever the method returned or 0 if it threw
12003 ///
12004 /// # Throws Java Exception
12005 /// * Whatever the method threw
12006 ///
12007 ///
12008 /// # Panics
12009 /// if asserts feature is enabled and UB was detected
12010 ///
12011 /// # Safety
12012 ///
12013 /// Current thread must not be detached from JNI.
12014 ///
12015 /// Current thread must not be currently throwing an exception.
12016 ///
12017 /// Current thread does not hold a critical reference.
12018 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12019 ///
12020 /// `obj` must a valid and not already garbage collected.
12021 /// `methodID` must be valid, non-static and actually be a method of `obj`, return float and have 3 parameter
12022 /// The parameter types must exactly match the java method parameters.
12023 ///
12024 pub unsafe fn CallFloatMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jfloat {
12025 unsafe {
12026 #[cfg(feature = "asserts")]
12027 {
12028 self.check_not_critical("CallFloatMethod");
12029 self.check_no_exception("CallFloatMethod");
12030 self.check_return_type_object("CallFloatMethod", obj, methodID, "float");
12031 self.check_parameter_types_object("CallFloatMethod", obj, methodID, arg1, 0, 3);
12032 self.check_parameter_types_object("CallFloatMethod", obj, methodID, arg2, 1, 3);
12033 self.check_parameter_types_object("CallFloatMethod", obj, methodID, arg3, 2, 3);
12034 }
12035 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jfloat>(55)(self.vtable, obj, methodID, arg1, arg2, arg3)
12036 }
12037 }
12038
12039 ///
12040 /// Calls a non-static java method that returns a double
12041 ///
12042 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
12043 ///
12044 ///
12045 /// # Arguments
12046 /// * `obj` - which object the method should be called on
12047 /// * must be valid
12048 /// * must not be null
12049 /// * must not be already garbage collected
12050 /// * `methodID` - method id of the method
12051 /// * must not be null
12052 /// * must be valid
12053 /// * must not be a static
12054 /// * must actually be a method of `obj`
12055 /// * `args` - argument pointer
12056 /// * can be null if the method has no arguments
12057 /// * must not be null otherwise and point to the exact number of arguments the method expects
12058 ///
12059 /// # Returns
12060 /// Whatever the method returned or 0 if it threw
12061 ///
12062 /// # Throws Java Exception
12063 /// * Whatever the method threw
12064 ///
12065 ///
12066 /// # Panics
12067 /// if asserts feature is enabled and UB was detected
12068 ///
12069 /// # Safety
12070 ///
12071 /// Current thread must not be detached from JNI.
12072 ///
12073 /// Current thread must not be currently throwing an exception.
12074 ///
12075 /// Current thread does not hold a critical reference.
12076 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12077 ///
12078 /// `obj` must a valid and not already garbage collected.
12079 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a double
12080 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
12081 /// `args` union must contain types that match the java methods parameters.
12082 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
12083 ///
12084 pub unsafe fn CallDoubleMethodA(&self, obj: jobject, methodID: jmethodID, args: *const jtype) -> jdouble {
12085 unsafe {
12086 #[cfg(feature = "asserts")]
12087 {
12088 self.check_not_critical("CallDoubleMethodA");
12089 self.check_no_exception("CallDoubleMethodA");
12090 self.check_return_type_object("CallDoubleMethodA", obj, methodID, "double");
12091 }
12092 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jdouble>(60)(self.vtable, obj, methodID, args)
12093 }
12094 }
12095
12096 ///
12097 /// Calls a non-static java method that has 0 arguments and returns double
12098 ///
12099 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
12100 ///
12101 ///
12102 /// # Arguments
12103 /// * `obj` - which object the method should be called on
12104 /// * must be valid
12105 /// * must not be null
12106 /// * must not be already garbage collected
12107 /// * `methodID` - method id of the method
12108 /// * must not be null
12109 /// * must be valid
12110 /// * must not be a static
12111 /// * must actually be a method of `obj`
12112 /// * must refer to a method with 0 arguments
12113 ///
12114 /// # Returns
12115 /// Whatever the method returned or 0 if it threw
12116 ///
12117 /// # Throws Java Exception
12118 /// * Whatever the method threw
12119 ///
12120 ///
12121 /// # Panics
12122 /// if asserts feature is enabled and UB was detected
12123 ///
12124 /// # Safety
12125 ///
12126 /// Current thread must not be detached from JNI.
12127 ///
12128 /// Current thread must not be currently throwing an exception.
12129 ///
12130 /// Current thread does not hold a critical reference.
12131 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12132 ///
12133 /// `obj` must a valid and not already garbage collected.
12134 /// `methodID` must be valid, non-static and actually be a method of `obj`, return double and have no parameters
12135 ///
12136 pub unsafe fn CallDoubleMethod0(&self, obj: jobject, methodID: jmethodID) -> jdouble {
12137 unsafe {
12138 #[cfg(feature = "asserts")]
12139 {
12140 self.check_not_critical("CallDoubleMethod");
12141 self.check_no_exception("CallDoubleMethod");
12142 self.check_return_type_object("CallDoubleMethod", obj, methodID, "double");
12143 }
12144 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jdouble>(58)(self.vtable, obj, methodID)
12145 }
12146 }
12147
12148 ///
12149 /// Calls a non-static java method that has 1 arguments and returns double
12150 ///
12151 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
12152 ///
12153 ///
12154 /// # Arguments
12155 /// * `obj` - which object the method should be called on
12156 /// * must be valid
12157 /// * must not be null
12158 /// * must not be already garbage collected
12159 /// * `methodID` - method id of the method
12160 /// * must not be null
12161 /// * must be valid
12162 /// * must not be a static
12163 /// * must actually be a method of `obj`
12164 /// * must refer to a method with 1 arguments
12165 ///
12166 /// # Returns
12167 /// Whatever the method returned or 0 if it threw
12168 ///
12169 /// # Throws Java Exception
12170 /// * Whatever the method threw
12171 ///
12172 ///
12173 /// # Panics
12174 /// if asserts feature is enabled and UB was detected
12175 ///
12176 /// # Safety
12177 ///
12178 /// Current thread must not be detached from JNI.
12179 ///
12180 /// Current thread must not be currently throwing an exception.
12181 ///
12182 /// Current thread does not hold a critical reference.
12183 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12184 ///
12185 /// `obj` must a valid and not already garbage collected.
12186 /// `methodID` must be valid, non-static and actually be a method of `obj`, return double and have 1 parameter
12187 /// The parameter types must exactly match the java method parameters.
12188 ///
12189 pub unsafe fn CallDoubleMethod1<A: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A) -> jdouble {
12190 unsafe {
12191 #[cfg(feature = "asserts")]
12192 {
12193 self.check_not_critical("CallDoubleMethod");
12194 self.check_no_exception("CallDoubleMethod");
12195 self.check_return_type_object("CallDoubleMethod", obj, methodID, "double");
12196 self.check_parameter_types_object("CallDoubleMethod", obj, methodID, arg1, 0, 1);
12197 }
12198 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jdouble>(58)(self.vtable, obj, methodID, arg1)
12199 }
12200 }
12201
12202 ///
12203 /// Calls a non-static java method that has 2 arguments and returns double
12204 ///
12205 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
12206 ///
12207 ///
12208 /// # Arguments
12209 /// * `obj` - which object the method should be called on
12210 /// * must be valid
12211 /// * must not be null
12212 /// * must not be already garbage collected
12213 /// * `methodID` - method id of the method
12214 /// * must not be null
12215 /// * must be valid
12216 /// * must not be a static
12217 /// * must actually be a method of `obj`
12218 /// * must refer to a method with 2 arguments
12219 ///
12220 /// # Returns
12221 /// Whatever the method returned or 0 if it threw
12222 ///
12223 /// # Throws Java Exception
12224 /// * Whatever the method threw
12225 ///
12226 ///
12227 /// # Panics
12228 /// if asserts feature is enabled and UB was detected
12229 ///
12230 /// # Safety
12231 ///
12232 /// Current thread must not be detached from JNI.
12233 ///
12234 /// Current thread must not be currently throwing an exception.
12235 ///
12236 /// Current thread does not hold a critical reference.
12237 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12238 ///
12239 /// `obj` must a valid and not already garbage collected.
12240 /// `methodID` must be valid, non-static and actually be a method of `obj`, return double and have 2 parameter
12241 /// The parameter types must exactly match the java method parameters.
12242 ///
12243 pub unsafe fn CallDoubleMethod2<A: JType, B: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B) -> jdouble {
12244 unsafe {
12245 #[cfg(feature = "asserts")]
12246 {
12247 self.check_not_critical("CallDoubleMethod");
12248 self.check_no_exception("CallDoubleMethod");
12249 self.check_return_type_object("CallDoubleMethod", obj, methodID, "double");
12250 self.check_parameter_types_object("CallDoubleMethod", obj, methodID, arg1, 0, 2);
12251 self.check_parameter_types_object("CallDoubleMethod", obj, methodID, arg2, 1, 2);
12252 }
12253 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jdouble>(58)(self.vtable, obj, methodID, arg1, arg2)
12254 }
12255 }
12256
12257 ///
12258 /// Calls a non-static java method that has 3 arguments and returns double
12259 ///
12260 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Call_type_Method_routines>
12261 ///
12262 ///
12263 /// # Arguments
12264 /// * `obj` - which object the method should be called on
12265 /// * must be valid
12266 /// * must not be null
12267 /// * must not be already garbage collected
12268 /// * `methodID` - method id of the method
12269 /// * must not be null
12270 /// * must be valid
12271 /// * must not be a static
12272 /// * must actually be a method of `obj`
12273 /// * must refer to a method with 3 arguments
12274 ///
12275 /// # Returns
12276 /// Whatever the method returned or 0 if it threw
12277 ///
12278 /// # Throws Java Exception
12279 /// * Whatever the method threw
12280 ///
12281 ///
12282 /// # Panics
12283 /// if asserts feature is enabled and UB was detected
12284 ///
12285 /// # Safety
12286 ///
12287 /// Current thread must not be detached from JNI.
12288 ///
12289 /// Current thread must not be currently throwing an exception.
12290 ///
12291 /// Current thread does not hold a critical reference.
12292 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12293 ///
12294 /// `obj` must a valid and not already garbage collected.
12295 /// `methodID` must be valid, non-static and actually be a method of `obj`, return double and have 3 parameter
12296 /// The parameter types must exactly match the java method parameters.
12297 ///
12298 pub unsafe fn CallDoubleMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jdouble {
12299 unsafe {
12300 #[cfg(feature = "asserts")]
12301 {
12302 self.check_not_critical("CallDoubleMethod");
12303 self.check_no_exception("CallDoubleMethod");
12304 self.check_return_type_object("CallDoubleMethod", obj, methodID, "double");
12305 self.check_parameter_types_object("CallDoubleMethod", obj, methodID, arg1, 0, 3);
12306 self.check_parameter_types_object("CallDoubleMethod", obj, methodID, arg2, 1, 3);
12307 self.check_parameter_types_object("CallDoubleMethod", obj, methodID, arg3, 2, 3);
12308 }
12309 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jdouble>(58)(self.vtable, obj, methodID, arg1, arg2, arg3)
12310 }
12311 }
12312
12313 ///
12314 /// Calls a non-static java method that returns void without using the objects vtable to look up the method.
12315 /// This means that should the object be a subclass of the class that the method is declared in
12316 /// then the base method that the methodID refers to is invoked instead of a potencially overwritten one.
12317 ///
12318 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12319 ///
12320 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12321 ///
12322 ///
12323 /// # Arguments
12324 /// * `obj` - which object the method should be called on
12325 /// * must be valid
12326 /// * must not be null
12327 /// * must not be already garbage collected
12328 /// * `methodID` - method id of the method
12329 /// * must not be null
12330 /// * must be valid
12331 /// * must not be a static
12332 /// * must actually be a method of `obj`
12333 /// * `args` - argument pointer
12334 /// * can be null if the method has no arguments
12335 /// * must not be null otherwise and point to the exact number of arguments the method expects
12336 ///
12337 /// # Throws Java Exception
12338 /// * Whatever the method threw
12339 ///
12340 ///
12341 /// # Panics
12342 /// if asserts feature is enabled and UB was detected
12343 ///
12344 /// # Safety
12345 ///
12346 /// Current thread must not be detached from JNI.
12347 ///
12348 /// Current thread must not be currently throwing an exception.
12349 ///
12350 /// Current thread does not hold a critical reference.
12351 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12352 ///
12353 /// `obj` must a valid and not already garbage collected.
12354 /// `methodID` must be valid, non-static and actually be a method of `obj` and return void
12355 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
12356 /// `args` union must contain types that match the java methods parameters.
12357 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
12358 ///
12359 pub unsafe fn CallNonvirtualVoidMethodA(&self, obj: jobject, class: jclass, methodID: jmethodID, args: *const jtype) {
12360 unsafe {
12361 #[cfg(feature = "asserts")]
12362 {
12363 self.check_not_critical("CallNonvirtualVoidMethodA");
12364 self.check_no_exception("CallNonvirtualVoidMethodA");
12365 self.check_return_type_object("CallNonvirtualVoidMethodA", obj, methodID, "void");
12366 self.check_is_class("CallNonvirtualVoidMethodA", class);
12367 }
12368 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jclass, jmethodID, *const jtype)>(93)(self.vtable, obj, class, methodID, args);
12369 }
12370 }
12371
12372 ///
12373 /// Calls a non-static java method with 0 arguments that returns void without using the objects vtable to look up the method.
12374 /// This means that should the object be a subclass of the class that the method is declared in
12375 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
12376 ///
12377 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12378 ///
12379 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12380 ///
12381 ///
12382 /// # Arguments
12383 /// * `obj` - which object the method should be called on
12384 /// * must be valid
12385 /// * must not be null
12386 /// * must not be already garbage collected
12387 /// * `methodID` - method id of the method
12388 /// * must not be null
12389 /// * must be valid
12390 /// * must not be a static
12391 /// * must actually be a method of `obj`
12392 /// * must refer to a method with 0 arguments
12393 ///
12394 /// # Throws Java Exception
12395 /// * Whatever the method threw
12396 ///
12397 ///
12398 /// # Panics
12399 /// if asserts feature is enabled and UB was detected
12400 ///
12401 /// # Safety
12402 ///
12403 /// Current thread must not be detached from JNI.
12404 ///
12405 /// Current thread must not be currently throwing an exception.
12406 ///
12407 /// Current thread does not hold a critical reference.
12408 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12409 ///
12410 /// `obj` must a valid and not already garbage collected.
12411 /// `methodID` must be valid, non-static and actually be a method of `obj`, return void and have no parameters
12412 ///
12413 pub unsafe fn CallNonvirtualVoidMethod0(&self, obj: jobject, class: jclass, methodID: jmethodID) {
12414 unsafe {
12415 #[cfg(feature = "asserts")]
12416 {
12417 self.check_not_critical("CallNonvirtualVoidMethod");
12418 self.check_no_exception("CallNonvirtualVoidMethod");
12419 self.check_return_type_object("CallNonvirtualVoidMethod", obj, methodID, "void");
12420 self.check_is_class("CallNonvirtualVoidMethod", class);
12421 }
12422 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID)>(91)(self.vtable, obj, class, methodID);
12423 }
12424 }
12425
12426 ///
12427 /// Calls a non-static java method with 1 arguments that returns void without using the objects vtable to look up the method.
12428 /// This means that should the object be a subclass of the class that the method is declared in
12429 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
12430 ///
12431 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12432 ///
12433 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12434 ///
12435 ///
12436 /// # Arguments
12437 /// * `obj` - which object the method should be called on
12438 /// * must be valid
12439 /// * must not be null
12440 /// * must not be already garbage collected
12441 /// * `methodID` - method id of the method
12442 /// * must not be null
12443 /// * must be valid
12444 /// * must not be a static
12445 /// * must actually be a method of `obj`
12446 /// * must refer to a method with 1 arguments
12447 ///
12448 /// # Throws Java Exception
12449 /// * Whatever the method threw
12450 ///
12451 ///
12452 /// # Panics
12453 /// if asserts feature is enabled and UB was detected
12454 ///
12455 /// # Safety
12456 ///
12457 /// Current thread must not be detached from JNI.
12458 ///
12459 /// Current thread must not be currently throwing an exception.
12460 ///
12461 /// Current thread does not hold a critical reference.
12462 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12463 ///
12464 /// `obj` must a valid and not already garbage collected.
12465 /// `methodID` must be valid, non-static and actually be a method of `obj`, return void and have 1 argument
12466 ///
12467 pub unsafe fn CallNonvirtualVoidMethod1<A: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A) {
12468 unsafe {
12469 #[cfg(feature = "asserts")]
12470 {
12471 self.check_not_critical("CallNonvirtualVoidMethod");
12472 self.check_no_exception("CallNonvirtualVoidMethod");
12473 self.check_return_type_object("CallNonvirtualVoidMethod", obj, methodID, "void");
12474 self.check_is_class("CallNonvirtualVoidMethod", class);
12475 self.check_parameter_types_object("CallNonvirtualVoidMethod", obj, methodID, arg1, 0, 1);
12476 }
12477 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...)>(91)(self.vtable, obj, class, methodID, arg1);
12478 }
12479 }
12480
12481 ///
12482 /// Calls a non-static java method with 2 arguments that returns void without using the objects vtable to look up the method.
12483 /// This means that should the object be a subclass of the class that the method is declared in
12484 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
12485 ///
12486 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12487 ///
12488 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12489 ///
12490 ///
12491 /// # Arguments
12492 /// * `obj` - which object the method should be called on
12493 /// * must be valid
12494 /// * must not be null
12495 /// * must not be already garbage collected
12496 /// * `methodID` - method id of the method
12497 /// * must not be null
12498 /// * must be valid
12499 /// * must not be a static
12500 /// * must actually be a method of `obj`
12501 /// * must refer to a method with 2 arguments
12502 ///
12503 /// # Throws Java Exception
12504 /// * Whatever the method threw
12505 ///
12506 ///
12507 /// # Panics
12508 /// if asserts feature is enabled and UB was detected
12509 ///
12510 /// # Safety
12511 ///
12512 /// Current thread must not be detached from JNI.
12513 ///
12514 /// Current thread must not be currently throwing an exception.
12515 ///
12516 /// Current thread does not hold a critical reference.
12517 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12518 ///
12519 /// `obj` must a valid and not already garbage collected.
12520 /// `methodID` must be valid, non-static and actually be a method of `obj`, return void and have 2 arguments
12521 ///
12522 pub unsafe fn CallNonvirtualVoidMethod2<A: JType, B: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B) {
12523 unsafe {
12524 #[cfg(feature = "asserts")]
12525 {
12526 self.check_not_critical("CallNonvirtualVoidMethod");
12527 self.check_no_exception("CallNonvirtualVoidMethod");
12528 self.check_return_type_object("CallNonvirtualVoidMethod", obj, methodID, "void");
12529 self.check_is_class("CallNonvirtualVoidMethod", class);
12530 self.check_parameter_types_object("CallNonvirtualVoidMethod", obj, methodID, arg1, 0, 2);
12531 self.check_parameter_types_object("CallNonvirtualVoidMethod", obj, methodID, arg2, 1, 2);
12532 }
12533 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...)>(91)(self.vtable, obj, class, methodID, arg1, arg2);
12534 }
12535 }
12536
12537 ///
12538 /// Calls a non-static java method with 3 arguments that returns void without using the objects vtable to look up the method.
12539 /// This means that should the object be a subclass of the class that the method is declared in
12540 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
12541 ///
12542 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12543 ///
12544 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12545 ///
12546 ///
12547 /// # Arguments
12548 /// * `obj` - which object the method should be called on
12549 /// * must be valid
12550 /// * must not be null
12551 /// * must not be already garbage collected
12552 /// * `methodID` - method id of the method
12553 /// * must not be null
12554 /// * must be valid
12555 /// * must not be a static
12556 /// * must actually be a method of `obj`
12557 /// * must refer to a method with 3 arguments
12558 ///
12559 /// # Throws Java Exception
12560 /// * Whatever the method threw
12561 ///
12562 ///
12563 /// # Panics
12564 /// if asserts feature is enabled and UB was detected
12565 ///
12566 /// # Safety
12567 ///
12568 /// Current thread must not be detached from JNI.
12569 ///
12570 /// Current thread must not be currently throwing an exception.
12571 ///
12572 /// Current thread does not hold a critical reference.
12573 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12574 ///
12575 /// `obj` must a valid and not already garbage collected.
12576 /// `methodID` must be valid, non-static and actually be a method of `obj`, return void and have 3 arguments
12577 ///
12578 pub unsafe fn CallNonvirtualVoidMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) {
12579 unsafe {
12580 #[cfg(feature = "asserts")]
12581 {
12582 self.check_not_critical("CallNonvirtualVoidMethod");
12583 self.check_no_exception("CallNonvirtualVoidMethod");
12584 self.check_return_type_object("CallNonvirtualVoidMethod", obj, methodID, "void");
12585 self.check_is_class("CallNonvirtualVoidMethod", class);
12586 self.check_parameter_types_object("CallNonvirtualVoidMethod", obj, methodID, arg1, 0, 3);
12587 self.check_parameter_types_object("CallNonvirtualVoidMethod", obj, methodID, arg2, 1, 3);
12588 self.check_parameter_types_object("CallNonvirtualVoidMethod", obj, methodID, arg3, 2, 3);
12589 }
12590 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...)>(91)(self.vtable, obj, class, methodID, arg1, arg2, arg3);
12591 }
12592 }
12593
12594 ///
12595 /// Calls a non-static java method that returns object without using the objects vtable to look up the method.
12596 /// This means that should the object be a subclass of the class that the method is declared in
12597 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
12598 ///
12599 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12600 ///
12601 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12602 ///
12603 ///
12604 /// # Arguments
12605 /// * `obj` - which object the method should be called on
12606 /// * must be valid
12607 /// * must not be null
12608 /// * must not be already garbage collected
12609 /// * `methodID` - method id of the method
12610 /// * must not be null
12611 /// * must be valid
12612 /// * must not be a static
12613 /// * must actually be a method of `obj`
12614 /// * `args` - argument pointer
12615 /// * can be null if the method has no arguments
12616 /// * must not be null otherwise and point to the exact number of arguments the method expects
12617 ///
12618 /// # Returns
12619 /// Whatever the method returned or null if it threw
12620 ///
12621 /// # Throws Java Exception
12622 /// * Whatever the method threw
12623 ///
12624 ///
12625 /// # Panics
12626 /// if asserts feature is enabled and UB was detected
12627 ///
12628 /// # Safety
12629 ///
12630 /// Current thread must not be detached from JNI.
12631 ///
12632 /// Current thread must not be currently throwing an exception.
12633 ///
12634 /// Current thread does not hold a critical reference.
12635 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12636 ///
12637 /// `obj` must a valid and not already garbage collected.
12638 /// `methodID` must be valid, non-static and actually be a method of `obj` and return an object
12639 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
12640 /// `args` union must contain types that match the java methods parameters.
12641 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
12642 ///
12643 pub unsafe fn CallNonvirtualObjectMethodA(&self, obj: jobject, class: jclass, methodID: jmethodID, args: *const jtype) -> jobject {
12644 unsafe {
12645 #[cfg(feature = "asserts")]
12646 {
12647 self.check_not_critical("CallNonvirtualObjectMethodA");
12648 self.check_no_exception("CallNonvirtualObjectMethodA");
12649 self.check_return_type_object("CallNonvirtualObjectMethodA", obj, methodID, "object");
12650 self.check_is_class("CallNonvirtualObjectMethodA", class);
12651 }
12652 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jclass, jmethodID, *const jtype) -> jobject>(66)(self.vtable, obj, class, methodID, args)
12653 }
12654 }
12655
12656 ///
12657 /// Calls a non-static java method with 0 arguments that returns object without using the objects vtable to look up the method.
12658 /// This means that should the object be a subclass of the class that the method is declared in
12659 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
12660 ///
12661 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12662 ///
12663 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12664 ///
12665 ///
12666 /// # Arguments
12667 /// * `obj` - which object the method should be called on
12668 /// * must be valid
12669 /// * must not be null
12670 /// * must not be already garbage collected
12671 /// * `methodID` - method id of the method
12672 /// * must not be null
12673 /// * must be valid
12674 /// * must not be a static
12675 /// * must actually be a method of `obj`
12676 /// * must refer to a method with 0 arguments
12677 ///
12678 /// # Returns
12679 /// Whatever the method returned or null if it threw
12680 ///
12681 /// # Throws Java Exception
12682 /// * Whatever the method threw
12683 ///
12684 ///
12685 /// # Panics
12686 /// if asserts feature is enabled and UB was detected
12687 ///
12688 /// # Safety
12689 ///
12690 /// Current thread must not be detached from JNI.
12691 ///
12692 /// Current thread must not be currently throwing an exception.
12693 ///
12694 /// Current thread does not hold a critical reference.
12695 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12696 ///
12697 /// `obj` must a valid and not already garbage collected.
12698 /// `methodID` must be valid, non-static and actually be a method of `obj`, return an object and have no parameters
12699 ///
12700 pub unsafe fn CallNonvirtualObjectMethod0(&self, obj: jobject, class: jclass, methodID: jmethodID) -> jobject {
12701 unsafe {
12702 #[cfg(feature = "asserts")]
12703 {
12704 self.check_not_critical("CallNonvirtualObjectMethod");
12705 self.check_no_exception("CallNonvirtualObjectMethod");
12706 self.check_return_type_object("CallNonvirtualObjectMethod", obj, methodID, "object");
12707 self.check_is_class("CallNonvirtualObjectMethod", class);
12708 }
12709 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID) -> jobject>(64)(self.vtable, obj, class, methodID)
12710 }
12711 }
12712
12713 ///
12714 /// Calls a non-static java method with 1 arguments that returns object without using the objects vtable to look up the method.
12715 /// This means that should the object be a subclass of the class that the method is declared in
12716 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
12717 ///
12718 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12719 ///
12720 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12721 ///
12722 ///
12723 /// # Arguments
12724 /// * `obj` - which object the method should be called on
12725 /// * must be valid
12726 /// * must not be null
12727 /// * must not be already garbage collected
12728 /// * `methodID` - method id of the method
12729 /// * must not be null
12730 /// * must be valid
12731 /// * must not be a static
12732 /// * must actually be a method of `obj`
12733 /// * must refer to a method with 1 arguments
12734 ///
12735 /// # Returns
12736 /// Whatever the method returned or null if it threw
12737 ///
12738 /// # Throws Java Exception
12739 /// * Whatever the method threw
12740 ///
12741 ///
12742 /// # Panics
12743 /// if asserts feature is enabled and UB was detected
12744 ///
12745 /// # Safety
12746 ///
12747 /// Current thread must not be detached from JNI.
12748 ///
12749 /// Current thread must not be currently throwing an exception.
12750 ///
12751 /// Current thread does not hold a critical reference.
12752 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12753 ///
12754 /// `obj` must a valid and not already garbage collected.
12755 /// `methodID` must be valid, non-static and actually be a method of `obj`, return an object and have 1 arguments
12756 ///
12757 pub unsafe fn CallNonvirtualObjectMethod1<A: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A) -> jobject {
12758 unsafe {
12759 #[cfg(feature = "asserts")]
12760 {
12761 self.check_not_critical("CallNonvirtualObjectMethod");
12762 self.check_no_exception("CallNonvirtualObjectMethod");
12763 self.check_return_type_object("CallNonvirtualObjectMethod", obj, methodID, "object");
12764 self.check_is_class("CallNonvirtualObjectMethod", class);
12765 self.check_parameter_types_object("CallNonvirtualObjectMethod", obj, methodID, arg1, 0, 1);
12766 }
12767 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jobject>(64)(self.vtable, obj, class, methodID, arg1)
12768 }
12769 }
12770
12771 ///
12772 /// Calls a non-static java method with 2 arguments that returns object without using the objects vtable to look up the method.
12773 /// This means that should the object be a subclass of the class that the method is declared in
12774 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
12775 ///
12776 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12777 ///
12778 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12779 ///
12780 ///
12781 /// # Arguments
12782 /// * `obj` - which object the method should be called on
12783 /// * must be valid
12784 /// * must not be null
12785 /// * must not be already garbage collected
12786 /// * `methodID` - method id of the method
12787 /// * must not be null
12788 /// * must be valid
12789 /// * must not be a static
12790 /// * must actually be a method of `obj`
12791 /// * must refer to a method with 2 arguments
12792 ///
12793 /// # Returns
12794 /// Whatever the method returned or null if it threw
12795 ///
12796 /// # Throws Java Exception
12797 /// * Whatever the method threw
12798 ///
12799 ///
12800 /// # Panics
12801 /// if asserts feature is enabled and UB was detected
12802 ///
12803 /// # Safety
12804 ///
12805 /// Current thread must not be detached from JNI.
12806 ///
12807 /// Current thread must not be currently throwing an exception.
12808 ///
12809 /// Current thread does not hold a critical reference.
12810 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12811 ///
12812 /// `obj` must a valid and not already garbage collected.
12813 /// `methodID` must be valid, non-static and actually be a method of `obj`, return an object and have 2 arguments
12814 ///
12815 pub unsafe fn CallNonvirtualObjectMethod2<A: JType, B: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jobject {
12816 unsafe {
12817 #[cfg(feature = "asserts")]
12818 {
12819 self.check_not_critical("CallNonvirtualObjectMethod");
12820 self.check_no_exception("CallNonvirtualObjectMethod");
12821 self.check_return_type_object("CallNonvirtualObjectMethod", obj, methodID, "object");
12822 self.check_is_class("CallNonvirtualObjectMethod", class);
12823 self.check_parameter_types_object("CallNonvirtualObjectMethod", obj, methodID, arg1, 0, 2);
12824 self.check_parameter_types_object("CallNonvirtualObjectMethod", obj, methodID, arg2, 1, 2);
12825 }
12826 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jobject>(64)(self.vtable, obj, class, methodID, arg1, arg2)
12827 }
12828 }
12829
12830 ///
12831 /// Calls a non-static java method with 3 arguments that returns object without using the objects vtable to look up the method.
12832 /// This means that should the object be a subclass of the class that the method is declared in
12833 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
12834 ///
12835 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12836 ///
12837 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12838 ///
12839 ///
12840 /// # Arguments
12841 /// * `obj` - which object the method should be called on
12842 /// * must be valid
12843 /// * must not be null
12844 /// * must not be already garbage collected
12845 /// * `methodID` - method id of the method
12846 /// * must not be null
12847 /// * must be valid
12848 /// * must not be a static
12849 /// * must actually be a method of `obj`
12850 /// * must refer to a method with 3 arguments
12851 ///
12852 /// # Returns
12853 /// Whatever the method returned or null if it threw
12854 ///
12855 /// # Throws Java Exception
12856 /// * Whatever the method threw
12857 ///
12858 ///
12859 /// # Panics
12860 /// if asserts feature is enabled and UB was detected
12861 ///
12862 /// # Safety
12863 ///
12864 /// Current thread must not be detached from JNI.
12865 ///
12866 /// Current thread must not be currently throwing an exception.
12867 ///
12868 /// Current thread does not hold a critical reference.
12869 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12870 ///
12871 /// `obj` must a valid and not already garbage collected.
12872 /// `methodID` must be valid, non-static and actually be a method of `obj`, return an object and have 3 arguments
12873 ///
12874 pub unsafe fn CallNonvirtualObjectMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jobject {
12875 unsafe {
12876 #[cfg(feature = "asserts")]
12877 {
12878 self.check_not_critical("CallNonvirtualObjectMethod");
12879 self.check_no_exception("CallNonvirtualObjectMethod");
12880 self.check_return_type_object("CallNonvirtualObjectMethod", obj, methodID, "object");
12881 self.check_is_class("CallNonvirtualObjectMethod", class);
12882 self.check_parameter_types_object("CallNonvirtualObjectMethod", obj, methodID, arg1, 0, 3);
12883 self.check_parameter_types_object("CallNonvirtualObjectMethod", obj, methodID, arg2, 1, 3);
12884 self.check_parameter_types_object("CallNonvirtualObjectMethod", obj, methodID, arg3, 2, 3);
12885 }
12886 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jobject>(64)(self.vtable, obj, class, methodID, arg1, arg2, arg3)
12887 }
12888 }
12889
12890 ///
12891 /// Calls a non-static java method that returns boolean without using the objects vtable to look up the method.
12892 /// This means that should the object be a subclass of the class that the method is declared in
12893 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
12894 ///
12895 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12896 ///
12897 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12898 ///
12899 ///
12900 /// # Arguments
12901 /// * `obj` - which object the method should be called on
12902 /// * must be valid
12903 /// * must not be null
12904 /// * must not be already garbage collected
12905 /// * `methodID` - method id of the method
12906 /// * must not be null
12907 /// * must be valid
12908 /// * must not be a static
12909 /// * must actually be a method of `obj`
12910 /// * `args` - argument pointer
12911 /// * can be null if the method has no arguments
12912 /// * must not be null otherwise and point to the exact number of arguments the method expects
12913 ///
12914 /// # Returns
12915 /// Whatever the method returned or false if it threw
12916 ///
12917 /// # Throws Java Exception
12918 /// * Whatever the method threw
12919 ///
12920 ///
12921 /// # Panics
12922 /// if asserts feature is enabled and UB was detected
12923 ///
12924 /// # Safety
12925 ///
12926 /// Current thread must not be detached from JNI.
12927 ///
12928 /// Current thread must not be currently throwing an exception.
12929 ///
12930 /// Current thread does not hold a critical reference.
12931 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12932 ///
12933 /// `obj` must a valid and not already garbage collected.
12934 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a boolean
12935 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
12936 /// `args` union must contain types that match the java methods parameters.
12937 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
12938 ///
12939 pub unsafe fn CallNonvirtualBooleanMethodA(&self, obj: jobject, class: jclass, methodID: jmethodID, args: *const jtype) -> bool {
12940 unsafe {
12941 #[cfg(feature = "asserts")]
12942 {
12943 self.check_not_critical("CallNonvirtualBooleanMethodA");
12944 self.check_no_exception("CallNonvirtualBooleanMethodA");
12945 self.check_return_type_object("CallNonvirtualBooleanMethodA", obj, methodID, "boolean");
12946 self.check_is_class("CallNonvirtualBooleanMethodA", class);
12947 }
12948 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jclass, jmethodID, *const jtype) -> jboolean>(69)(self.vtable, obj, class, methodID, args).as_bool()
12949 }
12950 }
12951
12952 ///
12953 /// Calls a non-static java method with 0 arguments that returns boolean without using the objects vtable to look up the method.
12954 /// This means that should the object be a subclass of the class that the method is declared in
12955 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
12956 ///
12957 /// This is roughly equivalent to calling "super.someMethod(...)" in java
12958 ///
12959 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
12960 ///
12961 ///
12962 /// # Arguments
12963 /// * `obj` - which object the method should be called on
12964 /// * must be valid
12965 /// * must not be null
12966 /// * must not be already garbage collected
12967 /// * `methodID` - method id of the method
12968 /// * must not be null
12969 /// * must be valid
12970 /// * must not be a static
12971 /// * must actually be a method of `obj`
12972 /// * must refer to a method with 0 arguments
12973 ///
12974 /// # Returns
12975 /// Whatever the method returned or false if it threw
12976 ///
12977 /// # Throws Java Exception
12978 /// * Whatever the method threw
12979 ///
12980 ///
12981 /// # Panics
12982 /// if asserts feature is enabled and UB was detected
12983 ///
12984 /// # Safety
12985 ///
12986 /// Current thread must not be detached from JNI.
12987 ///
12988 /// Current thread must not be currently throwing an exception.
12989 ///
12990 /// Current thread does not hold a critical reference.
12991 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
12992 ///
12993 /// `obj` must a valid and not already garbage collected.
12994 /// `methodID` must be valid, non-static and actually be a method of `obj`, return boolean and have no parameters
12995 ///
12996 pub unsafe fn CallNonvirtualBooleanMethod0(&self, obj: jobject, class: jclass, methodID: jmethodID) -> bool {
12997 unsafe {
12998 #[cfg(feature = "asserts")]
12999 {
13000 self.check_not_critical("CallNonvirtualBooleanMethod");
13001 self.check_no_exception("CallNonvirtualBooleanMethod");
13002 self.check_return_type_object("CallNonvirtualBooleanMethod", obj, methodID, "boolean");
13003 self.check_is_class("CallNonvirtualBooleanMethod", class);
13004 }
13005 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID) -> jboolean>(67)(self.vtable, obj, class, methodID).as_bool()
13006 }
13007 }
13008
13009 ///
13010 /// Calls a non-static java method with 1 arguments that returns boolean without using the objects vtable to look up the method.
13011 /// This means that should the object be a subclass of the class that the method is declared in
13012 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13013 ///
13014 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13015 ///
13016 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13017 ///
13018 ///
13019 /// # Arguments
13020 /// * `obj` - which object the method should be called on
13021 /// * must be valid
13022 /// * must not be null
13023 /// * must not be already garbage collected
13024 /// * `methodID` - method id of the method
13025 /// * must not be null
13026 /// * must be valid
13027 /// * must not be a static
13028 /// * must actually be a method of `obj`
13029 /// * must refer to a method with 1 arguments
13030 ///
13031 /// # Returns
13032 /// Whatever the method returned or false if it threw
13033 ///
13034 /// # Throws Java Exception
13035 /// * Whatever the method threw
13036 ///
13037 ///
13038 /// # Panics
13039 /// if asserts feature is enabled and UB was detected
13040 ///
13041 /// # Safety
13042 ///
13043 /// Current thread must not be detached from JNI.
13044 ///
13045 /// Current thread must not be currently throwing an exception.
13046 ///
13047 /// Current thread does not hold a critical reference.
13048 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13049 ///
13050 /// `obj` must a valid and not already garbage collected.
13051 /// `methodID` must be valid, non-static and actually be a method of `obj`, return boolean and have 1 arguments
13052 ///
13053 pub unsafe fn CallNonvirtualBooleanMethod1<A: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A) -> bool {
13054 unsafe {
13055 #[cfg(feature = "asserts")]
13056 {
13057 self.check_not_critical("CallNonvirtualBooleanMethod");
13058 self.check_no_exception("CallNonvirtualBooleanMethod");
13059 self.check_return_type_object("CallNonvirtualBooleanMethod", obj, methodID, "boolean");
13060 self.check_is_class("CallNonvirtualBooleanMethod", class);
13061 self.check_parameter_types_object("CallNonvirtualBooleanMethod", obj, methodID, arg1, 0, 1);
13062 }
13063 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jboolean>(67)(self.vtable, obj, class, methodID, arg1).as_bool()
13064 }
13065 }
13066
13067 ///
13068 /// Calls a non-static java method with 2 arguments that returns boolean without using the objects vtable to look up the method.
13069 /// This means that should the object be a subclass of the class that the method is declared in
13070 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13071 ///
13072 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13073 ///
13074 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13075 ///
13076 ///
13077 /// # Arguments
13078 /// * `obj` - which object the method should be called on
13079 /// * must be valid
13080 /// * must not be null
13081 /// * must not be already garbage collected
13082 /// * `methodID` - method id of the method
13083 /// * must not be null
13084 /// * must be valid
13085 /// * must not be a static
13086 /// * must actually be a method of `obj`
13087 /// * must refer to a method with 2 arguments
13088 ///
13089 /// # Returns
13090 /// Whatever the method returned or false if it threw
13091 ///
13092 /// # Throws Java Exception
13093 /// * Whatever the method threw
13094 ///
13095 ///
13096 /// # Panics
13097 /// if asserts feature is enabled and UB was detected
13098 ///
13099 /// # Safety
13100 ///
13101 /// Current thread must not be detached from JNI.
13102 ///
13103 /// Current thread must not be currently throwing an exception.
13104 ///
13105 /// Current thread does not hold a critical reference.
13106 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13107 ///
13108 /// `obj` must a valid and not already garbage collected.
13109 /// `methodID` must be valid, non-static and actually be a method of `obj`, return boolean and have 2 arguments
13110 ///
13111 pub unsafe fn CallNonvirtualBooleanMethod2<A: JType, B: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B) -> bool {
13112 unsafe {
13113 #[cfg(feature = "asserts")]
13114 {
13115 self.check_not_critical("CallNonvirtualBooleanMethod");
13116 self.check_no_exception("CallNonvirtualBooleanMethod");
13117 self.check_return_type_object("CallNonvirtualBooleanMethod", obj, methodID, "boolean");
13118 self.check_is_class("CallNonvirtualBooleanMethod", class);
13119 self.check_parameter_types_object("CallNonvirtualBooleanMethod", obj, methodID, arg1, 0, 2);
13120 self.check_parameter_types_object("CallNonvirtualBooleanMethod", obj, methodID, arg2, 1, 2);
13121 }
13122 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jboolean>(67)(self.vtable, obj, class, methodID, arg1, arg2).as_bool()
13123 }
13124 }
13125
13126 ///
13127 /// Calls a non-static java method with 3 arguments that returns boolean without using the objects vtable to look up the method.
13128 /// This means that should the object be a subclass of the class that the method is declared in
13129 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13130 ///
13131 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13132 ///
13133 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13134 ///
13135 ///
13136 /// # Arguments
13137 /// * `obj` - which object the method should be called on
13138 /// * must be valid
13139 /// * must not be null
13140 /// * must not be already garbage collected
13141 /// * `methodID` - method id of the method
13142 /// * must not be null
13143 /// * must be valid
13144 /// * must not be a static
13145 /// * must actually be a method of `obj`
13146 /// * must refer to a method with 3 arguments
13147 ///
13148 /// # Returns
13149 /// Whatever the method returned or false if it threw
13150 ///
13151 /// # Throws Java Exception
13152 /// * Whatever the method threw
13153 ///
13154 ///
13155 /// # Panics
13156 /// if asserts feature is enabled and UB was detected
13157 ///
13158 /// # Safety
13159 ///
13160 /// Current thread must not be detached from JNI.
13161 ///
13162 /// Current thread must not be currently throwing an exception.
13163 ///
13164 /// Current thread does not hold a critical reference.
13165 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13166 ///
13167 /// `obj` must a valid and not already garbage collected.
13168 /// `methodID` must be valid, non-static and actually be a method of `obj`, return boolean and have 3 arguments
13169 ///
13170 pub unsafe fn CallNonvirtualBooleanMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> bool {
13171 unsafe {
13172 #[cfg(feature = "asserts")]
13173 {
13174 self.check_not_critical("CallNonvirtualBooleanMethod");
13175 self.check_no_exception("CallNonvirtualBooleanMethod");
13176 self.check_return_type_object("CallNonvirtualBooleanMethod", obj, methodID, "boolean");
13177 self.check_is_class("CallNonvirtualBooleanMethod", class);
13178 self.check_parameter_types_object("CallNonvirtualBooleanMethod", obj, methodID, arg1, 0, 3);
13179 self.check_parameter_types_object("CallNonvirtualBooleanMethod", obj, methodID, arg2, 1, 3);
13180 self.check_parameter_types_object("CallNonvirtualBooleanMethod", obj, methodID, arg3, 2, 3);
13181 }
13182 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jboolean>(67)(self.vtable, obj, class, methodID, arg1, arg2, arg3).as_bool()
13183 }
13184 }
13185
13186 ///
13187 /// Calls a non-static java method that returns byte without using the objects vtable to look up the method.
13188 /// This means that should the object be a subclass of the class that the method is declared in
13189 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13190 ///
13191 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13192 ///
13193 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13194 ///
13195 ///
13196 /// # Arguments
13197 /// * `obj` - which object the method should be called on
13198 /// * must be valid
13199 /// * must not be null
13200 /// * must not be already garbage collected
13201 /// * `methodID` - method id of the method
13202 /// * must not be null
13203 /// * must be valid
13204 /// * must not be a static
13205 /// * must actually be a method of `obj`
13206 /// * `args` - argument pointer
13207 /// * can be null if the method has no arguments
13208 /// * must not be null otherwise and point to the exact number of arguments the method expects
13209 ///
13210 /// # Returns
13211 /// Whatever the method returned or 0 if it threw
13212 ///
13213 /// # Throws Java Exception
13214 /// * Whatever the method threw
13215 ///
13216 ///
13217 /// # Panics
13218 /// if asserts feature is enabled and UB was detected
13219 ///
13220 /// # Safety
13221 ///
13222 /// Current thread must not be detached from JNI.
13223 ///
13224 /// Current thread must not be currently throwing an exception.
13225 ///
13226 /// Current thread does not hold a critical reference.
13227 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13228 ///
13229 /// `obj` must a valid and not already garbage collected.
13230 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a byte
13231 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
13232 /// `args` union must contain types that match the java methods parameters.
13233 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
13234 ///
13235 pub unsafe fn CallNonvirtualByteMethodA(&self, obj: jobject, class: jclass, methodID: jmethodID, args: *const jtype) -> jbyte {
13236 unsafe {
13237 #[cfg(feature = "asserts")]
13238 {
13239 self.check_not_critical("CallNonvirtualByteMethodA");
13240 self.check_no_exception("CallNonvirtualByteMethodA");
13241 self.check_return_type_object("CallNonvirtualByteMethodA", obj, methodID, "byte");
13242 self.check_is_class("CallNonvirtualByteMethodA", class);
13243 }
13244 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jclass, jmethodID, *const jtype) -> jbyte>(72)(self.vtable, obj, class, methodID, args)
13245 }
13246 }
13247
13248 ///
13249 /// Calls a non-static java method with 0 arguments that returns byte without using the objects vtable to look up the method.
13250 /// This means that should the object be a subclass of the class that the method is declared in
13251 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13252 ///
13253 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13254 ///
13255 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13256 ///
13257 ///
13258 /// # Arguments
13259 /// * `obj` - which object the method should be called on
13260 /// * must be valid
13261 /// * must not be null
13262 /// * must not be already garbage collected
13263 /// * `methodID` - method id of the method
13264 /// * must not be null
13265 /// * must be valid
13266 /// * must not be a static
13267 /// * must actually be a method of `obj`
13268 /// * must refer to a method with 0 arguments
13269 ///
13270 /// # Returns
13271 /// Whatever the method returned or 0 if it threw
13272 ///
13273 /// # Throws Java Exception
13274 /// * Whatever the method threw
13275 ///
13276 ///
13277 /// # Panics
13278 /// if asserts feature is enabled and UB was detected
13279 ///
13280 /// # Safety
13281 ///
13282 /// Current thread must not be detached from JNI.
13283 ///
13284 /// Current thread must not be currently throwing an exception.
13285 ///
13286 /// Current thread does not hold a critical reference.
13287 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13288 ///
13289 /// `obj` must a valid and not already garbage collected.
13290 /// `methodID` must be valid, non-static and actually be a method of `obj`, return byte and have 0 arguments
13291 ///
13292 pub unsafe fn CallNonvirtualByteMethod0(&self, obj: jobject, class: jclass, methodID: jmethodID) -> jbyte {
13293 unsafe {
13294 #[cfg(feature = "asserts")]
13295 {
13296 self.check_not_critical("CallNonvirtualByteMethod");
13297 self.check_no_exception("CallNonvirtualByteMethod");
13298 self.check_return_type_object("CallNonvirtualByteMethod", obj, methodID, "byte");
13299 self.check_is_class("CallNonvirtualByteMethod", class);
13300 }
13301 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID) -> jbyte>(70)(self.vtable, obj, class, methodID)
13302 }
13303 }
13304
13305 ///
13306 /// Calls a non-static java method with 1 arguments that returns byte without using the objects vtable to look up the method.
13307 /// This means that should the object be a subclass of the class that the method is declared in
13308 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13309 ///
13310 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13311 ///
13312 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13313 ///
13314 ///
13315 /// # Arguments
13316 /// * `obj` - which object the method should be called on
13317 /// * must be valid
13318 /// * must not be null
13319 /// * must not be already garbage collected
13320 /// * `methodID` - method id of the method
13321 /// * must not be null
13322 /// * must be valid
13323 /// * must not be a static
13324 /// * must actually be a method of `obj`
13325 /// * must refer to a method with 1 arguments
13326 ///
13327 /// # Returns
13328 /// Whatever the method returned or 0 if it threw
13329 ///
13330 /// # Throws Java Exception
13331 /// * Whatever the method threw
13332 ///
13333 ///
13334 /// # Panics
13335 /// if asserts feature is enabled and UB was detected
13336 ///
13337 /// # Safety
13338 ///
13339 /// Current thread must not be detached from JNI.
13340 ///
13341 /// Current thread must not be currently throwing an exception.
13342 ///
13343 /// Current thread does not hold a critical reference.
13344 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13345 ///
13346 /// `obj` must a valid and not already garbage collected.
13347 /// `methodID` must be valid, non-static and actually be a method of `obj`, return byte and have 1 arguments
13348 ///
13349 pub unsafe fn CallNonvirtualByteMethod1<A: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A) -> jbyte {
13350 unsafe {
13351 #[cfg(feature = "asserts")]
13352 {
13353 self.check_not_critical("CallNonvirtualByteMethod");
13354 self.check_no_exception("CallNonvirtualByteMethod");
13355 self.check_return_type_object("CallNonvirtualByteMethod", obj, methodID, "byte");
13356 self.check_is_class("CallNonvirtualByteMethod", class);
13357 self.check_parameter_types_object("CallNonvirtualByteMethod", obj, methodID, arg1, 0, 1);
13358 }
13359 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jbyte>(70)(self.vtable, obj, class, methodID, arg1)
13360 }
13361 }
13362
13363 ///
13364 /// Calls a non-static java method with 2 arguments that returns byte without using the objects vtable to look up the method.
13365 /// This means that should the object be a subclass of the class that the method is declared in
13366 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13367 ///
13368 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13369 ///
13370 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13371 ///
13372 ///
13373 /// # Arguments
13374 /// * `obj` - which object the method should be called on
13375 /// * must be valid
13376 /// * must not be null
13377 /// * must not be already garbage collected
13378 /// * `methodID` - method id of the method
13379 /// * must not be null
13380 /// * must be valid
13381 /// * must not be a static
13382 /// * must actually be a method of `obj`
13383 /// * must refer to a method with 0 arguments
13384 ///
13385 /// # Returns
13386 /// Whatever the method returned or 2 if it threw
13387 ///
13388 /// # Throws Java Exception
13389 /// * Whatever the method threw
13390 ///
13391 ///
13392 /// # Panics
13393 /// if asserts feature is enabled and UB was detected
13394 ///
13395 /// # Safety
13396 ///
13397 /// Current thread must not be detached from JNI.
13398 ///
13399 /// Current thread must not be currently throwing an exception.
13400 ///
13401 /// Current thread does not hold a critical reference.
13402 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13403 ///
13404 /// `obj` must a valid and not already garbage collected.
13405 /// `methodID` must be valid, non-static and actually be a method of `obj`, return byte and have 2 arguments
13406 ///
13407 pub unsafe fn CallNonvirtualByteMethod2<A: JType, B: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jbyte {
13408 unsafe {
13409 #[cfg(feature = "asserts")]
13410 {
13411 self.check_not_critical("CallNonvirtualByteMethod");
13412 self.check_no_exception("CallNonvirtualByteMethod");
13413 self.check_return_type_object("CallNonvirtualByteMethod", obj, methodID, "byte");
13414 self.check_is_class("CallNonvirtualByteMethod", class);
13415 self.check_parameter_types_object("CallNonvirtualByteMethod", obj, methodID, arg1, 0, 2);
13416 self.check_parameter_types_object("CallNonvirtualByteMethod", obj, methodID, arg2, 1, 2);
13417 }
13418 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jbyte>(70)(self.vtable, obj, class, methodID, arg1, arg2)
13419 }
13420 }
13421
13422 ///
13423 /// Calls a non-static java method with 3 arguments that returns byte without using the objects vtable to look up the method.
13424 /// This means that should the object be a subclass of the class that the method is declared in
13425 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13426 ///
13427 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13428 ///
13429 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13430 ///
13431 ///
13432 /// # Arguments
13433 /// * `obj` - which object the method should be called on
13434 /// * must be valid
13435 /// * must not be null
13436 /// * must not be already garbage collected
13437 /// * `methodID` - method id of the method
13438 /// * must not be null
13439 /// * must be valid
13440 /// * must not be a static
13441 /// * must actually be a method of `obj`
13442 /// * must refer to a method with 0 arguments
13443 ///
13444 /// # Returns
13445 /// Whatever the method returned or 3 if it threw
13446 ///
13447 /// # Throws Java Exception
13448 /// * Whatever the method threw
13449 ///
13450 ///
13451 /// # Panics
13452 /// if asserts feature is enabled and UB was detected
13453 ///
13454 /// # Safety
13455 ///
13456 /// Current thread must not be detached from JNI.
13457 ///
13458 /// Current thread must not be currently throwing an exception.
13459 ///
13460 /// Current thread does not hold a critical reference.
13461 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13462 ///
13463 /// `obj` must a valid and not already garbage collected.
13464 /// `methodID` must be valid, non-static and actually be a method of `obj`, return byte and have 3 arguments
13465 ///
13466 pub unsafe fn CallNonvirtualByteMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jbyte {
13467 unsafe {
13468 #[cfg(feature = "asserts")]
13469 {
13470 self.check_not_critical("CallNonvirtualByteMethod");
13471 self.check_no_exception("CallNonvirtualByteMethod");
13472 self.check_return_type_object("CallNonvirtualByteMethod", obj, methodID, "byte");
13473 self.check_is_class("CallNonvirtualByteMethod", class);
13474 self.check_parameter_types_object("CallNonvirtualByteMethod", obj, methodID, arg1, 0, 3);
13475 self.check_parameter_types_object("CallNonvirtualByteMethod", obj, methodID, arg2, 1, 3);
13476 self.check_parameter_types_object("CallNonvirtualByteMethod", obj, methodID, arg3, 2, 3);
13477 }
13478 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jbyte>(70)(self.vtable, obj, class, methodID, arg1, arg2, arg3)
13479 }
13480 }
13481
13482 ///
13483 /// Calls a non-static java method with 3 arguments that returns char without using the objects vtable to look up the method.
13484 /// This means that should the object be a subclass of the class that the method is declared in
13485 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13486 ///
13487 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13488 ///
13489 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13490 ///
13491 ///
13492 /// # Arguments
13493 /// * `obj` - which object the method should be called on
13494 /// * must be valid
13495 /// * must not be null
13496 /// * must not be already garbage collected
13497 /// * `methodID` - method id of the method
13498 /// * must not be null
13499 /// * must be valid
13500 /// * must not be a static
13501 /// * must actually be a method of `obj`
13502 /// * `args` - argument pointer
13503 /// * can be null if the method has no arguments
13504 /// * must not be null otherwise and point to the exact number of arguments the method expects
13505 ///
13506 /// # Returns
13507 /// Whatever the method returned or 0 if it threw
13508 ///
13509 /// # Throws Java Exception
13510 /// * Whatever the method threw
13511 ///
13512 ///
13513 /// # Panics
13514 /// if asserts feature is enabled and UB was detected
13515 ///
13516 /// # Safety
13517 ///
13518 /// Current thread must not be detached from JNI.
13519 ///
13520 /// Current thread must not be currently throwing an exception.
13521 ///
13522 /// Current thread does not hold a critical reference.
13523 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13524 ///
13525 /// `obj` must a valid and not already garbage collected.
13526 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a char
13527 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
13528 /// `args` union must contain types that match the java methods parameters.
13529 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
13530 ///
13531 pub unsafe fn CallNonvirtualCharMethodA(&self, obj: jobject, class: jclass, methodID: jmethodID, args: *const jtype) -> jchar {
13532 unsafe {
13533 #[cfg(feature = "asserts")]
13534 {
13535 self.check_not_critical("CallNonvirtualCharMethodA");
13536 self.check_no_exception("CallNonvirtualCharMethodA");
13537 self.check_return_type_object("CallNonvirtualCharMethodA", obj, methodID, "char");
13538 self.check_is_class("CallNonvirtualCharMethodA", class);
13539 }
13540 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jclass, jmethodID, *const jtype) -> jchar>(75)(self.vtable, obj, class, methodID, args)
13541 }
13542 }
13543
13544 ///
13545 /// Calls a non-static java method with 0 arguments that returns char without using the objects vtable to look up the method.
13546 /// This means that should the object be a subclass of the class that the method is declared in
13547 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13548 ///
13549 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13550 ///
13551 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13552 ///
13553 ///
13554 /// # Arguments
13555 /// * `obj` - which object the method should be called on
13556 /// * must be valid
13557 /// * must not be null
13558 /// * must not be already garbage collected
13559 /// * `methodID` - method id of the method
13560 /// * must not be null
13561 /// * must be valid
13562 /// * must not be a static
13563 /// * must actually be a method of `obj`
13564 /// * must refer to a method with 0 arguments
13565 ///
13566 /// # Returns
13567 /// Whatever the method returned or 0 if it threw
13568 ///
13569 /// # Throws Java Exception
13570 /// * Whatever the method threw
13571 ///
13572 ///
13573 /// # Panics
13574 /// if asserts feature is enabled and UB was detected
13575 ///
13576 /// # Safety
13577 ///
13578 /// Current thread must not be detached from JNI.
13579 ///
13580 /// Current thread must not be currently throwing an exception.
13581 ///
13582 /// Current thread does not hold a critical reference.
13583 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13584 ///
13585 /// `obj` must a valid and not already garbage collected.
13586 /// `methodID` must be valid, non-static and actually be a method of `obj`, return char and have 0 arguments
13587 ///
13588 pub unsafe fn CallNonvirtualCharMethod0(&self, obj: jobject, class: jclass, methodID: jmethodID) -> jchar {
13589 unsafe {
13590 #[cfg(feature = "asserts")]
13591 {
13592 self.check_not_critical("CallNonvirtualCharMethod");
13593 self.check_no_exception("CallNonvirtualCharMethod");
13594 self.check_return_type_object("CallNonvirtualCharMethod", obj, methodID, "char");
13595 self.check_is_class("CallNonvirtualCharMethod", class);
13596 }
13597 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID) -> jchar>(73)(self.vtable, obj, class, methodID)
13598 }
13599 }
13600
13601 ///
13602 /// Calls a non-static java method with 1 arguments that returns char without using the objects vtable to look up the method.
13603 /// This means that should the object be a subclass of the class that the method is declared in
13604 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13605 ///
13606 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13607 ///
13608 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13609 ///
13610 ///
13611 /// # Arguments
13612 /// * `obj` - which object the method should be called on
13613 /// * must be valid
13614 /// * must not be null
13615 /// * must not be already garbage collected
13616 /// * `methodID` - method id of the method
13617 /// * must not be null
13618 /// * must be valid
13619 /// * must not be a static
13620 /// * must actually be a method of `obj`
13621 /// * must refer to a method with 1 arguments
13622 ///
13623 /// # Returns
13624 /// Whatever the method returned or 0 if it threw
13625 ///
13626 /// # Throws Java Exception
13627 /// * Whatever the method threw
13628 ///
13629 ///
13630 /// # Panics
13631 /// if asserts feature is enabled and UB was detected
13632 ///
13633 /// # Safety
13634 ///
13635 /// Current thread must not be detached from JNI.
13636 ///
13637 /// Current thread must not be currently throwing an exception.
13638 ///
13639 /// Current thread does not hold a critical reference.
13640 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13641 ///
13642 /// `obj` must a valid and not already garbage collected.
13643 /// `methodID` must be valid, non-static and actually be a method of `obj`, return char and have 1 arguments
13644 ///
13645 pub unsafe fn CallNonvirtualCharMethod1<A: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A) -> jchar {
13646 unsafe {
13647 #[cfg(feature = "asserts")]
13648 {
13649 self.check_not_critical("CallNonvirtualCharMethod");
13650 self.check_no_exception("CallNonvirtualCharMethod");
13651 self.check_return_type_object("CallNonvirtualCharMethod", obj, methodID, "char");
13652 self.check_is_class("CallNonvirtualCharMethod", class);
13653 self.check_parameter_types_object("CallNonvirtualCharMethod", obj, methodID, arg1, 0, 1);
13654 }
13655 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jchar>(73)(self.vtable, obj, class, methodID, arg1)
13656 }
13657 }
13658
13659 ///
13660 /// Calls a non-static java method with 2 arguments that returns char without using the objects vtable to look up the method.
13661 /// This means that should the object be a subclass of the class that the method is declared in
13662 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13663 ///
13664 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13665 ///
13666 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13667 ///
13668 ///
13669 /// # Arguments
13670 /// * `obj` - which object the method should be called on
13671 /// * must be valid
13672 /// * must not be null
13673 /// * must not be already garbage collected
13674 /// * `methodID` - method id of the method
13675 /// * must not be null
13676 /// * must be valid
13677 /// * must not be a static
13678 /// * must actually be a method of `obj`
13679 /// * must refer to a method with 2 arguments
13680 ///
13681 /// # Returns
13682 /// Whatever the method returned or 0 if it threw
13683 ///
13684 /// # Throws Java Exception
13685 /// * Whatever the method threw
13686 ///
13687 ///
13688 /// # Panics
13689 /// if asserts feature is enabled and UB was detected
13690 ///
13691 /// # Safety
13692 ///
13693 /// Current thread must not be detached from JNI.
13694 ///
13695 /// Current thread must not be currently throwing an exception.
13696 ///
13697 /// Current thread does not hold a critical reference.
13698 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13699 ///
13700 /// `obj` must a valid and not already garbage collected.
13701 /// `methodID` must be valid, non-static and actually be a method of `obj`, return char and have 2 arguments
13702 ///
13703 pub unsafe fn CallNonvirtualCharMethod2<A: JType, B: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jchar {
13704 unsafe {
13705 #[cfg(feature = "asserts")]
13706 {
13707 self.check_not_critical("CallNonvirtualCharMethod");
13708 self.check_no_exception("CallNonvirtualCharMethod");
13709 self.check_return_type_object("CallNonvirtualCharMethod", obj, methodID, "char");
13710 self.check_is_class("CallNonvirtualCharMethod", class);
13711 self.check_parameter_types_object("CallNonvirtualCharMethod", obj, methodID, arg1, 0, 2);
13712 self.check_parameter_types_object("CallNonvirtualCharMethod", obj, methodID, arg2, 1, 2);
13713 }
13714 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jchar>(73)(self.vtable, obj, class, methodID, arg1, arg2)
13715 }
13716 }
13717
13718 ///
13719 /// Calls a non-static java method with 3 arguments that returns char without using the objects vtable to look up the method.
13720 /// This means that should the object be a subclass of the class that the method is declared in
13721 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13722 ///
13723 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13724 ///
13725 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13726 ///
13727 ///
13728 /// # Arguments
13729 /// * `obj` - which object the method should be called on
13730 /// * must be valid
13731 /// * must not be null
13732 /// * must not be already garbage collected
13733 /// * `methodID` - method id of the method
13734 /// * must not be null
13735 /// * must be valid
13736 /// * must not be a static
13737 /// * must actually be a method of `obj`
13738 /// * must refer to a method with 3 arguments
13739 ///
13740 /// # Returns
13741 /// Whatever the method returned or 0 if it threw
13742 ///
13743 /// # Throws Java Exception
13744 /// * Whatever the method threw
13745 ///
13746 ///
13747 /// # Panics
13748 /// if asserts feature is enabled and UB was detected
13749 ///
13750 /// # Safety
13751 ///
13752 /// Current thread must not be detached from JNI.
13753 ///
13754 /// Current thread must not be currently throwing an exception.
13755 ///
13756 /// Current thread does not hold a critical reference.
13757 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13758 ///
13759 /// `obj` must a valid and not already garbage collected.
13760 /// `methodID` must be valid, non-static and actually be a method of `obj`, return char and have 3 arguments
13761 ///
13762 pub unsafe fn CallNonvirtualCharMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jchar {
13763 unsafe {
13764 #[cfg(feature = "asserts")]
13765 {
13766 self.check_not_critical("CallNonvirtualCharMethod");
13767 self.check_no_exception("CallNonvirtualCharMethod");
13768 self.check_return_type_object("CallNonvirtualCharMethod", obj, methodID, "char");
13769 self.check_is_class("CallNonvirtualCharMethod", class);
13770 self.check_parameter_types_object("CallNonvirtualCharMethod", obj, methodID, arg1, 0, 3);
13771 self.check_parameter_types_object("CallNonvirtualCharMethod", obj, methodID, arg2, 1, 3);
13772 self.check_parameter_types_object("CallNonvirtualCharMethod", obj, methodID, arg3, 2, 3);
13773 }
13774 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jchar>(73)(self.vtable, obj, class, methodID, arg1, arg2, arg3)
13775 }
13776 }
13777
13778 ///
13779 /// Calls a non-static java method with 3 arguments that returns short without using the objects vtable to look up the method.
13780 /// This means that should the object be a subclass of the class that the method is declared in
13781 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13782 ///
13783 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13784 ///
13785 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13786 ///
13787 ///
13788 /// # Arguments
13789 /// * `obj` - which object the method should be called on
13790 /// * must be valid
13791 /// * must not be null
13792 /// * must not be already garbage collected
13793 /// * `methodID` - method id of the method
13794 /// * must not be null
13795 /// * must be valid
13796 /// * must not be a static
13797 /// * must actually be a method of `obj`
13798 /// * `args` - argument pointer
13799 /// * can be null if the method has no arguments
13800 /// * must not be null otherwise and point to the exact number of arguments the method expects
13801 ///
13802 /// # Returns
13803 /// Whatever the method returned or 0 if it threw
13804 ///
13805 /// # Throws Java Exception
13806 /// * Whatever the method threw
13807 ///
13808 ///
13809 /// # Panics
13810 /// if asserts feature is enabled and UB was detected
13811 ///
13812 /// # Safety
13813 ///
13814 /// Current thread must not be detached from JNI.
13815 ///
13816 /// Current thread must not be currently throwing an exception.
13817 ///
13818 /// Current thread does not hold a critical reference.
13819 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13820 ///
13821 /// `obj` must a valid and not already garbage collected.
13822 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a short
13823 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
13824 /// `args` union must contain types that match the java methods parameters.
13825 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
13826 ///
13827 pub unsafe fn CallNonvirtualShortMethodA(&self, obj: jobject, class: jclass, methodID: jmethodID, args: *const jtype) -> jshort {
13828 unsafe {
13829 #[cfg(feature = "asserts")]
13830 {
13831 self.check_not_critical("CallNonvirtualShortMethodA");
13832 self.check_no_exception("CallNonvirtualShortMethodA");
13833 self.check_return_type_object("CallNonvirtualShortMethodA", obj, methodID, "short");
13834 self.check_is_class("CallNonvirtualShortMethodA", class);
13835 }
13836 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jclass, jmethodID, *const jtype) -> jshort>(78)(self.vtable, obj, class, methodID, args)
13837 }
13838 }
13839
13840 ///
13841 /// Calls a non-static java method with 0 arguments that returns short without using the objects vtable to look up the method.
13842 /// This means that should the object be a subclass of the class that the method is declared in
13843 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13844 ///
13845 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13846 ///
13847 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13848 ///
13849 ///
13850 /// # Arguments
13851 /// * `obj` - which object the method should be called on
13852 /// * must be valid
13853 /// * must not be null
13854 /// * must not be already garbage collected
13855 /// * `methodID` - method id of the method
13856 /// * must not be null
13857 /// * must be valid
13858 /// * must not be a static
13859 /// * must actually be a method of `obj`
13860 /// * must refer to a method with 0 arguments
13861 ///
13862 /// # Returns
13863 /// Whatever the method returned or 0 if it threw
13864 ///
13865 /// # Throws Java Exception
13866 /// * Whatever the method threw
13867 ///
13868 ///
13869 /// # Panics
13870 /// if asserts feature is enabled and UB was detected
13871 ///
13872 /// # Safety
13873 ///
13874 /// Current thread must not be detached from JNI.
13875 ///
13876 /// Current thread must not be currently throwing an exception.
13877 ///
13878 /// Current thread does not hold a critical reference.
13879 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13880 ///
13881 /// `obj` must a valid and not already garbage collected.
13882 /// `methodID` must be valid, non-static and actually be a method of `obj`, return short and have 0 arguments
13883 ///
13884 pub unsafe fn CallNonvirtualShortMethod0(&self, obj: jobject, class: jclass, methodID: jmethodID) -> jshort {
13885 unsafe {
13886 #[cfg(feature = "asserts")]
13887 {
13888 self.check_not_critical("CallNonvirtualShortMethod");
13889 self.check_no_exception("CallNonvirtualShortMethod");
13890 self.check_return_type_object("CallNonvirtualShortMethod", obj, methodID, "short");
13891 self.check_is_class("CallNonvirtualShortMethod", class);
13892 }
13893 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID) -> jshort>(76)(self.vtable, obj, class, methodID)
13894 }
13895 }
13896
13897 ///
13898 /// Calls a non-static java method with 1 arguments that returns short without using the objects vtable to look up the method.
13899 /// This means that should the object be a subclass of the class that the method is declared in
13900 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13901 ///
13902 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13903 ///
13904 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13905 ///
13906 ///
13907 /// # Arguments
13908 /// * `obj` - which object the method should be called on
13909 /// * must be valid
13910 /// * must not be null
13911 /// * must not be already garbage collected
13912 /// * `methodID` - method id of the method
13913 /// * must not be null
13914 /// * must be valid
13915 /// * must not be a static
13916 /// * must actually be a method of `obj`
13917 /// * must refer to a method with 1 arguments
13918 ///
13919 /// # Returns
13920 /// Whatever the method returned or 0 if it threw
13921 ///
13922 /// # Throws Java Exception
13923 /// * Whatever the method threw
13924 ///
13925 ///
13926 /// # Panics
13927 /// if asserts feature is enabled and UB was detected
13928 ///
13929 /// # Safety
13930 ///
13931 /// Current thread must not be detached from JNI.
13932 ///
13933 /// Current thread must not be currently throwing an exception.
13934 ///
13935 /// Current thread does not hold a critical reference.
13936 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13937 ///
13938 /// `obj` must a valid and not already garbage collected.
13939 /// `methodID` must be valid, non-static and actually be a method of `obj`, return short and have 1 arguments
13940 ///
13941 pub unsafe fn CallNonvirtualShortMethod1<A: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A) -> jshort {
13942 unsafe {
13943 #[cfg(feature = "asserts")]
13944 {
13945 self.check_not_critical("CallNonvirtualShortMethod");
13946 self.check_no_exception("CallNonvirtualShortMethod");
13947 self.check_return_type_object("CallNonvirtualShortMethod", obj, methodID, "short");
13948 self.check_is_class("CallNonvirtualShortMethod", class);
13949 self.check_parameter_types_object("CallNonvirtualShortMethod", obj, methodID, arg1, 0, 1);
13950 }
13951 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jshort>(76)(self.vtable, obj, class, methodID, arg1)
13952 }
13953 }
13954
13955 ///
13956 /// Calls a non-static java method with 2 arguments that returns short without using the objects vtable to look up the method.
13957 /// This means that should the object be a subclass of the class that the method is declared in
13958 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
13959 ///
13960 /// This is roughly equivalent to calling "super.someMethod(...)" in java
13961 ///
13962 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
13963 ///
13964 ///
13965 /// # Arguments
13966 /// * `obj` - which object the method should be called on
13967 /// * must be valid
13968 /// * must not be null
13969 /// * must not be already garbage collected
13970 /// * `methodID` - method id of the method
13971 /// * must not be null
13972 /// * must be valid
13973 /// * must not be a static
13974 /// * must actually be a method of `obj`
13975 /// * must refer to a method with 2 arguments
13976 ///
13977 /// # Returns
13978 /// Whatever the method returned or 0 if it threw
13979 ///
13980 /// # Throws Java Exception
13981 /// * Whatever the method threw
13982 ///
13983 ///
13984 /// # Panics
13985 /// if asserts feature is enabled and UB was detected
13986 ///
13987 /// # Safety
13988 ///
13989 /// Current thread must not be detached from JNI.
13990 ///
13991 /// Current thread must not be currently throwing an exception.
13992 ///
13993 /// Current thread does not hold a critical reference.
13994 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
13995 ///
13996 /// `obj` must a valid and not already garbage collected.
13997 /// `methodID` must be valid, non-static and actually be a method of `obj`, return short and have 2 arguments
13998 ///
13999 pub unsafe fn CallNonvirtualShortMethod2<A: JType, B: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jshort {
14000 unsafe {
14001 #[cfg(feature = "asserts")]
14002 {
14003 self.check_not_critical("CallNonvirtualShortMethod");
14004 self.check_no_exception("CallNonvirtualShortMethod");
14005 self.check_return_type_object("CallNonvirtualShortMethod", obj, methodID, "short");
14006 self.check_is_class("CallNonvirtualShortMethod", class);
14007 self.check_parameter_types_object("CallNonvirtualShortMethod", obj, methodID, arg1, 0, 2);
14008 self.check_parameter_types_object("CallNonvirtualShortMethod", obj, methodID, arg2, 1, 2);
14009 }
14010 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jshort>(76)(self.vtable, obj, class, methodID, arg1, arg2)
14011 }
14012 }
14013
14014 ///
14015 /// Calls a non-static java method with 3 arguments that returns short without using the objects vtable to look up the method.
14016 /// This means that should the object be a subclass of the class that the method is declared in
14017 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14018 ///
14019 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14020 ///
14021 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14022 ///
14023 ///
14024 /// # Arguments
14025 /// * `obj` - which object the method should be called on
14026 /// * must be valid
14027 /// * must not be null
14028 /// * must not be already garbage collected
14029 /// * `methodID` - method id of the method
14030 /// * must not be null
14031 /// * must be valid
14032 /// * must not be a static
14033 /// * must actually be a method of `obj`
14034 /// * must refer to a method with 3 arguments
14035 ///
14036 /// # Returns
14037 /// Whatever the method returned or 0 if it threw
14038 ///
14039 /// # Throws Java Exception
14040 /// * Whatever the method threw
14041 ///
14042 ///
14043 /// # Panics
14044 /// if asserts feature is enabled and UB was detected
14045 ///
14046 /// # Safety
14047 ///
14048 /// Current thread must not be detached from JNI.
14049 ///
14050 /// Current thread must not be currently throwing an exception.
14051 ///
14052 /// Current thread does not hold a critical reference.
14053 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14054 ///
14055 /// `obj` must a valid and not already garbage collected.
14056 /// `methodID` must be valid, non-static and actually be a method of `obj`, return short and have 3 arguments
14057 ///
14058 pub unsafe fn CallNonvirtualShortMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jshort {
14059 unsafe {
14060 #[cfg(feature = "asserts")]
14061 {
14062 self.check_not_critical("CallNonvirtualShortMethod");
14063 self.check_no_exception("CallNonvirtualShortMethod");
14064 self.check_return_type_object("CallNonvirtualShortMethod", obj, methodID, "short");
14065 self.check_is_class("CallNonvirtualShortMethod", class);
14066 self.check_parameter_types_object("CallNonvirtualShortMethod", obj, methodID, arg1, 0, 3);
14067 self.check_parameter_types_object("CallNonvirtualShortMethod", obj, methodID, arg2, 1, 3);
14068 self.check_parameter_types_object("CallNonvirtualShortMethod", obj, methodID, arg3, 2, 3);
14069 }
14070 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jshort>(76)(self.vtable, obj, class, methodID, arg1, arg2, arg3)
14071 }
14072 }
14073
14074 ///
14075 /// Calls a non-static java method with 3 arguments that returns int without using the objects vtable to look up the method.
14076 /// This means that should the object be a subclass of the class that the method is declared in
14077 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14078 ///
14079 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14080 ///
14081 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14082 ///
14083 ///
14084 /// # Arguments
14085 /// * `obj` - which object the method should be called on
14086 /// * must be valid
14087 /// * must not be null
14088 /// * must not be already garbage collected
14089 /// * `methodID` - method id of the method
14090 /// * must not be null
14091 /// * must be valid
14092 /// * must not be a static
14093 /// * must actually be a method of `obj`
14094 /// * `args` - argument pointer
14095 /// * can be null if the method has no arguments
14096 /// * must not be null otherwise and point to the exact number of arguments the method expects
14097 ///
14098 /// # Returns
14099 /// Whatever the method returned or 0 if it threw
14100 ///
14101 /// # Throws Java Exception
14102 /// * Whatever the method threw
14103 ///
14104 ///
14105 /// # Panics
14106 /// if asserts feature is enabled and UB was detected
14107 ///
14108 /// # Safety
14109 ///
14110 /// Current thread must not be detached from JNI.
14111 ///
14112 /// Current thread must not be currently throwing an exception.
14113 ///
14114 /// Current thread does not hold a critical reference.
14115 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14116 ///
14117 /// `obj` must a valid and not already garbage collected.
14118 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a int
14119 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
14120 /// `args` union must contain types that match the java methods parameters.
14121 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
14122 ///
14123 pub unsafe fn CallNonvirtualIntMethodA(&self, obj: jobject, class: jclass, methodID: jmethodID, args: *const jtype) -> jint {
14124 unsafe {
14125 #[cfg(feature = "asserts")]
14126 {
14127 self.check_not_critical("CallNonvirtualIntMethodA");
14128 self.check_no_exception("CallNonvirtualIntMethodA");
14129 self.check_return_type_object("CallNonvirtualIntMethodA", obj, methodID, "int");
14130 self.check_is_class("CallNonvirtualIntMethodA", class);
14131 }
14132 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jclass, jmethodID, *const jtype) -> jint>(81)(self.vtable, obj, class, methodID, args)
14133 }
14134 }
14135
14136 ///
14137 /// Calls a non-static java method with 0 arguments that returns short without using the objects vtable to look up the method.
14138 /// This means that should the object be a subclass of the class that the method is declared in
14139 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14140 ///
14141 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14142 ///
14143 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14144 ///
14145 ///
14146 /// # Arguments
14147 /// * `obj` - which object the method should be called on
14148 /// * must be valid
14149 /// * must not be null
14150 /// * must not be already garbage collected
14151 /// * `methodID` - method id of the method
14152 /// * must not be null
14153 /// * must be valid
14154 /// * must not be a static
14155 /// * must actually be a method of `obj`
14156 /// * must refer to a method with 0 arguments
14157 ///
14158 /// # Returns
14159 /// Whatever the method returned or 0 if it threw
14160 ///
14161 /// # Throws Java Exception
14162 /// * Whatever the method threw
14163 ///
14164 ///
14165 /// # Panics
14166 /// if asserts feature is enabled and UB was detected
14167 ///
14168 /// # Safety
14169 ///
14170 /// Current thread must not be detached from JNI.
14171 ///
14172 /// Current thread must not be currently throwing an exception.
14173 ///
14174 /// Current thread does not hold a critical reference.
14175 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14176 ///
14177 /// `obj` must a valid and not already garbage collected.
14178 /// `methodID` must be valid, non-static and actually be a method of `obj`, return int and have 0 arguments
14179 ///
14180 pub unsafe fn CallNonvirtualIntMethod0(&self, obj: jobject, class: jclass, methodID: jmethodID) -> jint {
14181 unsafe {
14182 #[cfg(feature = "asserts")]
14183 {
14184 self.check_not_critical("CallNonvirtualIntMethod");
14185 self.check_no_exception("CallNonvirtualIntMethod");
14186 self.check_return_type_object("CallNonvirtualIntMethod", obj, methodID, "int");
14187 self.check_is_class("CallNonvirtualIntMethod", class);
14188 }
14189 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID) -> jint>(79)(self.vtable, obj, class, methodID)
14190 }
14191 }
14192
14193 ///
14194 /// Calls a non-static java method with 1 arguments that returns int without using the objects vtable to look up the method.
14195 /// This means that should the object be a subclass of the class that the method is declared in
14196 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14197 ///
14198 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14199 ///
14200 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14201 ///
14202 ///
14203 /// # Arguments
14204 /// * `obj` - which object the method should be called on
14205 /// * must be valid
14206 /// * must not be null
14207 /// * must not be already garbage collected
14208 /// * `methodID` - method id of the method
14209 /// * must not be null
14210 /// * must be valid
14211 /// * must not be a static
14212 /// * must actually be a method of `obj`
14213 /// * must refer to a method with 1 arguments
14214 ///
14215 /// # Returns
14216 /// Whatever the method returned or 0 if it threw
14217 ///
14218 /// # Throws Java Exception
14219 /// * Whatever the method threw
14220 ///
14221 ///
14222 /// # Panics
14223 /// if asserts feature is enabled and UB was detected
14224 ///
14225 /// # Safety
14226 ///
14227 /// Current thread must not be detached from JNI.
14228 ///
14229 /// Current thread must not be currently throwing an exception.
14230 ///
14231 /// Current thread does not hold a critical reference.
14232 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14233 ///
14234 /// `obj` must a valid and not already garbage collected.
14235 /// `methodID` must be valid, non-static and actually be a method of `obj`, return int and have 1 arguments
14236 ///
14237 pub unsafe fn CallNonvirtualIntMethod1<A: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A) -> jint {
14238 unsafe {
14239 #[cfg(feature = "asserts")]
14240 {
14241 self.check_not_critical("CallNonvirtualIntMethod");
14242 self.check_no_exception("CallNonvirtualIntMethod");
14243 self.check_return_type_object("CallNonvirtualIntMethod", obj, methodID, "int");
14244 self.check_is_class("CallNonvirtualIntMethod", class);
14245 self.check_parameter_types_object("CallNonvirtualIntMethod", obj, methodID, arg1, 0, 1);
14246 }
14247 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jint>(79)(self.vtable, obj, class, methodID, arg1)
14248 }
14249 }
14250
14251 ///
14252 /// Calls a non-static java method with 2 arguments that returns int without using the objects vtable to look up the method.
14253 /// This means that should the object be a subclass of the class that the method is declared in
14254 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14255 ///
14256 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14257 ///
14258 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14259 ///
14260 ///
14261 /// # Arguments
14262 /// * `obj` - which object the method should be called on
14263 /// * must be valid
14264 /// * must not be null
14265 /// * must not be already garbage collected
14266 /// * `methodID` - method id of the method
14267 /// * must not be null
14268 /// * must be valid
14269 /// * must not be a static
14270 /// * must actually be a method of `obj`
14271 /// * must refer to a method with 2 arguments
14272 ///
14273 /// # Returns
14274 /// Whatever the method returned or 0 if it threw
14275 ///
14276 /// # Throws Java Exception
14277 /// * Whatever the method threw
14278 ///
14279 ///
14280 /// # Panics
14281 /// if asserts feature is enabled and UB was detected
14282 ///
14283 /// # Safety
14284 ///
14285 /// Current thread must not be detached from JNI.
14286 ///
14287 /// Current thread must not be currently throwing an exception.
14288 ///
14289 /// Current thread does not hold a critical reference.
14290 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14291 ///
14292 /// `obj` must a valid and not already garbage collected.
14293 /// `methodID` must be valid, non-static and actually be a method of `obj`, return int and have 2 arguments
14294 ///
14295 pub unsafe fn CallNonvirtualIntMethod2<A: JType, B: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jint {
14296 unsafe {
14297 #[cfg(feature = "asserts")]
14298 {
14299 self.check_not_critical("CallNonvirtualIntMethod");
14300 self.check_no_exception("CallNonvirtualIntMethod");
14301 self.check_return_type_object("CallNonvirtualIntMethod", obj, methodID, "int");
14302 self.check_is_class("CallNonvirtualIntMethod", class);
14303 self.check_parameter_types_object("CallNonvirtualIntMethod", obj, methodID, arg1, 0, 2);
14304 self.check_parameter_types_object("CallNonvirtualIntMethod", obj, methodID, arg2, 1, 2);
14305 }
14306 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jint>(79)(self.vtable, obj, class, methodID, arg1, arg2)
14307 }
14308 }
14309
14310 ///
14311 /// Calls a non-static java method with 3 arguments that returns int without using the objects vtable to look up the method.
14312 /// This means that should the object be a subclass of the class that the method is declared in
14313 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14314 ///
14315 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14316 ///
14317 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14318 ///
14319 ///
14320 /// # Arguments
14321 /// * `obj` - which object the method should be called on
14322 /// * must be valid
14323 /// * must not be null
14324 /// * must not be already garbage collected
14325 /// * `methodID` - method id of the method
14326 /// * must not be null
14327 /// * must be valid
14328 /// * must not be a static
14329 /// * must actually be a method of `obj`
14330 /// * must refer to a method with 3 arguments
14331 ///
14332 /// # Returns
14333 /// Whatever the method returned or 0 if it threw
14334 ///
14335 /// # Throws Java Exception
14336 /// * Whatever the method threw
14337 ///
14338 ///
14339 /// # Panics
14340 /// if asserts feature is enabled and UB was detected
14341 ///
14342 /// # Safety
14343 ///
14344 /// Current thread must not be detached from JNI.
14345 ///
14346 /// Current thread must not be currently throwing an exception.
14347 ///
14348 /// Current thread does not hold a critical reference.
14349 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14350 ///
14351 /// `obj` must a valid and not already garbage collected.
14352 /// `methodID` must be valid, non-static and actually be a method of `obj`, return int and have 3 arguments
14353 ///
14354 pub unsafe fn CallNonvirtualIntMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jint {
14355 unsafe {
14356 #[cfg(feature = "asserts")]
14357 {
14358 self.check_not_critical("CallNonvirtualIntMethod");
14359 self.check_no_exception("CallNonvirtualIntMethod");
14360 self.check_return_type_object("CallNonvirtualIntMethod", obj, methodID, "int");
14361 self.check_is_class("CallNonvirtualIntMethod", class);
14362 self.check_parameter_types_object("CallNonvirtualIntMethod", obj, methodID, arg1, 0, 3);
14363 self.check_parameter_types_object("CallNonvirtualIntMethod", obj, methodID, arg2, 1, 3);
14364 self.check_parameter_types_object("CallNonvirtualIntMethod", obj, methodID, arg3, 2, 3);
14365 }
14366 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jint>(79)(self.vtable, obj, class, methodID, arg1, arg2, arg3)
14367 }
14368 }
14369
14370 ///
14371 /// Calls a non-static java method with 3 arguments that returns long without using the objects vtable to look up the method.
14372 /// This means that should the object be a subclass of the class that the method is declared in
14373 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14374 ///
14375 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14376 ///
14377 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14378 ///
14379 ///
14380 /// # Arguments
14381 /// * `obj` - which object the method should be called on
14382 /// * must be valid
14383 /// * must not be null
14384 /// * must not be already garbage collected
14385 /// * `methodID` - method id of the method
14386 /// * must not be null
14387 /// * must be valid
14388 /// * must not be a static
14389 /// * must actually be a method of `obj`
14390 /// * `args` - argument pointer
14391 /// * can be null if the method has no arguments
14392 /// * must not be null otherwise and point to the exact number of arguments the method expects
14393 ///
14394 /// # Returns
14395 /// Whatever the method returned or 0 if it threw
14396 ///
14397 /// # Throws Java Exception
14398 /// * Whatever the method threw
14399 ///
14400 ///
14401 /// # Panics
14402 /// if asserts feature is enabled and UB was detected
14403 ///
14404 /// # Safety
14405 ///
14406 /// Current thread must not be detached from JNI.
14407 ///
14408 /// Current thread must not be currently throwing an exception.
14409 ///
14410 /// Current thread does not hold a critical reference.
14411 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14412 ///
14413 /// `obj` must a valid and not already garbage collected.
14414 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a long
14415 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
14416 /// `args` union must contain types that match the java methods parameters.
14417 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
14418 ///
14419 pub unsafe fn CallNonvirtualLongMethodA(&self, obj: jobject, class: jclass, methodID: jmethodID, args: *const jtype) -> jlong {
14420 unsafe {
14421 #[cfg(feature = "asserts")]
14422 {
14423 self.check_not_critical("CallNonvirtualLongMethodA");
14424 self.check_no_exception("CallNonvirtualLongMethodA");
14425 self.check_return_type_object("CallNonvirtualLongMethodA", obj, methodID, "long");
14426 self.check_is_class("CallNonvirtualLongMethodA", class);
14427 }
14428 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jclass, jmethodID, *const jtype) -> jlong>(84)(self.vtable, obj, class, methodID, args)
14429 }
14430 }
14431
14432 ///
14433 /// Calls a non-static java method with 0 arguments that returns long without using the objects vtable to look up the method.
14434 /// This means that should the object be a subclass of the class that the method is declared in
14435 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14436 ///
14437 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14438 ///
14439 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14440 ///
14441 ///
14442 /// # Arguments
14443 /// * `obj` - which object the method should be called on
14444 /// * must be valid
14445 /// * must not be null
14446 /// * must not be already garbage collected
14447 /// * `methodID` - method id of the method
14448 /// * must not be null
14449 /// * must be valid
14450 /// * must not be a static
14451 /// * must actually be a method of `obj`
14452 /// * must refer to a method with 0 arguments
14453 ///
14454 /// # Returns
14455 /// Whatever the method returned or 0 if it threw
14456 ///
14457 /// # Throws Java Exception
14458 /// * Whatever the method threw
14459 ///
14460 ///
14461 /// # Panics
14462 /// if asserts feature is enabled and UB was detected
14463 ///
14464 /// # Safety
14465 ///
14466 /// Current thread must not be detached from JNI.
14467 ///
14468 /// Current thread must not be currently throwing an exception.
14469 ///
14470 /// Current thread does not hold a critical reference.
14471 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14472 ///
14473 /// `obj` must a valid and not already garbage collected.
14474 /// `methodID` must be valid, non-static and actually be a method of `obj`, return long and have 0 arguments
14475 ///
14476 pub unsafe fn CallNonvirtualLongMethod0(&self, obj: jobject, class: jclass, methodID: jmethodID) -> jlong {
14477 unsafe {
14478 #[cfg(feature = "asserts")]
14479 {
14480 self.check_not_critical("CallNonvirtualLongMethod");
14481 self.check_no_exception("CallNonvirtualLongMethod");
14482 self.check_return_type_object("CallNonvirtualLongMethod", obj, methodID, "long");
14483 self.check_is_class("CallNonvirtualLongMethod", class);
14484 }
14485 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID) -> jlong>(82)(self.vtable, obj, class, methodID)
14486 }
14487 }
14488
14489 ///
14490 /// Calls a non-static java method with 1 arguments that returns long without using the objects vtable to look up the method.
14491 /// This means that should the object be a subclass of the class that the method is declared in
14492 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14493 ///
14494 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14495 ///
14496 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14497 ///
14498 ///
14499 /// # Arguments
14500 /// * `obj` - which object the method should be called on
14501 /// * must be valid
14502 /// * must not be null
14503 /// * must not be already garbage collected
14504 /// * `methodID` - method id of the method
14505 /// * must not be null
14506 /// * must be valid
14507 /// * must not be a static
14508 /// * must actually be a method of `obj`
14509 /// * must refer to a method with 1 arguments
14510 ///
14511 /// # Returns
14512 /// Whatever the method returned or 0 if it threw
14513 ///
14514 /// # Throws Java Exception
14515 /// * Whatever the method threw
14516 ///
14517 ///
14518 /// # Panics
14519 /// if asserts feature is enabled and UB was detected
14520 ///
14521 /// # Safety
14522 ///
14523 /// Current thread must not be detached from JNI.
14524 ///
14525 /// Current thread must not be currently throwing an exception.
14526 ///
14527 /// Current thread does not hold a critical reference.
14528 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14529 ///
14530 /// `obj` must a valid and not already garbage collected.
14531 /// `methodID` must be valid, non-static and actually be a method of `obj`, return long and have 1 arguments
14532 ///
14533 pub unsafe fn CallNonvirtualLongMethod1<A: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A) -> jlong {
14534 unsafe {
14535 #[cfg(feature = "asserts")]
14536 {
14537 self.check_not_critical("CallNonvirtualLongMethod");
14538 self.check_no_exception("CallNonvirtualLongMethod");
14539 self.check_return_type_object("CallNonvirtualLongMethod", obj, methodID, "long");
14540 self.check_is_class("CallNonvirtualLongMethod", class);
14541 self.check_parameter_types_object("CallNonvirtualLongMethod", obj, methodID, arg1, 0, 1);
14542 }
14543 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jlong>(82)(self.vtable, obj, class, methodID, arg1)
14544 }
14545 }
14546
14547 ///
14548 /// Calls a non-static java method with 2 arguments that returns long without using the objects vtable to look up the method.
14549 /// This means that should the object be a subclass of the class that the method is declared in
14550 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14551 ///
14552 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14553 ///
14554 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14555 ///
14556 ///
14557 /// # Arguments
14558 /// * `obj` - which object the method should be called on
14559 /// * must be valid
14560 /// * must not be null
14561 /// * must not be already garbage collected
14562 /// * `methodID` - method id of the method
14563 /// * must not be null
14564 /// * must be valid
14565 /// * must not be a static
14566 /// * must actually be a method of `obj`
14567 /// * must refer to a method with 2 arguments
14568 ///
14569 /// # Returns
14570 /// Whatever the method returned or 0 if it threw
14571 ///
14572 /// # Throws Java Exception
14573 /// * Whatever the method threw
14574 ///
14575 ///
14576 /// # Panics
14577 /// if asserts feature is enabled and UB was detected
14578 ///
14579 /// # Safety
14580 ///
14581 /// Current thread must not be detached from JNI.
14582 ///
14583 /// Current thread must not be currently throwing an exception.
14584 ///
14585 /// Current thread does not hold a critical reference.
14586 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14587 ///
14588 /// `obj` must a valid and not already garbage collected.
14589 /// `methodID` must be valid, non-static and actually be a method of `obj`, return long and have 2 arguments
14590 ///
14591 pub unsafe fn CallNonvirtualLongMethod2<A: JType, B: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jlong {
14592 unsafe {
14593 #[cfg(feature = "asserts")]
14594 {
14595 self.check_not_critical("CallNonvirtualLongMethod");
14596 self.check_no_exception("CallNonvirtualLongMethod");
14597 self.check_return_type_object("CallNonvirtualLongMethod", obj, methodID, "long");
14598 self.check_is_class("CallNonvirtualLongMethod", class);
14599 self.check_parameter_types_object("CallNonvirtualLongMethod", obj, methodID, arg1, 0, 2);
14600 self.check_parameter_types_object("CallNonvirtualLongMethod", obj, methodID, arg2, 1, 2);
14601 }
14602 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jlong>(82)(self.vtable, obj, class, methodID, arg1, arg2)
14603 }
14604 }
14605
14606 ///
14607 /// Calls a non-static java method with 3 arguments that returns long without using the objects vtable to look up the method.
14608 /// This means that should the object be a subclass of the class that the method is declared in
14609 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14610 ///
14611 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14612 ///
14613 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14614 ///
14615 ///
14616 /// # Arguments
14617 /// * `obj` - which object the method should be called on
14618 /// * must be valid
14619 /// * must not be null
14620 /// * must not be already garbage collected
14621 /// * `methodID` - method id of the method
14622 /// * must not be null
14623 /// * must be valid
14624 /// * must not be a static
14625 /// * must actually be a method of `obj`
14626 /// * must refer to a method with 3 arguments
14627 ///
14628 /// # Returns
14629 /// Whatever the method returned or 0 if it threw
14630 ///
14631 /// # Throws Java Exception
14632 /// * Whatever the method threw
14633 ///
14634 ///
14635 /// # Panics
14636 /// if asserts feature is enabled and UB was detected
14637 ///
14638 /// # Safety
14639 ///
14640 /// Current thread must not be detached from JNI.
14641 ///
14642 /// Current thread must not be currently throwing an exception.
14643 ///
14644 /// Current thread does not hold a critical reference.
14645 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14646 ///
14647 /// `obj` must a valid and not already garbage collected.
14648 /// `methodID` must be valid, non-static and actually be a method of `obj`, return long and have 3 arguments
14649 ///
14650 pub unsafe fn CallNonvirtualLongMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jlong {
14651 unsafe {
14652 #[cfg(feature = "asserts")]
14653 {
14654 self.check_not_critical("CallNonvirtualLongMethod");
14655 self.check_no_exception("CallNonvirtualLongMethod");
14656 self.check_return_type_object("CallNonvirtualLongMethod", obj, methodID, "long");
14657 self.check_is_class("CallNonvirtualLongMethod", class);
14658 self.check_parameter_types_object("CallNonvirtualLongMethod", obj, methodID, arg1, 0, 3);
14659 self.check_parameter_types_object("CallNonvirtualLongMethod", obj, methodID, arg2, 1, 3);
14660 self.check_parameter_types_object("CallNonvirtualLongMethod", obj, methodID, arg3, 2, 3);
14661 }
14662 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jlong>(82)(self.vtable, obj, class, methodID, arg1, arg2, arg3)
14663 }
14664 }
14665
14666 ///
14667 /// Calls a non-static java method with 3 arguments that returns float without using the objects vtable to look up the method.
14668 /// This means that should the object be a subclass of the class that the method is declared in
14669 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14670 ///
14671 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14672 ///
14673 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14674 ///
14675 ///
14676 /// # Arguments
14677 /// * `obj` - which object the method should be called on
14678 /// * must be valid
14679 /// * must not be null
14680 /// * must not be already garbage collected
14681 /// * `methodID` - method id of the method
14682 /// * must not be null
14683 /// * must be valid
14684 /// * must not be a static
14685 /// * must actually be a method of `obj`
14686 /// * `args` - argument pointer
14687 /// * can be null if the method has no arguments
14688 /// * must not be null otherwise and point to the exact number of arguments the method expects
14689 ///
14690 /// # Returns
14691 /// Whatever the method returned or 0 if it threw
14692 ///
14693 /// # Throws Java Exception
14694 /// * Whatever the method threw
14695 ///
14696 ///
14697 /// # Panics
14698 /// if asserts feature is enabled and UB was detected
14699 ///
14700 /// # Safety
14701 ///
14702 /// Current thread must not be detached from JNI.
14703 ///
14704 /// Current thread must not be currently throwing an exception.
14705 ///
14706 /// Current thread does not hold a critical reference.
14707 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14708 ///
14709 /// `obj` must a valid and not already garbage collected.
14710 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a float
14711 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
14712 /// `args` union must contain types that match the java methods parameters.
14713 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
14714 ///
14715 pub unsafe fn CallNonvirtualFloatMethodA(&self, obj: jobject, class: jclass, methodID: jmethodID, args: *const jtype) -> jfloat {
14716 unsafe {
14717 #[cfg(feature = "asserts")]
14718 {
14719 self.check_not_critical("CallNonvirtualFloatMethodA");
14720 self.check_no_exception("CallNonvirtualFloatMethodA");
14721 self.check_return_type_object("CallNonvirtualFloatMethodA", obj, methodID, "float");
14722 self.check_is_class("CallNonvirtualFloatMethodA", class);
14723 }
14724 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jclass, jmethodID, *const jtype) -> jfloat>(87)(self.vtable, obj, class, methodID, args)
14725 }
14726 }
14727
14728 ///
14729 /// Calls a non-static java method with 0 arguments that returns float without using the objects vtable to look up the method.
14730 /// This means that should the object be a subclass of the class that the method is declared in
14731 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14732 ///
14733 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14734 ///
14735 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14736 ///
14737 ///
14738 /// # Arguments
14739 /// * `obj` - which object the method should be called on
14740 /// * must be valid
14741 /// * must not be null
14742 /// * must not be already garbage collected
14743 /// * `methodID` - method id of the method
14744 /// * must not be null
14745 /// * must be valid
14746 /// * must not be a static
14747 /// * must actually be a method of `obj`
14748 /// * must refer to a method with 0 arguments
14749 ///
14750 /// # Returns
14751 /// Whatever the method returned or 0 if it threw
14752 ///
14753 /// # Throws Java Exception
14754 /// * Whatever the method threw
14755 ///
14756 ///
14757 /// # Panics
14758 /// if asserts feature is enabled and UB was detected
14759 ///
14760 /// # Safety
14761 ///
14762 /// Current thread must not be detached from JNI.
14763 ///
14764 /// Current thread must not be currently throwing an exception.
14765 ///
14766 /// Current thread does not hold a critical reference.
14767 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14768 ///
14769 /// `obj` must a valid and not already garbage collected.
14770 /// `methodID` must be valid, non-static and actually be a method of `obj`, return float and have 0 arguments
14771 ///
14772 pub unsafe fn CallNonvirtualFloatMethod0(&self, obj: jobject, class: jclass, methodID: jmethodID) -> jfloat {
14773 unsafe {
14774 #[cfg(feature = "asserts")]
14775 {
14776 self.check_not_critical("CallNonvirtualFloatMethod");
14777 self.check_no_exception("CallNonvirtualFloatMethod");
14778 self.check_return_type_object("CallNonvirtualFloatMethod", obj, methodID, "float");
14779 self.check_is_class("CallNonvirtualFloatMethod", class);
14780 }
14781 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID) -> jfloat>(85)(self.vtable, obj, class, methodID)
14782 }
14783 }
14784
14785 ///
14786 /// Calls a non-static java method with 1 arguments that returns float without using the objects vtable to look up the method.
14787 /// This means that should the object be a subclass of the class that the method is declared in
14788 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14789 ///
14790 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14791 ///
14792 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14793 ///
14794 ///
14795 /// # Arguments
14796 /// * `obj` - which object the method should be called on
14797 /// * must be valid
14798 /// * must not be null
14799 /// * must not be already garbage collected
14800 /// * `methodID` - method id of the method
14801 /// * must not be null
14802 /// * must be valid
14803 /// * must not be a static
14804 /// * must actually be a method of `obj`
14805 /// * must refer to a method with 1 arguments
14806 ///
14807 /// # Returns
14808 /// Whatever the method returned or 0 if it threw
14809 ///
14810 /// # Throws Java Exception
14811 /// * Whatever the method threw
14812 ///
14813 ///
14814 /// # Panics
14815 /// if asserts feature is enabled and UB was detected
14816 ///
14817 /// # Safety
14818 ///
14819 /// Current thread must not be detached from JNI.
14820 ///
14821 /// Current thread must not be currently throwing an exception.
14822 ///
14823 /// Current thread does not hold a critical reference.
14824 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14825 ///
14826 /// `obj` must a valid and not already garbage collected.
14827 /// `methodID` must be valid, non-static and actually be a method of `obj`, return float and have 1 arguments
14828 ///
14829 pub unsafe fn CallNonvirtualFloatMethod1<A: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A) -> jfloat {
14830 unsafe {
14831 #[cfg(feature = "asserts")]
14832 {
14833 self.check_not_critical("CallNonvirtualFloatMethod");
14834 self.check_no_exception("CallNonvirtualFloatMethod");
14835 self.check_return_type_object("CallNonvirtualFloatMethod", obj, methodID, "float");
14836 self.check_is_class("CallNonvirtualFloatMethod", class);
14837 self.check_parameter_types_object("CallNonvirtualFloatMethod", obj, methodID, arg1, 0, 1);
14838 }
14839 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jfloat>(85)(self.vtable, obj, class, methodID, arg1)
14840 }
14841 }
14842
14843 ///
14844 /// Calls a non-static java method with 2 arguments that returns float without using the objects vtable to look up the method.
14845 /// This means that should the object be a subclass of the class that the method is declared in
14846 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14847 ///
14848 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14849 ///
14850 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14851 ///
14852 ///
14853 /// # Arguments
14854 /// * `obj` - which object the method should be called on
14855 /// * must be valid
14856 /// * must not be null
14857 /// * must not be already garbage collected
14858 /// * `methodID` - method id of the method
14859 /// * must not be null
14860 /// * must be valid
14861 /// * must not be a static
14862 /// * must actually be a method of `obj`
14863 /// * must refer to a method with 2 arguments
14864 ///
14865 /// # Returns
14866 /// Whatever the method returned or 0 if it threw
14867 ///
14868 /// # Throws Java Exception
14869 /// * Whatever the method threw
14870 ///
14871 ///
14872 /// # Panics
14873 /// if asserts feature is enabled and UB was detected
14874 ///
14875 /// # Safety
14876 ///
14877 /// Current thread must not be detached from JNI.
14878 ///
14879 /// Current thread must not be currently throwing an exception.
14880 ///
14881 /// Current thread does not hold a critical reference.
14882 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14883 ///
14884 /// `obj` must a valid and not already garbage collected.
14885 /// `methodID` must be valid, non-static and actually be a method of `obj`, return float and have 2 arguments
14886 ///
14887 pub unsafe fn CallNonvirtualFloatMethod2<A: JType, B: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jfloat {
14888 unsafe {
14889 #[cfg(feature = "asserts")]
14890 {
14891 self.check_not_critical("CallNonvirtualFloatMethod");
14892 self.check_no_exception("CallNonvirtualFloatMethod");
14893 self.check_return_type_object("CallNonvirtualFloatMethod", obj, methodID, "float");
14894 self.check_is_class("CallNonvirtualFloatMethod", class);
14895 self.check_parameter_types_object("CallNonvirtualFloatMethod", obj, methodID, arg1, 0, 2);
14896 self.check_parameter_types_object("CallNonvirtualFloatMethod", obj, methodID, arg2, 1, 2);
14897 }
14898 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jfloat>(85)(self.vtable, obj, class, methodID, arg1, arg2)
14899 }
14900 }
14901
14902 ///
14903 /// Calls a non-static java method with 3 arguments that returns float without using the objects vtable to look up the method.
14904 /// This means that should the object be a subclass of the class that the method is declared in
14905 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14906 ///
14907 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14908 ///
14909 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14910 ///
14911 ///
14912 /// # Arguments
14913 /// * `obj` - which object the method should be called on
14914 /// * must be valid
14915 /// * must not be null
14916 /// * must not be already garbage collected
14917 /// * `methodID` - method id of the method
14918 /// * must not be null
14919 /// * must be valid
14920 /// * must not be a static
14921 /// * must actually be a method of `obj`
14922 /// * must refer to a method with 3 arguments
14923 ///
14924 /// # Returns
14925 /// Whatever the method returned or 0 if it threw
14926 ///
14927 /// # Throws Java Exception
14928 /// * Whatever the method threw
14929 ///
14930 ///
14931 /// # Panics
14932 /// if asserts feature is enabled and UB was detected
14933 ///
14934 /// # Safety
14935 ///
14936 /// Current thread must not be detached from JNI.
14937 ///
14938 /// Current thread must not be currently throwing an exception.
14939 ///
14940 /// Current thread does not hold a critical reference.
14941 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
14942 ///
14943 /// `obj` must a valid and not already garbage collected.
14944 /// `methodID` must be valid, non-static and actually be a method of `obj`, return float and have 3 arguments
14945 ///
14946 pub unsafe fn CallNonvirtualFloatMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jfloat {
14947 unsafe {
14948 #[cfg(feature = "asserts")]
14949 {
14950 self.check_not_critical("CallNonvirtualFloatMethod");
14951 self.check_no_exception("CallNonvirtualFloatMethod");
14952 self.check_return_type_object("CallNonvirtualFloatMethod", obj, methodID, "float");
14953 self.check_is_class("CallNonvirtualFloatMethod", class);
14954 self.check_parameter_types_object("CallNonvirtualFloatMethod", obj, methodID, arg1, 0, 3);
14955 self.check_parameter_types_object("CallNonvirtualFloatMethod", obj, methodID, arg2, 1, 3);
14956 self.check_parameter_types_object("CallNonvirtualFloatMethod", obj, methodID, arg3, 2, 3);
14957 }
14958 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jfloat>(85)(self.vtable, obj, class, methodID, arg1, arg2, arg3)
14959 }
14960 }
14961
14962 ///
14963 /// Calls a non-static java method with 3 arguments that returns double without using the objects vtable to look up the method.
14964 /// This means that should the object be a subclass of the class that the method is declared in
14965 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
14966 ///
14967 /// This is roughly equivalent to calling "super.someMethod(...)" in java
14968 ///
14969 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
14970 ///
14971 ///
14972 /// # Arguments
14973 /// * `obj` - which object the method should be called on
14974 /// * must be valid
14975 /// * must not be null
14976 /// * must not be already garbage collected
14977 /// * `methodID` - method id of the method
14978 /// * must not be null
14979 /// * must be valid
14980 /// * must not be a static
14981 /// * must actually be a method of `obj`
14982 /// * `args` - argument pointer
14983 /// * can be null if the method has no arguments
14984 /// * must not be null otherwise and point to the exact number of arguments the method expects
14985 ///
14986 /// # Returns
14987 /// Whatever the method returned or 0 if it threw
14988 ///
14989 /// # Throws Java Exception
14990 /// * Whatever the method threw
14991 ///
14992 ///
14993 /// # Panics
14994 /// if asserts feature is enabled and UB was detected
14995 ///
14996 /// # Safety
14997 ///
14998 /// Current thread must not be detached from JNI.
14999 ///
15000 /// Current thread must not be currently throwing an exception.
15001 ///
15002 /// Current thread does not hold a critical reference.
15003 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15004 ///
15005 /// `obj` must a valid and not already garbage collected.
15006 /// `methodID` must be valid, non-static and actually be a method of `obj` and return a double
15007 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
15008 /// `args` union must contain types that match the java methods parameters.
15009 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
15010 ///
15011 pub unsafe fn CallNonvirtualDoubleMethodA(&self, obj: jobject, class: jclass, methodID: jmethodID, args: *const jtype) -> jdouble {
15012 unsafe {
15013 #[cfg(feature = "asserts")]
15014 {
15015 self.check_not_critical("CallNonvirtualDoubleMethodA");
15016 self.check_no_exception("CallNonvirtualDoubleMethodA");
15017 self.check_return_type_object("CallNonvirtualDoubleMethodA", obj, methodID, "double");
15018 self.check_is_class("CallNonvirtualDoubleMethodA", class);
15019 }
15020 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jclass, jmethodID, *const jtype) -> jdouble>(90)(self.vtable, obj, class, methodID, args)
15021 }
15022 }
15023
15024 ///
15025 /// Calls a non-static java method with 0 arguments that returns double without using the objects vtable to look up the method.
15026 /// This means that should the object be a subclass of the class that the method is declared in
15027 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
15028 ///
15029 /// This is roughly equivalent to calling "super.someMethod(...)" in java
15030 ///
15031 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
15032 ///
15033 ///
15034 /// # Arguments
15035 /// * `obj` - which object the method should be called on
15036 /// * must be valid
15037 /// * must not be null
15038 /// * must not be already garbage collected
15039 /// * `methodID` - method id of the method
15040 /// * must not be null
15041 /// * must be valid
15042 /// * must not be a static
15043 /// * must actually be a method of `obj`
15044 /// * must refer to a method with 0 arguments
15045 ///
15046 /// # Returns
15047 /// Whatever the method returned or 0 if it threw
15048 ///
15049 /// # Throws Java Exception
15050 /// * Whatever the method threw
15051 ///
15052 ///
15053 /// # Panics
15054 /// if asserts feature is enabled and UB was detected
15055 ///
15056 /// # Safety
15057 ///
15058 /// Current thread must not be detached from JNI.
15059 ///
15060 /// Current thread must not be currently throwing an exception.
15061 ///
15062 /// Current thread does not hold a critical reference.
15063 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15064 ///
15065 /// `obj` must a valid and not already garbage collected.
15066 /// `methodID` must be valid, non-static and actually be a method of `obj`, return double and have 0 arguments
15067 ///
15068 pub unsafe fn CallNonvirtualDoubleMethod0(&self, obj: jobject, class: jclass, methodID: jmethodID) -> jdouble {
15069 unsafe {
15070 #[cfg(feature = "asserts")]
15071 {
15072 self.check_not_critical("CallNonvirtualDoubleMethod");
15073 self.check_no_exception("CallNonvirtualDoubleMethod");
15074 self.check_return_type_object("CallNonvirtualDoubleMethod", obj, methodID, "double");
15075 self.check_is_class("CallNonvirtualDoubleMethod", class);
15076 }
15077 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID) -> jdouble>(88)(self.vtable, obj, class, methodID)
15078 }
15079 }
15080
15081 ///
15082 /// Calls a non-static java method with 1 arguments that returns double without using the objects vtable to look up the method.
15083 /// This means that should the object be a subclass of the class that the method is declared in
15084 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
15085 ///
15086 /// This is roughly equivalent to calling "super.someMethod(...)" in java
15087 ///
15088 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
15089 ///
15090 ///
15091 /// # Arguments
15092 /// * `obj` - which object the method should be called on
15093 /// * must be valid
15094 /// * must not be null
15095 /// * must not be already garbage collected
15096 /// * `methodID` - method id of the method
15097 /// * must not be null
15098 /// * must be valid
15099 /// * must not be a static
15100 /// * must actually be a method of `obj`
15101 /// * must refer to a method with 1 arguments
15102 ///
15103 /// # Returns
15104 /// Whatever the method returned or 0 if it threw
15105 ///
15106 /// # Throws Java Exception
15107 /// * Whatever the method threw
15108 ///
15109 ///
15110 /// # Panics
15111 /// if asserts feature is enabled and UB was detected
15112 ///
15113 /// # Safety
15114 ///
15115 /// Current thread must not be detached from JNI.
15116 ///
15117 /// Current thread must not be currently throwing an exception.
15118 ///
15119 /// Current thread does not hold a critical reference.
15120 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15121 ///
15122 /// `obj` must a valid and not already garbage collected.
15123 /// `methodID` must be valid, non-static and actually be a method of `obj`, return double and have 1 arguments
15124 ///
15125 pub unsafe fn CallNonvirtualDoubleMethod1<A: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A) -> jdouble {
15126 unsafe {
15127 #[cfg(feature = "asserts")]
15128 {
15129 self.check_not_critical("CallNonvirtualDoubleMethod");
15130 self.check_no_exception("CallNonvirtualDoubleMethod");
15131 self.check_return_type_object("CallNonvirtualDoubleMethod", obj, methodID, "double");
15132 self.check_is_class("CallNonvirtualDoubleMethod", class);
15133 self.check_parameter_types_object("CallNonvirtualDoubleMethod", obj, methodID, arg1, 0, 1);
15134 }
15135 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jdouble>(88)(self.vtable, obj, class, methodID, arg1)
15136 }
15137 }
15138
15139 ///
15140 /// Calls a non-static java method with 2 arguments that returns double without using the objects vtable to look up the method.
15141 /// This means that should the object be a subclass of the class that the method is declared in
15142 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
15143 ///
15144 /// This is roughly equivalent to calling "super.someMethod(...)" in java
15145 ///
15146 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
15147 ///
15148 ///
15149 /// # Arguments
15150 /// * `obj` - which object the method should be called on
15151 /// * must be valid
15152 /// * must not be null
15153 /// * must not be already garbage collected
15154 /// * `methodID` - method id of the method
15155 /// * must not be null
15156 /// * must be valid
15157 /// * must not be a static
15158 /// * must actually be a method of `obj`
15159 /// * must refer to a method with 2 arguments
15160 ///
15161 /// # Returns
15162 /// Whatever the method returned or 0 if it threw
15163 ///
15164 /// # Throws Java Exception
15165 /// * Whatever the method threw
15166 ///
15167 ///
15168 /// # Panics
15169 /// if asserts feature is enabled and UB was detected
15170 ///
15171 /// # Safety
15172 ///
15173 /// Current thread must not be detached from JNI.
15174 ///
15175 /// Current thread must not be currently throwing an exception.
15176 ///
15177 /// Current thread does not hold a critical reference.
15178 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15179 ///
15180 /// `obj` must a valid and not already garbage collected.
15181 /// `methodID` must be valid, non-static and actually be a method of `obj`, return double and have 2 arguments
15182 ///
15183 pub unsafe fn CallNonvirtualDoubleMethod2<A: JType, B: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jdouble {
15184 unsafe {
15185 #[cfg(feature = "asserts")]
15186 {
15187 self.check_not_critical("CallNonvirtualDoubleMethod");
15188 self.check_no_exception("CallNonvirtualDoubleMethod");
15189 self.check_return_type_object("CallNonvirtualDoubleMethod", obj, methodID, "double");
15190 self.check_is_class("CallNonvirtualDoubleMethod", class);
15191 self.check_parameter_types_object("CallNonvirtualDoubleMethod", obj, methodID, arg1, 0, 2);
15192 self.check_parameter_types_object("CallNonvirtualDoubleMethod", obj, methodID, arg2, 1, 2);
15193 }
15194 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jdouble>(88)(self.vtable, obj, class, methodID, arg1, arg2)
15195 }
15196 }
15197
15198 ///
15199 /// Calls a non-static java method with 3 arguments that returns double without using the objects vtable to look up the method.
15200 /// This means that should the object be a subclass of the class that the method is declared in
15201 /// then the base method that the methodID refers to is invoked instead of a potentially overwritten one.
15202 ///
15203 /// This is roughly equivalent to calling "super.someMethod(...)" in java
15204 ///
15205 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallNonvirtual_type_Method_routines>
15206 ///
15207 ///
15208 /// # Arguments
15209 /// * `obj` - which object the method should be called on
15210 /// * must be valid
15211 /// * must not be null
15212 /// * must not be already garbage collected
15213 /// * `methodID` - method id of the method
15214 /// * must not be null
15215 /// * must be valid
15216 /// * must not be a static
15217 /// * must actually be a method of `obj`
15218 /// * must refer to a method with 3 arguments
15219 ///
15220 /// # Returns
15221 /// Whatever the method returned or 0 if it threw
15222 ///
15223 /// # Throws Java Exception
15224 /// * Whatever the method threw
15225 ///
15226 ///
15227 /// # Panics
15228 /// if asserts feature is enabled and UB was detected
15229 ///
15230 /// # Safety
15231 ///
15232 /// Current thread must not be detached from JNI.
15233 ///
15234 /// Current thread must not be currently throwing an exception.
15235 ///
15236 /// Current thread does not hold a critical reference.
15237 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15238 ///
15239 /// `obj` must a valid and not already garbage collected.
15240 /// `methodID` must be valid, non-static and actually be a method of `obj`, return double and have 3 arguments
15241 ///
15242 pub unsafe fn CallNonvirtualDoubleMethod3<A: JType, B: JType, C: JType>(&self, obj: jobject, class: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jdouble {
15243 unsafe {
15244 #[cfg(feature = "asserts")]
15245 {
15246 self.check_not_critical("CallNonvirtualDoubleMethod");
15247 self.check_no_exception("CallNonvirtualDoubleMethod");
15248 self.check_return_type_object("CallNonvirtualDoubleMethod", obj, methodID, "double");
15249 self.check_is_class("CallNonvirtualDoubleMethod", class);
15250 self.check_parameter_types_object("CallNonvirtualDoubleMethod", obj, methodID, arg1, 0, 3);
15251 self.check_parameter_types_object("CallNonvirtualDoubleMethod", obj, methodID, arg2, 1, 3);
15252 self.check_parameter_types_object("CallNonvirtualDoubleMethod", obj, methodID, arg3, 2, 3);
15253 }
15254 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jclass, jmethodID, ...) -> jdouble>(88)(self.vtable, obj, class, methodID, arg1, arg2, arg3)
15255 }
15256 }
15257
15258 ///
15259 /// Gets the field id of a static field
15260 ///
15261 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStaticFieldID>
15262 ///
15263 ///
15264 /// # Arguments
15265 /// * `clazz` - reference to the clazz where the field is declared in.
15266 /// * must be valid
15267 /// * must not be null
15268 /// * must not be already garbage collected
15269 /// * `name` - name of the field
15270 /// * must not be null
15271 /// * must be zero terminated utf-8
15272 /// * `sig` - jni signature of the field
15273 /// * must not be null
15274 /// * must be zero terminated utf-8
15275 ///
15276 /// # Returns
15277 /// A non-null field handle or null on error.
15278 /// The field handle can be assumed to be constant for the given class and must not be freed.
15279 /// It can also be safely shared with any thread or stored in a constant.
15280 ///
15281 /// # Throws Java Exception
15282 /// * `NoSuchFieldError` - field with the given name and sig doesn't exist in the class
15283 /// * `ExceptionInInitializerError` - Exception occurs in initializer of the class
15284 /// * `OutOfMemoryError` - if the jvm runs out of memory
15285 ///
15286 ///
15287 /// # Panics
15288 /// if asserts feature is enabled and UB was detected
15289 ///
15290 /// # Safety
15291 ///
15292 /// Current thread must not be detached from JNI.
15293 ///
15294 /// Current thread must not be currently throwing an exception.
15295 ///
15296 /// Current thread does not hold a critical reference.
15297 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15298 ///
15299 /// `clazz` must a valid reference to a class that is not already garbage collected.
15300 /// `name` must be non-null and zero terminated utf-8.
15301 /// `sig` must be non-null and zero terminated utf-8.
15302 ///
15303 pub unsafe fn GetStaticFieldID(&self, clazz: jclass, name: impl UseCString, sig: impl UseCString) -> jfieldID {
15304 unsafe {
15305 name.use_as_const_c_char(|name| {
15306 sig.use_as_const_c_char(|sig| {
15307 #[cfg(feature = "asserts")]
15308 {
15309 self.check_not_critical("GetStaticFieldID");
15310 self.check_no_exception("GetStaticFieldID");
15311 assert!(!name.is_null(), "GetStaticFieldID name is null");
15312 assert!(!sig.is_null(), "GetStaticFieldID sig is null");
15313 self.check_is_class("GetStaticFieldID", clazz);
15314 }
15315 self.jni::<extern "system" fn(JNIEnvVTable, jclass, *const c_char, *const c_char) -> jfieldID>(144)(self.vtable, clazz, name, sig)
15316 })
15317 })
15318 }
15319 }
15320
15321 ///
15322 /// Returns a local reference from a static field.
15323 ///
15324 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStatic_type_Field_routines>
15325 ///
15326 ///
15327 /// # Arguments
15328 /// * `obj` - reference to the class the field is in
15329 /// * must be valid
15330 /// * must not be null
15331 /// * must not be already garbage collected
15332 /// * `fieldID` - the field to get
15333 /// * must be valid
15334 /// * must be an object field
15335 ///
15336 /// # Returns
15337 /// A local reference to the fields value or null if the field is null
15338 ///
15339 ///
15340 /// # Panics
15341 /// if asserts feature is enabled and UB was detected
15342 ///
15343 /// # Safety
15344 ///
15345 /// Current thread must not be detached from JNI.
15346 ///
15347 /// Current thread must not be currently throwing an exception.
15348 ///
15349 /// Current thread does not hold a critical reference.
15350 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15351 ///
15352 /// `obj` must a valid reference to a class that is not already garbage collected.
15353 /// `fieldID` must be a fieldID of a field located in `obj` class and not some other unrelated class
15354 /// `fieldID` must be from a static field
15355 /// `fieldID` must refer to a field that is an object and not a primitive.
15356 ///
15357 pub unsafe fn GetStaticObjectField(&self, obj: jclass, fieldID: jfieldID) -> jobject {
15358 unsafe {
15359 #[cfg(feature = "asserts")]
15360 {
15361 self.check_not_critical("GetStaticObjectField");
15362 self.check_no_exception("GetStaticObjectField");
15363 self.check_field_type_static("GetStaticObjectField", obj, fieldID, "object");
15364 }
15365 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jobject>(145)(self.vtable, obj, fieldID)
15366 }
15367 }
15368
15369 ///
15370 /// Returns a boolean from a static field.
15371 ///
15372 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStatic_type_Field_routines>
15373 ///
15374 ///
15375 /// # Arguments
15376 /// * `obj` - reference to the class the field is in
15377 /// * must be valid
15378 /// * must not be null
15379 /// * must not be already garbage collected
15380 /// * `fieldID` - the field to get
15381 /// * must be valid
15382 /// * must be a boolean field
15383 ///
15384 /// # Returns
15385 /// The value of the field
15386 ///
15387 ///
15388 /// # Panics
15389 /// if asserts feature is enabled and UB was detected
15390 ///
15391 /// # Safety
15392 ///
15393 /// Current thread must not be detached from JNI.
15394 ///
15395 /// Current thread must not be currently throwing an exception.
15396 ///
15397 /// Current thread does not hold a critical reference.
15398 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15399 ///
15400 /// `obj` must a valid reference to a class that is not already garbage collected.
15401 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15402 /// `fieldID` must be from a static field
15403 /// `fieldID` must refer to a field that is a boolean.
15404 ///
15405 pub unsafe fn GetStaticBooleanField(&self, obj: jclass, fieldID: jfieldID) -> bool {
15406 unsafe {
15407 #[cfg(feature = "asserts")]
15408 {
15409 self.check_not_critical("GetStaticBooleanField");
15410 self.check_no_exception("GetStaticBooleanField");
15411 self.check_field_type_static("GetStaticBooleanField", obj, fieldID, "boolean");
15412 }
15413 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jboolean>(146)(self.vtable, obj, fieldID).as_bool()
15414 }
15415 }
15416
15417 ///
15418 /// Returns a byte from a static field.
15419 ///
15420 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStatic_type_Field_routines>
15421 ///
15422 ///
15423 /// # Arguments
15424 /// * `obj` - reference to the class the field is in
15425 /// * must be valid
15426 /// * must not be null
15427 /// * must not be already garbage collected
15428 /// * `fieldID` - the field to get
15429 /// * must be valid
15430 /// * must be a byte field
15431 ///
15432 /// # Returns
15433 /// The value of the field
15434 ///
15435 ///
15436 /// # Panics
15437 /// if asserts feature is enabled and UB was detected
15438 ///
15439 /// # Safety
15440 ///
15441 /// Current thread must not be detached from JNI.
15442 ///
15443 /// Current thread must not be currently throwing an exception.
15444 ///
15445 /// Current thread does not hold a critical reference.
15446 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15447 ///
15448 /// `obj` must a valid reference to a class that is not already garbage collected.
15449 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15450 /// `fieldID` must be from a static field
15451 /// `fieldID` must refer to a field that is a byte.
15452 ///
15453 pub unsafe fn GetStaticByteField(&self, obj: jclass, fieldID: jfieldID) -> jbyte {
15454 unsafe {
15455 #[cfg(feature = "asserts")]
15456 {
15457 self.check_not_critical("GetStaticByteField");
15458 self.check_no_exception("GetStaticByteField");
15459 self.check_field_type_static("GetStaticByteField", obj, fieldID, "byte");
15460 }
15461 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jbyte>(147)(self.vtable, obj, fieldID)
15462 }
15463 }
15464
15465 ///
15466 /// Returns a char from a static field.
15467 ///
15468 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStatic_type_Field_routines>
15469 ///
15470 ///
15471 /// # Arguments
15472 /// * `obj` - reference to the class the field is in
15473 /// * must be valid
15474 /// * must not be null
15475 /// * must not be already garbage collected
15476 /// * `fieldID` - the field to get
15477 /// * must be valid
15478 /// * must be a char field
15479 ///
15480 /// # Returns
15481 /// The value of the field
15482 ///
15483 ///
15484 /// # Panics
15485 /// if asserts feature is enabled and UB was detected
15486 ///
15487 /// # Safety
15488 ///
15489 /// Current thread must not be detached from JNI.
15490 ///
15491 /// Current thread must not be currently throwing an exception.
15492 ///
15493 /// Current thread does not hold a critical reference.
15494 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15495 ///
15496 /// `obj` must a valid reference to a class that is not already garbage collected.
15497 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15498 /// `fieldID` must be from a static field
15499 /// `fieldID` must refer to a field that is a char.
15500 ///
15501 pub unsafe fn GetStaticCharField(&self, obj: jclass, fieldID: jfieldID) -> jchar {
15502 unsafe {
15503 #[cfg(feature = "asserts")]
15504 {
15505 self.check_not_critical("GetStaticCharField");
15506 self.check_no_exception("GetStaticCharField");
15507 self.check_field_type_static("GetStaticCharField", obj, fieldID, "char");
15508 }
15509 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jchar>(148)(self.vtable, obj, fieldID)
15510 }
15511 }
15512
15513 ///
15514 /// Returns a short from a static field.
15515 ///
15516 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStatic_type_Field_routines>
15517 ///
15518 ///
15519 /// # Arguments
15520 /// * `obj` - reference to the class the field is in
15521 /// * must be valid
15522 /// * must not be null
15523 /// * must not be already garbage collected
15524 /// * `fieldID` - the field to get
15525 /// * must be valid
15526 /// * must be a short field
15527 ///
15528 /// # Returns
15529 /// The value of the field
15530 ///
15531 ///
15532 /// # Panics
15533 /// if asserts feature is enabled and UB was detected
15534 ///
15535 /// # Safety
15536 ///
15537 /// Current thread must not be detached from JNI.
15538 ///
15539 /// Current thread must not be currently throwing an exception.
15540 ///
15541 /// Current thread does not hold a critical reference.
15542 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15543 ///
15544 /// `obj` must a valid reference to a class that is not already garbage collected.
15545 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15546 /// `fieldID` must be from a static field
15547 /// `fieldID` must refer to a field that is a short.
15548 ///
15549 pub unsafe fn GetStaticShortField(&self, obj: jclass, fieldID: jfieldID) -> jshort {
15550 unsafe {
15551 #[cfg(feature = "asserts")]
15552 {
15553 self.check_not_critical("GetStaticShortField");
15554 self.check_no_exception("GetStaticShortField");
15555 self.check_field_type_static("GetStaticShortField", obj, fieldID, "short");
15556 }
15557 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jshort>(149)(self.vtable, obj, fieldID)
15558 }
15559 }
15560
15561 ///
15562 /// Returns a int from a static field.
15563 ///
15564 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStatic_type_Field_routines>
15565 ///
15566 ///
15567 /// # Arguments
15568 /// * `obj` - reference to the class the field is in
15569 /// * must be valid
15570 /// * must not be null
15571 /// * must not be already garbage collected
15572 /// * `fieldID` - the field to get
15573 /// * must be valid
15574 /// * must be a int field
15575 ///
15576 /// # Returns
15577 /// The value of the field
15578 ///
15579 ///
15580 /// # Panics
15581 /// if asserts feature is enabled and UB was detected
15582 ///
15583 /// # Safety
15584 ///
15585 /// Current thread must not be detached from JNI.
15586 ///
15587 /// Current thread must not be currently throwing an exception.
15588 ///
15589 /// Current thread does not hold a critical reference.
15590 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15591 ///
15592 /// `obj` must a valid reference to a class that is not already garbage collected.
15593 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15594 /// `fieldID` must be from a static field
15595 /// `fieldID` must refer to a field that is a int.
15596 ///
15597 pub unsafe fn GetStaticIntField(&self, obj: jclass, fieldID: jfieldID) -> jint {
15598 unsafe {
15599 #[cfg(feature = "asserts")]
15600 {
15601 self.check_not_critical("GetStaticIntField");
15602 self.check_no_exception("GetStaticIntField");
15603 self.check_field_type_static("GetStaticIntField", obj, fieldID, "int");
15604 }
15605 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jint>(150)(self.vtable, obj, fieldID)
15606 }
15607 }
15608
15609 ///
15610 /// Returns a long from a static field.
15611 ///
15612 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStatic_type_Field_routines>
15613 ///
15614 ///
15615 /// # Arguments
15616 /// * `obj` - reference to the class the field is in
15617 /// * must be valid
15618 /// * must not be null
15619 /// * must not be already garbage collected
15620 ///
15621 /// * `fieldID` - the field to get
15622 /// * must be valid
15623 /// * must be a long field
15624 ///
15625 /// # Returns
15626 /// The value of the field
15627 ///
15628 ///
15629 /// # Panics
15630 /// if asserts feature is enabled and UB was detected
15631 ///
15632 /// # Safety
15633 ///
15634 /// Current thread must not be detached from JNI.
15635 ///
15636 /// Current thread must not be currently throwing an exception.
15637 ///
15638 /// Current thread does not hold a critical reference.
15639 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15640 ///
15641 /// `obj` must a valid reference to a class that is not already garbage collected.
15642 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15643 /// `fieldID` must be from a static field
15644 /// `fieldID` must refer to a field that is a long.
15645 ///
15646 pub unsafe fn GetStaticLongField(&self, obj: jclass, fieldID: jfieldID) -> jlong {
15647 unsafe {
15648 #[cfg(feature = "asserts")]
15649 {
15650 self.check_not_critical("GetStaticLongField");
15651 self.check_no_exception("GetStaticLongField");
15652 self.check_field_type_static("GetStaticLongField", obj, fieldID, "long");
15653 }
15654 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jlong>(151)(self.vtable, obj, fieldID)
15655 }
15656 }
15657
15658 ///
15659 /// Returns a float from a static field.
15660 ///
15661 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStatic_type_Field_routines>
15662 ///
15663 ///
15664 /// # Arguments
15665 /// * `obj` - reference to the class the field is in
15666 /// * must be valid
15667 /// * must not be null
15668 /// * must not be already garbage collected
15669 ///
15670 /// * `fieldID` - the field to get
15671 /// * must be valid
15672 /// * must be a float field
15673 ///
15674 /// # Returns
15675 /// The value of the field
15676 ///
15677 ///
15678 /// # Panics
15679 /// if asserts feature is enabled and UB was detected
15680 ///
15681 /// # Safety
15682 ///
15683 /// Current thread must not be detached from JNI.
15684 ///
15685 /// Current thread must not be currently throwing an exception.
15686 ///
15687 /// Current thread does not hold a critical reference.
15688 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15689 ///
15690 /// `obj` must a valid reference to a class that is not already garbage collected.
15691 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15692 /// `fieldID` must be from a static field
15693 /// `fieldID` must refer to a field that is a float.
15694 ///
15695 pub unsafe fn GetStaticFloatField(&self, obj: jclass, fieldID: jfieldID) -> jfloat {
15696 unsafe {
15697 #[cfg(feature = "asserts")]
15698 {
15699 self.check_not_critical("GetStaticFloatField");
15700 self.check_no_exception("GetStaticFloatField");
15701 self.check_field_type_static("GetStaticFloatField", obj, fieldID, "float");
15702 }
15703 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jfloat>(152)(self.vtable, obj, fieldID)
15704 }
15705 }
15706
15707 ///
15708 /// Returns a double from a static field.
15709 ///
15710 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStatic_type_Field_routines>
15711 ///
15712 ///
15713 /// # Arguments
15714 /// * `obj` - reference to the class the field is in
15715 /// * must be valid
15716 /// * must not be null
15717 /// * must not be already garbage collected
15718 ///
15719 /// * `fieldID` - the field to get
15720 /// * must be valid
15721 /// * must be a double field
15722 ///
15723 /// # Returns
15724 /// The value of the field
15725 ///
15726 ///
15727 /// # Panics
15728 /// if asserts feature is enabled and UB was detected
15729 ///
15730 /// # Safety
15731 ///
15732 /// Current thread must not be detached from JNI.
15733 ///
15734 /// Current thread must not be currently throwing an exception.
15735 ///
15736 /// Current thread does not hold a critical reference.
15737 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15738 ///
15739 /// `obj` must a valid reference to a class that is not already garbage collected.
15740 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15741 /// `fieldID` must be from a static field
15742 /// `fieldID` must refer to a field that is a double.
15743 ///
15744 pub unsafe fn GetStaticDoubleField(&self, obj: jclass, fieldID: jfieldID) -> jdouble {
15745 unsafe {
15746 #[cfg(feature = "asserts")]
15747 {
15748 self.check_not_critical("GetStaticDoubleField");
15749 self.check_no_exception("GetStaticDoubleField");
15750 self.check_field_type_static("GetStaticDoubleField", obj, fieldID, "double");
15751 }
15752 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID) -> jdouble>(153)(self.vtable, obj, fieldID)
15753 }
15754 }
15755
15756 ///
15757 /// Sets a static object field to a given value
15758 ///
15759 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#SetStatic_type_Field_routines>
15760 ///
15761 /// # Arguments
15762 /// * `obj` - reference to the object the field is in
15763 /// * must be valid
15764 /// * must not be null
15765 /// * must not be already garbage collected
15766 ///
15767 /// * `fieldID` - the field to set
15768 /// * must be valid
15769 /// * must be a object field
15770 /// * must reside in the object `obj`
15771 ///
15772 /// * `value`
15773 /// * must be null or valid
15774 /// * must not be already garbage collected (if non-null)
15775 /// * must be assignable to the field type (if non-null)
15776 ///
15777 ///
15778 /// # Panics
15779 /// if asserts feature is enabled and UB was detected
15780 ///
15781 /// # Safety
15782 ///
15783 /// Current thread must not be detached from JNI.
15784 ///
15785 /// Current thread must not be currently throwing an exception.
15786 ///
15787 /// Current thread does not hold a critical reference.
15788 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15789 ///
15790 /// `obj` must be a valid reference to the class the field is in that is not already garbage collected.
15791 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15792 /// `fieldID` must be from a static field
15793 /// `fieldID` must refer to a field that is an object and not a primitive.
15794 /// `value` must be a valid reference to the object that is not already garbage collected or it must be null.
15795 /// `value` must be assignable to the field type (i.e. if it's a String field setting to an `ArrayList` for example is UB)
15796 ///
15797 pub unsafe fn SetStaticObjectField(&self, obj: jclass, fieldID: jfieldID, value: jobject) {
15798 unsafe {
15799 #[cfg(feature = "asserts")]
15800 {
15801 self.check_not_critical("SetStaticObjectField");
15802 self.check_no_exception("SetStaticObjectField");
15803 self.check_field_type_static("SetStaticObjectField", obj, fieldID, "object");
15804 }
15805 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jobject)>(154)(self.vtable, obj, fieldID, value);
15806 }
15807 }
15808
15809 ///
15810 /// Sets a static boolean field to a given value
15811 ///
15812 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#SetStatic_type_Field_routines>
15813 ///
15814 /// # Arguments
15815 /// * `obj` - reference to the object the field is in
15816 /// * must be valid
15817 /// * must not be null
15818 /// * must not be already garbage collected
15819 ///
15820 /// * `fieldID` - the field to set
15821 /// * must be valid
15822 /// * must be a object field
15823 /// * must reside in the object `obj`
15824 ///
15825 /// * `value` - that value to set
15826 ///
15827 ///
15828 /// # Panics
15829 /// if asserts feature is enabled and UB was detected
15830 ///
15831 /// # Safety
15832 ///
15833 /// Current thread must not be detached from JNI.
15834 ///
15835 /// Current thread must not be currently throwing an exception.
15836 ///
15837 /// Current thread does not hold a critical reference.
15838 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15839 ///
15840 /// `obj` must be a valid reference to the class the field is in that is not already garbage collected.
15841 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15842 /// `fieldID` must be from a static field
15843 /// `fieldID` must refer to a field that is a boolean.
15844 ///
15845 pub unsafe fn SetStaticBooleanField(&self, obj: jclass, fieldID: jfieldID, value: impl Into<jboolean>) {
15846 let value = value.into();
15847 unsafe {
15848 #[cfg(feature = "asserts")]
15849 {
15850 self.check_not_critical("SetStaticBooleanField");
15851 self.check_no_exception("SetStaticBooleanField");
15852 self.check_field_type_static("SetStaticBooleanField", obj, fieldID, "boolean");
15853 assert!(!value.is_wide(), "SetStaticBooleanField with wide boolean value");
15854 }
15855 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jboolean)>(155)(self.vtable, obj, fieldID, value);
15856 }
15857 }
15858
15859 ///
15860 /// Sets a static byte field to a given value
15861 ///
15862 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#SetStatic_type_Field_routines>
15863 ///
15864 /// # Arguments
15865 /// * `obj` - reference to the object the field is in
15866 /// * must be valid
15867 /// * must not be null
15868 /// * must not be already garbage collected
15869 ///
15870 /// * `fieldID` - the field to set
15871 /// * must be valid
15872 /// * must be a object field
15873 /// * must reside in the object `obj`
15874 ///
15875 /// * `value` - that value to set
15876 ///
15877 ///
15878 /// # Panics
15879 /// if asserts feature is enabled and UB was detected
15880 ///
15881 /// # Safety
15882 ///
15883 /// Current thread must not be detached from JNI.
15884 ///
15885 /// Current thread must not be currently throwing an exception.
15886 ///
15887 /// Current thread does not hold a critical reference.
15888 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15889 ///
15890 /// `obj` must be a valid reference to the class the field is in that is not already garbage collected.
15891 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15892 /// `fieldID` must be from a static field
15893 /// `fieldID` must refer to a field that is a byte.
15894 ///
15895 pub unsafe fn SetStaticByteField(&self, obj: jclass, fieldID: jfieldID, value: jbyte) {
15896 unsafe {
15897 #[cfg(feature = "asserts")]
15898 {
15899 self.check_not_critical("SetStaticByteField");
15900 self.check_no_exception("SetStaticByteField");
15901 self.check_field_type_static("SetStaticByteField", obj, fieldID, "byte");
15902 }
15903 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jbyte)>(156)(self.vtable, obj, fieldID, value);
15904 }
15905 }
15906
15907 ///
15908 /// Sets a static char field to a given value
15909 ///
15910 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#SetStatic_type_Field_routines>
15911 ///
15912 /// # Arguments
15913 /// * `obj` - reference to the object the field is in
15914 /// * must be valid
15915 /// * must not be null
15916 /// * must not be already garbage collected
15917 ///
15918 /// * `fieldID` - the field to set
15919 /// * must be valid
15920 /// * must be a object field
15921 /// * must reside in the object `obj`
15922 ///
15923 /// * `value` - that value to set
15924 ///
15925 ///
15926 /// # Panics
15927 /// if asserts feature is enabled and UB was detected
15928 ///
15929 /// # Safety
15930 ///
15931 /// Current thread must not be detached from JNI.
15932 ///
15933 /// Current thread must not be currently throwing an exception.
15934 ///
15935 /// Current thread does not hold a critical reference.
15936 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15937 ///
15938 /// `obj` must be a valid reference to the class the field is in that is not already garbage collected.
15939 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15940 /// `fieldID` must be from a static field
15941 /// `fieldID` must refer to a field that is a char.
15942 ///
15943 pub unsafe fn SetStaticCharField(&self, obj: jclass, fieldID: jfieldID, value: jchar) {
15944 unsafe {
15945 #[cfg(feature = "asserts")]
15946 {
15947 self.check_not_critical("SetStaticCharField");
15948 self.check_no_exception("SetStaticCharField");
15949 self.check_field_type_static("SetStaticCharField", obj, fieldID, "char");
15950 }
15951 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jchar)>(157)(self.vtable, obj, fieldID, value);
15952 }
15953 }
15954
15955 ///
15956 /// Sets a static short field to a given value
15957 ///
15958 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#SetStatic_type_Field_routines>
15959 ///
15960 /// # Arguments
15961 /// * `obj` - reference to the object the field is in
15962 /// * must be valid
15963 /// * must not be null
15964 /// * must not be already garbage collected
15965 ///
15966 /// * `fieldID` - the field to set
15967 /// * must be valid
15968 /// * must be a object field
15969 /// * must reside in the object `obj`
15970 ///
15971 /// * `value` - that value to set
15972 ///
15973 ///
15974 /// # Panics
15975 /// if asserts feature is enabled and UB was detected
15976 ///
15977 /// # Safety
15978 ///
15979 /// Current thread must not be detached from JNI.
15980 ///
15981 /// Current thread must not be currently throwing an exception.
15982 ///
15983 /// Current thread does not hold a critical reference.
15984 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
15985 ///
15986 /// `obj` must be a valid reference to the class the field is in that is not already garbage collected.
15987 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
15988 /// `fieldID` must be from a static field
15989 /// `fieldID` must refer to a field that is a short.
15990 ///
15991 pub unsafe fn SetStaticShortField(&self, obj: jclass, fieldID: jfieldID, value: jshort) {
15992 unsafe {
15993 #[cfg(feature = "asserts")]
15994 {
15995 self.check_not_critical("SetStaticShortField");
15996 self.check_no_exception("SetStaticShortField");
15997 self.check_field_type_static("SetStaticShortField", obj, fieldID, "short");
15998 }
15999 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jshort)>(158)(self.vtable, obj, fieldID, value);
16000 }
16001 }
16002
16003 ///
16004 /// Sets a static int field to a given value
16005 ///
16006 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#SetStatic_type_Field_routines>
16007 ///
16008 /// # Arguments
16009 /// * `obj` - reference to the object the field is in
16010 /// * must be valid
16011 /// * must not be null
16012 /// * must not be already garbage collected
16013 ///
16014 /// * `fieldID` - the field to set
16015 /// * must be valid
16016 /// * must be a object field
16017 /// * must reside in the object `obj`
16018 ///
16019 /// * `value` - that value to set
16020 ///
16021 ///
16022 /// # Panics
16023 /// if asserts feature is enabled and UB was detected
16024 ///
16025 /// # Safety
16026 ///
16027 /// Current thread must not be detached from JNI.
16028 ///
16029 /// Current thread must not be currently throwing an exception.
16030 ///
16031 /// Current thread does not hold a critical reference.
16032 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16033 ///
16034 /// `obj` must be a valid reference to the class the field is in that is not already garbage collected.
16035 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
16036 /// `fieldID` must be from a static field
16037 /// `fieldID` must refer to a field that is a int.
16038 ///
16039 pub unsafe fn SetStaticIntField(&self, obj: jclass, fieldID: jfieldID, value: jint) {
16040 unsafe {
16041 #[cfg(feature = "asserts")]
16042 {
16043 self.check_not_critical("SetStaticIntField");
16044 self.check_no_exception("SetStaticIntField");
16045 self.check_field_type_static("SetStaticIntField", obj, fieldID, "int");
16046 }
16047 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jint)>(159)(self.vtable, obj, fieldID, value);
16048 }
16049 }
16050
16051 ///
16052 /// Sets a static long field to a given value
16053 ///
16054 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#SetStatic_type_Field_routines>
16055 ///
16056 /// # Arguments
16057 /// * `obj` - reference to the object the field is in
16058 /// * must be valid
16059 /// * must not be null
16060 /// * must not be already garbage collected
16061 ///
16062 /// * `fieldID` - the field to set
16063 /// * must be valid
16064 /// * must be a object field
16065 /// * must reside in the object `obj`
16066 ///
16067 /// * `value` - that value to set
16068 ///
16069 ///
16070 /// # Panics
16071 /// if asserts feature is enabled and UB was detected
16072 ///
16073 /// # Safety
16074 ///
16075 /// Current thread must not be detached from JNI.
16076 ///
16077 /// Current thread must not be currently throwing an exception.
16078 ///
16079 /// Current thread does not hold a critical reference.
16080 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16081 ///
16082 /// `obj` must be a valid reference to the class the field is in that is not already garbage collected.
16083 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
16084 /// `fieldID` must be from a static field
16085 /// `fieldID` must refer to a field that is a long.
16086 ///
16087 pub unsafe fn SetStaticLongField(&self, obj: jclass, fieldID: jfieldID, value: jlong) {
16088 unsafe {
16089 #[cfg(feature = "asserts")]
16090 {
16091 self.check_not_critical("SetStaticLongField");
16092 self.check_no_exception("SetStaticLongField");
16093 self.check_field_type_static("SetStaticLongField", obj, fieldID, "long");
16094 }
16095 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jlong)>(160)(self.vtable, obj, fieldID, value);
16096 }
16097 }
16098
16099 ///
16100 /// Sets a static float field to a given value
16101 ///
16102 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#SetStatic_type_Field_routines>
16103 ///
16104 /// # Arguments
16105 /// * `obj` - reference to the object the field is in
16106 /// * must be valid
16107 /// * must not be null
16108 /// * must not be already garbage collected
16109 ///
16110 /// * `fieldID` - the field to set
16111 /// * must be valid
16112 /// * must be a object field
16113 /// * must reside in the object `obj`
16114 ///
16115 /// * `value` - that value to set
16116 ///
16117 ///
16118 /// # Panics
16119 /// if asserts feature is enabled and UB was detected
16120 ///
16121 /// # Safety
16122 ///
16123 /// Current thread must not be detached from JNI.
16124 ///
16125 /// Current thread must not be currently throwing an exception.
16126 ///
16127 /// Current thread does not hold a critical reference.
16128 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16129 ///
16130 /// `obj` must be a valid reference to the class the field is in that is not already garbage collected.
16131 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
16132 /// `fieldID` must be from a static field
16133 /// `fieldID` must refer to a field that is a float.
16134 ///
16135 pub unsafe fn SetStaticFloatField(&self, obj: jclass, fieldID: jfieldID, value: jfloat) {
16136 unsafe {
16137 #[cfg(feature = "asserts")]
16138 {
16139 self.check_not_critical("SetStaticFloatField");
16140 self.check_no_exception("SetStaticFloatField");
16141 self.check_field_type_static("SetStaticFloatField", obj, fieldID, "float");
16142 }
16143 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jfloat)>(161)(self.vtable, obj, fieldID, value);
16144 }
16145 }
16146
16147 ///
16148 /// Sets a static double field to a given value
16149 ///
16150 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#SetStatic_type_Field_routines>
16151 ///
16152 /// # Arguments
16153 /// * `obj` - reference to the object the field is in
16154 /// * must be valid
16155 /// * must not be null
16156 /// * must not be already garbage collected
16157 ///
16158 /// * `fieldID` - the field to set
16159 /// * must be valid
16160 /// * must be a object field
16161 /// * must reside in the object `obj`
16162 ///
16163 /// * `value` - that value to set
16164 ///
16165 ///
16166 /// # Panics
16167 /// if asserts feature is enabled and UB was detected
16168 ///
16169 /// # Safety
16170 ///
16171 /// Current thread must not be detached from JNI.
16172 ///
16173 /// Current thread must not be currently throwing an exception.
16174 ///
16175 /// Current thread does not hold a critical reference.
16176 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16177 ///
16178 /// `obj` must be a valid reference to the class the field is in that is not already garbage collected.
16179 /// `fieldID` must be a fieldID of a field in `obj` and not some other unrelated class
16180 /// `fieldID` must be from a static field
16181 /// `fieldID` must refer to a field that is a double.
16182 ///
16183 pub unsafe fn SetStaticDoubleField(&self, obj: jclass, fieldID: jfieldID, value: jdouble) {
16184 unsafe {
16185 #[cfg(feature = "asserts")]
16186 {
16187 self.check_not_critical("SetStaticDoubleField");
16188 self.check_no_exception("SetStaticDoubleField");
16189 self.check_field_type_static("SetStaticDoubleField", obj, fieldID, "double");
16190 }
16191 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jfieldID, jdouble)>(162)(self.vtable, obj, fieldID, value);
16192 }
16193 }
16194
16195 ///
16196 /// Gets the method id of a static method
16197 ///
16198 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetMethodID>
16199 ///
16200 ///
16201 /// # Arguments
16202 /// * `clazz` - reference to the clazz where the field is declared in.
16203 /// * must be valid
16204 /// * must not be null
16205 /// * must not be already garbage collected
16206 /// * `name` - name of the method
16207 /// * must not be null
16208 /// * must be zero terminated utf-8
16209 /// * `sig` - jni signature of the method
16210 /// * must not be null
16211 /// * must be zero terminated utf-8
16212 ///
16213 /// # Returns
16214 /// A non-null field handle or null on error.
16215 /// The field handle can be assumed to be constant for the given class and must not be freed.
16216 /// It can also be safely shared with any thread or stored in a constant.
16217 ///
16218 /// # Throws Java Exception
16219 /// * `NoSuchMethodError` - method with the given name and sig doesn't exist in the class
16220 /// * `ExceptionInInitializerError` - Exception occurs in initializer of the class
16221 /// * `OutOfMemoryError` - if the jvm runs out of memory
16222 ///
16223 ///
16224 /// # Panics
16225 /// if asserts feature is enabled and UB was detected
16226 ///
16227 /// # Safety
16228 ///
16229 /// Current thread must not be detached from JNI.
16230 ///
16231 /// Current thread must not be currently throwing an exception.
16232 ///
16233 /// Current thread does not hold a critical reference.
16234 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16235 ///
16236 /// `clazz` must a valid reference to a class that is not already garbage collected.
16237 /// `name` must be non-null and zero terminated utf-8.
16238 /// `sig` must be non-null and zero terminated utf-8.
16239 ///
16240 pub unsafe fn GetStaticMethodID(&self, class: jclass, name: impl UseCString, sig: impl UseCString) -> jmethodID {
16241 unsafe {
16242 name.use_as_const_c_char(|name| {
16243 sig.use_as_const_c_char(|sig| {
16244 #[cfg(feature = "asserts")]
16245 {
16246 self.check_not_critical("GetStaticMethodID");
16247 self.check_no_exception("GetStaticMethodID");
16248 self.check_is_class("GetStaticMethodID", class);
16249 assert!(!name.is_null(), "GetStaticMethodID name is null");
16250 assert!(!sig.is_null(), "GetStaticMethodID sig is null");
16251 }
16252
16253 self.jni::<extern "system" fn(JNIEnvVTable, jobject, *const c_char, *const c_char) -> jmethodID>(113)(self.vtable, class, name, sig)
16254 })
16255 })
16256 }
16257 }
16258
16259 ///
16260 /// Calls a static java method that returns void
16261 ///
16262 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16263 ///
16264 ///
16265 /// # Arguments
16266 /// * `obj` - which object the method should be called on
16267 /// * must be valid
16268 /// * must not be null
16269 /// * must not be already garbage collected
16270 ///
16271 /// * `methodID` - method id of the method
16272 /// * must not be null
16273 /// * must be valid
16274 /// * must not be a static
16275 /// * must actually be a method of `obj`
16276 ///
16277 /// * `args` - argument pointer
16278 /// * can be null if the method has no arguments
16279 /// * must not be null otherwise and point to the exact number of arguments the method expects
16280 ///
16281 /// # Throws Java Exception
16282 /// * Whatever the method threw
16283 ///
16284 ///
16285 /// # Panics
16286 /// if asserts feature is enabled and UB was detected
16287 ///
16288 /// # Safety
16289 ///
16290 /// Current thread must not be detached from JNI.
16291 ///
16292 /// Current thread must not be currently throwing an exception.
16293 ///
16294 /// Current thread does not hold a critical reference.
16295 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16296 ///
16297 /// `obj` must a valid and not already garbage collected.
16298 /// `methodID` must be valid, static and actually be a method of `obj` class and return void
16299 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
16300 /// `args` union must contain types that match the java methods parameters.
16301 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
16302 ///
16303 pub unsafe fn CallStaticVoidMethodA(&self, clazz: jclass, methodID: jmethodID, args: *const jtype) {
16304 unsafe {
16305 #[cfg(feature = "asserts")]
16306 {
16307 self.check_not_critical("CallStaticVoidMethodA");
16308 self.check_no_exception("CallStaticVoidMethodA");
16309 self.check_return_type_static("CallStaticVoidMethodA", clazz, methodID, "void");
16310 }
16311 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype)>(143)(self.vtable, clazz, methodID, args);
16312 }
16313 }
16314
16315 ///
16316 /// Calls a static java method that has 0 arguments and returns void
16317 ///
16318 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16319 ///
16320 ///
16321 /// # Arguments
16322 /// * `obj` - which object the method should be called on
16323 /// * must be valid
16324 /// * must not be null
16325 /// * must not be already garbage collected
16326 ///
16327 /// * `methodID` - method id of the method
16328 /// * must not be null
16329 /// * must be valid
16330 /// * must be a static
16331 /// * must actually be a method of `obj`
16332 /// * must refer to a method with 0 arguments
16333 ///
16334 /// # Throws Java Exception
16335 /// * Whatever the method threw
16336 ///
16337 ///
16338 /// # Panics
16339 /// if asserts feature is enabled and UB was detected
16340 ///
16341 /// # Safety
16342 ///
16343 /// Current thread must not be detached from JNI.
16344 ///
16345 /// Current thread must not be currently throwing an exception.
16346 ///
16347 /// Current thread does not hold a critical reference.
16348 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16349 ///
16350 /// `clazz` must a valid and not already garbage collected.
16351 /// `methodID` must be valid, static and actually be a method of `obj`, return void and have 0 arguments
16352 ///
16353 pub unsafe fn CallStaticVoidMethod0(&self, clazz: jclass, methodID: jmethodID) {
16354 unsafe {
16355 #[cfg(feature = "asserts")]
16356 {
16357 self.check_not_critical("CallStaticVoidMethod");
16358 self.check_no_exception("CallStaticVoidMethod");
16359 self.check_return_type_static("CallStaticVoidMethod", clazz, methodID, "void");
16360 }
16361 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID)>(141)(self.vtable, clazz, methodID);
16362 }
16363 }
16364
16365 ///
16366 /// Calls a static java method that has 1 arguments and returns void
16367 ///
16368 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16369 ///
16370 ///
16371 /// # Arguments
16372 /// * `obj` - which object the method should be called on
16373 /// * must be valid
16374 /// * must not be null
16375 /// * must not be already garbage collected
16376 ///
16377 /// * `methodID` - method id of the method
16378 /// * must not be null
16379 /// * must be valid
16380 /// * must be a static
16381 /// * must actually be a method of `obj`
16382 /// * must refer to a method with 1 arguments
16383 ///
16384 /// # Throws Java Exception
16385 /// * Whatever the method threw
16386 ///
16387 ///
16388 /// # Panics
16389 /// if asserts feature is enabled and UB was detected
16390 ///
16391 /// # Safety
16392 ///
16393 /// Current thread must not be detached from JNI.
16394 ///
16395 /// Current thread must not be currently throwing an exception.
16396 ///
16397 /// Current thread does not hold a critical reference.
16398 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16399 ///
16400 /// `clazz` must a valid and not already garbage collected.
16401 /// `methodID` must be valid, static and actually be a method of `obj`, return void and have 1 arguments
16402 ///
16403 pub unsafe fn CallStaticVoidMethod1<A: JType>(&self, clazz: jclass, methodID: jmethodID, arg1: A) {
16404 unsafe {
16405 #[cfg(feature = "asserts")]
16406 {
16407 self.check_not_critical("CallStaticVoidMethod");
16408 self.check_no_exception("CallStaticVoidMethod");
16409 self.check_return_type_static("CallStaticVoidMethod", clazz, methodID, "void");
16410 self.check_parameter_types_static("CallStaticVoidMethod", clazz, methodID, arg1, 0, 1);
16411 }
16412 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...)>(141)(self.vtable, clazz, methodID, arg1);
16413 }
16414 }
16415
16416 ///
16417 /// Calls a static java method that has 2 arguments and returns void
16418 ///
16419 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16420 ///
16421 ///
16422 /// # Arguments
16423 /// * `obj` - which object the method should be called on
16424 /// * must be valid
16425 /// * must not be null
16426 /// * must not be already garbage collected
16427 ///
16428 /// * `methodID` - method id of the method
16429 /// * must not be null
16430 /// * must be valid
16431 /// * must be a static
16432 /// * must actually be a method of `obj`
16433 /// * must refer to a method with 2 arguments
16434 ///
16435 /// # Throws Java Exception
16436 /// * Whatever the method threw
16437 ///
16438 ///
16439 /// # Panics
16440 /// if asserts feature is enabled and UB was detected
16441 ///
16442 /// # Safety
16443 ///
16444 /// Current thread must not be detached from JNI.
16445 ///
16446 /// Current thread must not be currently throwing an exception.
16447 ///
16448 /// Current thread does not hold a critical reference.
16449 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16450 ///
16451 /// `obj` must a valid and not already garbage collected.
16452 /// `methodID` must be valid, static and actually be a method of `obj`, return void and have 2 arguments
16453 ///
16454 pub unsafe fn CallStaticVoidMethod2<A: JType, B: JType>(&self, clazz: jclass, methodID: jmethodID, arg1: A, arg2: B) {
16455 unsafe {
16456 #[cfg(feature = "asserts")]
16457 {
16458 self.check_not_critical("CallStaticVoidMethod");
16459 self.check_no_exception("CallStaticVoidMethod");
16460 self.check_return_type_static("CallStaticVoidMethod", clazz, methodID, "void");
16461 self.check_parameter_types_static("CallStaticVoidMethod", clazz, methodID, arg1, 0, 2);
16462 self.check_parameter_types_static("CallStaticVoidMethod", clazz, methodID, arg2, 1, 2);
16463 }
16464 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...)>(141)(self.vtable, clazz, methodID, arg1, arg2);
16465 }
16466 }
16467
16468 ///
16469 /// Calls a static java method that has 3 arguments and returns void
16470 ///
16471 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16472 ///
16473 ///
16474 /// # Arguments
16475 /// * `obj` - which object the method should be called on
16476 /// * must be valid
16477 /// * must not be null
16478 /// * must not be already garbage collected
16479 ///
16480 /// * `methodID` - method id of the method
16481 /// * must not be null
16482 /// * must be valid
16483 /// * must be a static
16484 /// * must actually be a method of `obj`
16485 /// * must refer to a method with 3 arguments
16486 ///
16487 /// # Throws Java Exception
16488 /// * Whatever the method threw
16489 ///
16490 ///
16491 /// # Panics
16492 /// if asserts feature is enabled and UB was detected
16493 ///
16494 /// # Safety
16495 ///
16496 /// Current thread must not be detached from JNI.
16497 ///
16498 /// Current thread must not be currently throwing an exception.
16499 ///
16500 /// Current thread does not hold a critical reference.
16501 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16502 ///
16503 /// `obj` must a valid and not already garbage collected.
16504 /// `methodID` must be valid, static and actually be a method of `obj`, return void and have 3 arguments
16505 ///
16506 pub unsafe fn CallStaticVoidMethod3<A: JType, B: JType, C: JType>(&self, clazz: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) {
16507 unsafe {
16508 #[cfg(feature = "asserts")]
16509 {
16510 self.check_not_critical("CallStaticVoidMethod");
16511 self.check_no_exception("CallStaticVoidMethod");
16512 self.check_return_type_static("CallStaticVoidMethod", clazz, methodID, "void");
16513 self.check_parameter_types_static("CallStaticVoidMethod", clazz, methodID, arg1, 0, 3);
16514 self.check_parameter_types_static("CallStaticVoidMethod", clazz, methodID, arg2, 1, 3);
16515 self.check_parameter_types_static("CallStaticVoidMethod", clazz, methodID, arg3, 2, 3);
16516 }
16517 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...)>(141)(self.vtable, clazz, methodID, arg1, arg2, arg3);
16518 }
16519 }
16520
16521 ///
16522 /// Calls a static java method that returns an object
16523 ///
16524 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16525 ///
16526 ///
16527 /// # Arguments
16528 /// * `obj` - which object the method should be called on
16529 /// * must be valid
16530 /// * must not be null
16531 /// * must not be already garbage collected
16532 ///
16533 /// * `methodID` - method id of the method
16534 /// * must not be null
16535 /// * must be valid
16536 /// * must not be a static
16537 /// * must actually be a method of `obj`
16538 ///
16539 /// * `args` - argument pointer
16540 /// * can be null if the method has no arguments
16541 /// * must not be null otherwise and point to the exact number of arguments the method expects
16542 ///
16543 /// # Returns
16544 /// Whatever the method returned or null if it threw
16545 ///
16546 /// # Throws Java Exception
16547 /// * Whatever the method threw
16548 ///
16549 ///
16550 /// # Panics
16551 /// if asserts feature is enabled and UB was detected
16552 ///
16553 /// # Safety
16554 ///
16555 /// Current thread must not be detached from JNI.
16556 ///
16557 /// Current thread must not be currently throwing an exception.
16558 ///
16559 /// Current thread does not hold a critical reference.
16560 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16561 ///
16562 /// `obj` must a valid and not already garbage collected.
16563 /// `methodID` must be valid, static and actually be a method of `obj` class and return an object
16564 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
16565 /// `args` union must contain types that match the java methods parameters.
16566 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
16567 ///
16568 pub unsafe fn CallStaticObjectMethodA(&self, obj: jclass, methodID: jmethodID, args: *const jtype) -> jobject {
16569 unsafe {
16570 #[cfg(feature = "asserts")]
16571 {
16572 self.check_not_critical("CallStaticObjectMethodA");
16573 self.check_no_exception("CallStaticObjectMethodA");
16574 self.check_return_type_static("CallStaticBooleanMethodA", obj, methodID, "object");
16575 }
16576 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(116)(self.vtable, obj, methodID, args)
16577 }
16578 }
16579
16580 ///
16581 /// Calls a static java method that has 0 arguments and returns an object
16582 ///
16583 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16584 ///
16585 ///
16586 /// # Arguments
16587 /// * `obj` - which object the method should be called on
16588 /// * must be valid
16589 /// * must not be null
16590 /// * must not be already garbage collected
16591 ///
16592 /// * `methodID` - method id of the method
16593 /// * must not be null
16594 /// * must be valid
16595 /// * must be a static
16596 /// * must actually be a method of `obj`
16597 /// * must refer to a method with 0 arguments
16598 ///
16599 /// # Returns
16600 /// Whatever the method returned or null if it threw
16601 ///
16602 /// # Throws Java Exception
16603 /// * Whatever the method threw
16604 ///
16605 ///
16606 /// # Panics
16607 /// if asserts feature is enabled and UB was detected
16608 ///
16609 /// # Safety
16610 ///
16611 /// Current thread must not be detached from JNI.
16612 ///
16613 /// Current thread must not be currently throwing an exception.
16614 ///
16615 /// Current thread does not hold a critical reference.
16616 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16617 ///
16618 /// `obj` must a valid and not already garbage collected.
16619 /// `methodID` must be valid, static and actually be a method of `obj`, return an object and have 0 arguments
16620 ///
16621 pub unsafe fn CallStaticObjectMethod0(&self, obj: jclass, methodID: jmethodID) -> jobject {
16622 unsafe {
16623 #[cfg(feature = "asserts")]
16624 {
16625 self.check_not_critical("CallStaticObjectMethod");
16626 self.check_no_exception("CallStaticObjectMethod");
16627 self.check_return_type_static("CallStaticObjectMethod", obj, methodID, "object");
16628 }
16629 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jobject>(114)(self.vtable, obj, methodID)
16630 }
16631 }
16632
16633 ///
16634 /// Calls a static java method that has 1 arguments and returns an object
16635 ///
16636 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16637 ///
16638 ///
16639 /// # Arguments
16640 /// * `obj` - which object the method should be called on
16641 /// * must be valid
16642 /// * must not be null
16643 /// * must not be already garbage collected
16644 ///
16645 /// * `methodID` - method id of the method
16646 /// * must not be null
16647 /// * must be valid
16648 /// * must be a static
16649 /// * must actually be a method of `obj`
16650 /// * must refer to a method with 1 arguments
16651 ///
16652 /// # Returns
16653 /// Whatever the method returned or null if it threw
16654 ///
16655 /// # Throws Java Exception
16656 /// * Whatever the method threw
16657 ///
16658 ///
16659 /// # Panics
16660 /// if asserts feature is enabled and UB was detected
16661 ///
16662 /// # Safety
16663 ///
16664 /// Current thread must not be detached from JNI.
16665 ///
16666 /// Current thread must not be currently throwing an exception.
16667 ///
16668 /// Current thread does not hold a critical reference.
16669 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16670 ///
16671 /// `obj` must a valid and not already garbage collected.
16672 /// `methodID` must be valid, static and actually be a method of `obj`, return an object and have 1 arguments
16673 ///
16674 pub unsafe fn CallStaticObjectMethod1<A: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A) -> jobject {
16675 unsafe {
16676 #[cfg(feature = "asserts")]
16677 {
16678 self.check_not_critical("CallStaticObjectMethod");
16679 self.check_no_exception("CallStaticObjectMethod");
16680 self.check_return_type_static("CallStaticObjectMethod", obj, methodID, "object");
16681 self.check_parameter_types_static("CallStaticObjectMethod", obj, methodID, arg1, 0, 1);
16682 }
16683 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jobject>(114)(self.vtable, obj, methodID, arg1)
16684 }
16685 }
16686
16687 ///
16688 /// Calls a static java method that has 2 arguments and returns an object
16689 ///
16690 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16691 ///
16692 ///
16693 /// # Arguments
16694 /// * `obj` - which object the method should be called on
16695 /// * must be valid
16696 /// * must not be null
16697 /// * must not be already garbage collected
16698 ///
16699 /// * `methodID` - method id of the method
16700 /// * must not be null
16701 /// * must be valid
16702 /// * must be a static
16703 /// * must actually be a method of `obj`
16704 /// * must refer to a method with 2 arguments
16705 ///
16706 /// # Returns
16707 /// Whatever the method returned or null if it threw
16708 ///
16709 /// # Throws Java Exception
16710 /// * Whatever the method threw
16711 ///
16712 ///
16713 /// # Panics
16714 /// if asserts feature is enabled and UB was detected
16715 ///
16716 /// # Safety
16717 ///
16718 /// Current thread must not be detached from JNI.
16719 ///
16720 /// Current thread must not be currently throwing an exception.
16721 ///
16722 /// Current thread does not hold a critical reference.
16723 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16724 ///
16725 /// `obj` must a valid and not already garbage collected.
16726 /// `methodID` must be valid, static and actually be a method of `obj`, return an object and have 2 arguments
16727 ///
16728 pub unsafe fn CallStaticObjectMethod2<A: JType, B: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jobject {
16729 unsafe {
16730 #[cfg(feature = "asserts")]
16731 {
16732 self.check_not_critical("CallStaticObjectMethod");
16733 self.check_no_exception("CallStaticObjectMethod");
16734 self.check_return_type_static("CallStaticObjectMethod", obj, methodID, "object");
16735 self.check_parameter_types_static("CallStaticObjectMethod", obj, methodID, arg1, 0, 2);
16736 self.check_parameter_types_static("CallStaticObjectMethod", obj, methodID, arg2, 1, 2);
16737 }
16738 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jobject>(114)(self.vtable, obj, methodID, arg1, arg2)
16739 }
16740 }
16741
16742 ///
16743 /// Calls a static java method that has 3 arguments and returns an object
16744 ///
16745 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16746 ///
16747 ///
16748 /// # Arguments
16749 /// * `obj` - which object the method should be called on
16750 /// * must be valid
16751 /// * must not be null
16752 /// * must not be already garbage collected
16753 ///
16754 /// * `methodID` - method id of the method
16755 /// * must not be null
16756 /// * must be valid
16757 /// * must be a static
16758 /// * must actually be a method of `obj`
16759 /// * must refer to a method with 3 arguments
16760 ///
16761 /// # Returns
16762 /// Whatever the method returned or null if it threw
16763 ///
16764 /// # Throws Java Exception
16765 /// * Whatever the method threw
16766 ///
16767 ///
16768 /// # Panics
16769 /// if asserts feature is enabled and UB was detected
16770 ///
16771 /// # Safety
16772 ///
16773 /// Current thread must not be detached from JNI.
16774 ///
16775 /// Current thread must not be currently throwing an exception.
16776 ///
16777 /// Current thread does not hold a critical reference.
16778 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16779 ///
16780 /// `obj` must a valid and not already garbage collected.
16781 /// `methodID` must be valid, static and actually be a method of `obj`, return an object and have 3 arguments
16782 ///
16783 pub unsafe fn CallStaticObjectMethod3<A: JType, B: JType, C: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jobject {
16784 unsafe {
16785 #[cfg(feature = "asserts")]
16786 {
16787 self.check_not_critical("CallStaticObjectMethod");
16788 self.check_no_exception("CallStaticObjectMethod");
16789 self.check_return_type_static("CallStaticObjectMethod", obj, methodID, "object");
16790 self.check_parameter_types_static("CallStaticObjectMethod", obj, methodID, arg1, 0, 3);
16791 self.check_parameter_types_static("CallStaticObjectMethod", obj, methodID, arg2, 1, 3);
16792 self.check_parameter_types_static("CallStaticObjectMethod", obj, methodID, arg3, 2, 3);
16793 }
16794 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jobject>(114)(self.vtable, obj, methodID, arg1, arg2, arg3)
16795 }
16796 }
16797
16798 ///
16799 /// Calls a static java method that returns a boolean
16800 ///
16801 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16802 ///
16803 ///
16804 /// # Arguments
16805 /// * `obj` - which object the method should be called on
16806 /// * must be valid
16807 /// * must not be null
16808 /// * must not be already garbage collected
16809 ///
16810 /// * `methodID` - method id of the method
16811 /// * must not be null
16812 /// * must be valid
16813 /// * must not be a static
16814 /// * must actually be a method of `obj`
16815 ///
16816 /// * `args` - argument pointer
16817 /// * can be null if the method has no arguments
16818 /// * must not be null otherwise and point to the exact number of arguments the method expects
16819 ///
16820 /// # Returns
16821 /// Whatever the method returned or null if it threw
16822 ///
16823 /// # Throws Java Exception
16824 /// * Whatever the method threw
16825 ///
16826 ///
16827 /// # Panics
16828 /// if asserts feature is enabled and UB was detected
16829 ///
16830 /// # Safety
16831 ///
16832 /// Current thread must not be detached from JNI.
16833 ///
16834 /// Current thread must not be currently throwing an exception.
16835 ///
16836 /// Current thread does not hold a critical reference.
16837 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16838 ///
16839 /// `obj` must a valid and not already garbage collected.
16840 /// `methodID` must be valid, static and actually be a method of `obj` class and return a boolean
16841 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
16842 /// `args` union must contain types that match the java methods parameters.
16843 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
16844 ///
16845 pub unsafe fn CallStaticBooleanMethodA(&self, obj: jclass, methodID: jmethodID, args: *const jtype) -> bool {
16846 unsafe {
16847 #[cfg(feature = "asserts")]
16848 {
16849 self.check_not_critical("CallStaticBooleanMethodA");
16850 self.check_no_exception("CallStaticBooleanMethodA");
16851 self.check_return_type_static("CallStaticBooleanMethodA", obj, methodID, "boolean");
16852 }
16853 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jboolean>(119)(self.vtable, obj, methodID, args).as_bool()
16854 }
16855 }
16856
16857 ///
16858 /// Calls a static java method that has 0 arguments and returns boolean
16859 ///
16860 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16861 ///
16862 ///
16863 /// # Arguments
16864 /// * `obj` - which object the method should be called on
16865 /// * must be valid
16866 /// * must not be null
16867 /// * must not be already garbage collected
16868 ///
16869 /// * `methodID` - method id of the method
16870 /// * must not be null
16871 /// * must be valid
16872 /// * must be a static
16873 /// * must actually be a method of `obj`
16874 /// * must refer to a method with 0 arguments
16875 ///
16876 /// # Returns
16877 /// Whatever the method returned or false if it threw
16878 ///
16879 /// # Throws Java Exception
16880 /// * Whatever the method threw
16881 ///
16882 ///
16883 /// # Panics
16884 /// if asserts feature is enabled and UB was detected
16885 ///
16886 /// # Safety
16887 ///
16888 /// Current thread must not be detached from JNI.
16889 ///
16890 /// Current thread must not be currently throwing an exception.
16891 ///
16892 /// Current thread does not hold a critical reference.
16893 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16894 ///
16895 /// `obj` must a valid and not already garbage collected.
16896 /// `methodID` must be valid, static and actually be a method of `obj`, return boolean and have 0 arguments
16897 ///
16898 pub unsafe fn CallStaticBooleanMethod0(&self, obj: jclass, methodID: jmethodID) -> bool {
16899 unsafe {
16900 #[cfg(feature = "asserts")]
16901 {
16902 self.check_not_critical("CallStaticBooleanMethod");
16903 self.check_no_exception("CallStaticBooleanMethod");
16904 self.check_return_type_static("CallStaticBooleanMethod", obj, methodID, "boolean");
16905 }
16906 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jboolean>(117)(self.vtable, obj, methodID).as_bool()
16907 }
16908 }
16909
16910 ///
16911 /// Calls a static java method that has 1 arguments and returns boolean
16912 ///
16913 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16914 ///
16915 ///
16916 /// # Arguments
16917 /// * `obj` - which object the method should be called on
16918 /// * must be valid
16919 /// * must not be null
16920 /// * must not be already garbage collected
16921 ///
16922 /// * `methodID` - method id of the method
16923 /// * must not be null
16924 /// * must be valid
16925 /// * must be a static
16926 /// * must actually be a method of `obj`
16927 /// * must refer to a method with 1 arguments
16928 ///
16929 /// # Returns
16930 /// Whatever the method returned or false if it threw
16931 ///
16932 /// # Throws Java Exception
16933 /// * Whatever the method threw
16934 ///
16935 ///
16936 /// # Panics
16937 /// if asserts feature is enabled and UB was detected
16938 ///
16939 /// # Safety
16940 ///
16941 /// Current thread must not be detached from JNI.
16942 ///
16943 /// Current thread must not be currently throwing an exception.
16944 ///
16945 /// Current thread does not hold a critical reference.
16946 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
16947 ///
16948 /// `obj` must a valid and not already garbage collected.
16949 /// `methodID` must be valid, static and actually be a method of `obj`, return boolean and have 1 arguments
16950 ///
16951 pub unsafe fn CallStaticBooleanMethod1<A: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A) -> bool {
16952 unsafe {
16953 #[cfg(feature = "asserts")]
16954 {
16955 self.check_not_critical("CallStaticBooleanMethod");
16956 self.check_no_exception("CallStaticBooleanMethod");
16957 self.check_return_type_static("CallStaticBooleanMethod", obj, methodID, "boolean");
16958 self.check_parameter_types_static("CallStaticBooleanMethod", obj, methodID, arg1, 0, 1);
16959 }
16960 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jboolean>(117)(self.vtable, obj, methodID, arg1).as_bool()
16961 }
16962 }
16963
16964 ///
16965 /// Calls a static java method that has 2 arguments and returns boolean
16966 ///
16967 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
16968 ///
16969 ///
16970 /// # Arguments
16971 /// * `obj` - which object the method should be called on
16972 /// * must be valid
16973 /// * must not be null
16974 /// * must not be already garbage collected
16975 ///
16976 /// * `methodID` - method id of the method
16977 /// * must not be null
16978 /// * must be valid
16979 /// * must be a static
16980 /// * must actually be a method of `obj`
16981 /// * must refer to a method with 2 arguments
16982 ///
16983 /// # Returns
16984 /// Whatever the method returned or false if it threw
16985 ///
16986 /// # Throws Java Exception
16987 /// * Whatever the method threw
16988 ///
16989 ///
16990 /// # Panics
16991 /// if asserts feature is enabled and UB was detected
16992 ///
16993 /// # Safety
16994 ///
16995 /// Current thread must not be detached from JNI.
16996 ///
16997 /// Current thread must not be currently throwing an exception.
16998 ///
16999 /// Current thread does not hold a critical reference.
17000 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17001 ///
17002 /// `obj` must a valid and not already garbage collected.
17003 /// `methodID` must be valid, static and actually be a method of `obj`, return boolean and have 2 arguments
17004 ///
17005 pub unsafe fn CallStaticBooleanMethod2<A: JType, B: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B) -> bool {
17006 unsafe {
17007 #[cfg(feature = "asserts")]
17008 {
17009 self.check_not_critical("CallStaticBooleanMethod");
17010 self.check_no_exception("CallStaticBooleanMethod");
17011 self.check_return_type_static("CallStaticBooleanMethod", obj, methodID, "boolean");
17012 self.check_parameter_types_static("CallStaticBooleanMethod", obj, methodID, arg1, 0, 2);
17013 self.check_parameter_types_static("CallStaticBooleanMethod", obj, methodID, arg2, 1, 2);
17014 }
17015 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jboolean>(117)(self.vtable, obj, methodID, arg1, arg2).as_bool()
17016 }
17017 }
17018
17019 ///
17020 /// Calls a static java method that has 3 arguments and returns boolean
17021 ///
17022 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17023 ///
17024 ///
17025 /// # Arguments
17026 /// * `obj` - which object the method should be called on
17027 /// * must be valid
17028 /// * must not be null
17029 /// * must not be already garbage collected
17030 ///
17031 /// * `methodID` - method id of the method
17032 /// * must not be null
17033 /// * must be valid
17034 /// * must be a static
17035 /// * must actually be a method of `obj`
17036 /// * must refer to a method with 3 arguments
17037 ///
17038 /// # Returns
17039 /// Whatever the method returned or false if it threw
17040 ///
17041 /// # Throws Java Exception
17042 /// * Whatever the method threw
17043 ///
17044 ///
17045 /// # Panics
17046 /// if asserts feature is enabled and UB was detected
17047 ///
17048 /// # Safety
17049 ///
17050 /// Current thread must not be detached from JNI.
17051 ///
17052 /// Current thread must not be currently throwing an exception.
17053 ///
17054 /// Current thread does not hold a critical reference.
17055 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17056 ///
17057 /// `obj` must a valid and not already garbage collected.
17058 /// `methodID` must be valid, static and actually be a method of `obj`, return boolean and have 3 arguments
17059 ///
17060 pub unsafe fn CallStaticBooleanMethod3<A: JType, B: JType, C: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> bool {
17061 unsafe {
17062 #[cfg(feature = "asserts")]
17063 {
17064 self.check_not_critical("CallStaticBooleanMethod");
17065 self.check_no_exception("CallStaticBooleanMethod");
17066 self.check_return_type_static("CallStaticBooleanMethod", obj, methodID, "boolean");
17067 self.check_parameter_types_static("CallStaticBooleanMethod", obj, methodID, arg1, 0, 3);
17068 self.check_parameter_types_static("CallStaticBooleanMethod", obj, methodID, arg2, 1, 3);
17069 self.check_parameter_types_static("CallStaticBooleanMethod", obj, methodID, arg3, 2, 3);
17070 }
17071 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jboolean>(117)(self.vtable, obj, methodID, arg1, arg2, arg3).as_bool()
17072 }
17073 }
17074
17075 ///
17076 /// Calls a static java method that returns a byte
17077 ///
17078 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17079 ///
17080 ///
17081 /// # Arguments
17082 /// * `obj` - which object the method should be called on
17083 /// * must be valid
17084 /// * must not be null
17085 /// * must not be already garbage collected
17086 ///
17087 /// * `methodID` - method id of the method
17088 /// * must not be null
17089 /// * must be valid
17090 /// * must not be a static
17091 /// * must actually be a method of `obj`
17092 ///
17093 /// * `args` - argument pointer
17094 /// * can be null if the method has no arguments
17095 /// * must not be null otherwise and point to the exact number of arguments the method expects
17096 ///
17097 /// # Returns
17098 /// Whatever the method returned or 0 if it threw
17099 ///
17100 /// # Throws Java Exception
17101 /// * Whatever the method threw
17102 ///
17103 ///
17104 /// # Panics
17105 /// if asserts feature is enabled and UB was detected
17106 ///
17107 /// # Safety
17108 ///
17109 /// Current thread must not be detached from JNI.
17110 ///
17111 /// Current thread must not be currently throwing an exception.
17112 ///
17113 /// Current thread does not hold a critical reference.
17114 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17115 ///
17116 /// `obj` must a valid and not already garbage collected.
17117 /// `methodID` must be valid, static and actually be a method of `obj` class and return a byte
17118 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
17119 /// `args` union must contain types that match the java methods parameters.
17120 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
17121 ///
17122 pub unsafe fn CallStaticByteMethodA(&self, obj: jclass, methodID: jmethodID, args: *const jtype) -> jbyte {
17123 unsafe {
17124 #[cfg(feature = "asserts")]
17125 {
17126 self.check_not_critical("CallStaticByteMethodA");
17127 self.check_no_exception("CallStaticByteMethodA");
17128 self.check_return_type_static("CallStaticByteMethodA", obj, methodID, "byte");
17129 }
17130 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jbyte>(122)(self.vtable, obj, methodID, args)
17131 }
17132 }
17133
17134 ///
17135 /// Calls a static java method that has 0 arguments and returns byte
17136 ///
17137 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17138 ///
17139 ///
17140 /// # Arguments
17141 /// * `obj` - which object the method should be called on
17142 /// * must be valid
17143 /// * must not be null
17144 /// * must not be already garbage collected
17145 ///
17146 /// * `methodID` - method id of the method
17147 /// * must not be null
17148 /// * must be valid
17149 /// * must be a static
17150 /// * must actually be a method of `obj`
17151 /// * must refer to a method with 0 arguments
17152 ///
17153 /// # Returns
17154 /// Whatever the method returned or 0 if it threw
17155 ///
17156 /// # Throws Java Exception
17157 /// * Whatever the method threw
17158 ///
17159 ///
17160 /// # Panics
17161 /// if asserts feature is enabled and UB was detected
17162 ///
17163 /// # Safety
17164 ///
17165 /// Current thread must not be detached from JNI.
17166 ///
17167 /// Current thread must not be currently throwing an exception.
17168 ///
17169 /// Current thread does not hold a critical reference.
17170 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17171 ///
17172 /// `obj` must a valid and not already garbage collected.
17173 /// `methodID` must be valid, static and actually be a method of `obj`, return byte and have 0 arguments
17174 ///
17175 pub unsafe fn CallStaticByteMethod0(&self, obj: jclass, methodID: jmethodID) -> jbyte {
17176 unsafe {
17177 #[cfg(feature = "asserts")]
17178 {
17179 self.check_not_critical("CallStaticByteMethod");
17180 self.check_no_exception("CallStaticByteMethod");
17181 self.check_return_type_static("CallStaticByteMethod", obj, methodID, "byte");
17182 }
17183 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jbyte>(120)(self.vtable, obj, methodID)
17184 }
17185 }
17186
17187 ///
17188 /// Calls a static java method that has 1 arguments and returns byte
17189 ///
17190 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17191 ///
17192 ///
17193 /// # Arguments
17194 /// * `obj` - which object the method should be called on
17195 /// * must be valid
17196 /// * must not be null
17197 /// * must not be already garbage collected
17198 ///
17199 /// * `methodID` - method id of the method
17200 /// * must not be null
17201 /// * must be valid
17202 /// * must be a static
17203 /// * must actually be a method of `obj`
17204 /// * must refer to a method with 1 arguments
17205 ///
17206 /// # Returns
17207 /// Whatever the method returned or 0 if it threw
17208 ///
17209 /// # Throws Java Exception
17210 /// * Whatever the method threw
17211 ///
17212 ///
17213 /// # Panics
17214 /// if asserts feature is enabled and UB was detected
17215 ///
17216 /// # Safety
17217 ///
17218 /// Current thread must not be detached from JNI.
17219 ///
17220 /// Current thread must not be currently throwing an exception.
17221 ///
17222 /// Current thread does not hold a critical reference.
17223 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17224 ///
17225 /// `obj` must a valid and not already garbage collected.
17226 /// `methodID` must be valid, static and actually be a method of `obj`, return byte and have 1 arguments
17227 ///
17228 pub unsafe fn CallStaticByteMethod1<A: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A) -> jbyte {
17229 unsafe {
17230 #[cfg(feature = "asserts")]
17231 {
17232 self.check_not_critical("CallStaticByteMethod");
17233 self.check_no_exception("CallStaticByteMethod");
17234 self.check_return_type_static("CallStaticByteMethod", obj, methodID, "byte");
17235 self.check_parameter_types_static("CallStaticByteMethod", obj, methodID, arg1, 0, 1);
17236 }
17237 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jbyte>(120)(self.vtable, obj, methodID, arg1)
17238 }
17239 }
17240
17241 ///
17242 /// Calls a static java method that has 2 arguments and returns byte
17243 ///
17244 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17245 ///
17246 ///
17247 /// # Arguments
17248 /// * `obj` - which object the method should be called on
17249 /// * must be valid
17250 /// * must not be null
17251 /// * must not be already garbage collected
17252 ///
17253 /// * `methodID` - method id of the method
17254 /// * must not be null
17255 /// * must be valid
17256 /// * must be a static
17257 /// * must actually be a method of `obj`
17258 /// * must refer to a method with 2 arguments
17259 ///
17260 /// # Returns
17261 /// Whatever the method returned or 0 if it threw
17262 ///
17263 /// # Throws Java Exception
17264 /// * Whatever the method threw
17265 ///
17266 ///
17267 /// # Panics
17268 /// if asserts feature is enabled and UB was detected
17269 ///
17270 /// # Safety
17271 ///
17272 /// Current thread must not be detached from JNI.
17273 ///
17274 /// Current thread must not be currently throwing an exception.
17275 ///
17276 /// Current thread does not hold a critical reference.
17277 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17278 ///
17279 /// `obj` must a valid and not already garbage collected.
17280 /// `methodID` must be valid, static and actually be a method of `obj`, return byte and have 2 arguments
17281 ///
17282 pub unsafe fn CallStaticByteMethod2<A: JType, B: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jbyte {
17283 unsafe {
17284 #[cfg(feature = "asserts")]
17285 {
17286 self.check_not_critical("CallStaticByteMethod");
17287 self.check_no_exception("CallStaticByteMethod");
17288 self.check_return_type_static("CallStaticByteMethod", obj, methodID, "byte");
17289 self.check_parameter_types_static("CallStaticByteMethod", obj, methodID, arg1, 0, 2);
17290 self.check_parameter_types_static("CallStaticByteMethod", obj, methodID, arg2, 1, 2);
17291 }
17292 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jbyte>(120)(self.vtable, obj, methodID, arg1, arg2)
17293 }
17294 }
17295
17296 ///
17297 /// Calls a static java method that has 3 arguments and returns byte
17298 ///
17299 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17300 ///
17301 ///
17302 /// # Arguments
17303 /// * `obj` - which object the method should be called on
17304 /// * must be valid
17305 /// * must not be null
17306 /// * must not be already garbage collected
17307 ///
17308 /// * `methodID` - method id of the method
17309 /// * must not be null
17310 /// * must be valid
17311 /// * must be a static
17312 /// * must actually be a method of `obj`
17313 /// * must refer to a method with 3 arguments
17314 ///
17315 /// # Returns
17316 /// Whatever the method returned or 0 if it threw
17317 ///
17318 /// # Throws Java Exception
17319 /// * Whatever the method threw
17320 ///
17321 ///
17322 /// # Panics
17323 /// if asserts feature is enabled and UB was detected
17324 ///
17325 /// # Safety
17326 ///
17327 /// Current thread must not be detached from JNI.
17328 ///
17329 /// Current thread must not be currently throwing an exception.
17330 ///
17331 /// Current thread does not hold a critical reference.
17332 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17333 ///
17334 /// `obj` must a valid and not already garbage collected.
17335 /// `methodID` must be valid, static and actually be a method of `obj`, return byte and have 3 arguments
17336 ///
17337 pub unsafe fn CallStaticByteMethod3<A: JType, B: JType, C: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jbyte {
17338 unsafe {
17339 #[cfg(feature = "asserts")]
17340 {
17341 self.check_not_critical("CallStaticByteMethod");
17342 self.check_no_exception("CallStaticByteMethod");
17343 self.check_return_type_static("CallStaticByteMethod", obj, methodID, "byte");
17344 self.check_parameter_types_static("CallStaticByteMethod", obj, methodID, arg1, 0, 3);
17345 self.check_parameter_types_static("CallStaticByteMethod", obj, methodID, arg2, 1, 3);
17346 self.check_parameter_types_static("CallStaticByteMethod", obj, methodID, arg3, 2, 3);
17347 }
17348 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jbyte>(120)(self.vtable, obj, methodID, arg1, arg2, arg3)
17349 }
17350 }
17351
17352 ///
17353 /// Calls a static java method that returns a char
17354 ///
17355 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17356 ///
17357 ///
17358 /// # Arguments
17359 /// * `obj` - which object the method should be called on
17360 /// * must be valid
17361 /// * must not be null
17362 /// * must not be already garbage collected
17363 ///
17364 /// * `methodID` - method id of the method
17365 /// * must not be null
17366 /// * must be valid
17367 /// * must not be a static
17368 /// * must actually be a method of `obj`
17369 ///
17370 /// * `args` - argument pointer
17371 /// * can be null if the method has no arguments
17372 /// * must not be null otherwise and point to the exact number of arguments the method expects
17373 ///
17374 /// # Returns
17375 /// Whatever the method returned or 0 if it threw
17376 ///
17377 /// # Throws Java Exception
17378 /// * Whatever the method threw
17379 ///
17380 ///
17381 /// # Panics
17382 /// if asserts feature is enabled and UB was detected
17383 ///
17384 /// # Safety
17385 ///
17386 /// Current thread must not be detached from JNI.
17387 ///
17388 /// Current thread must not be currently throwing an exception.
17389 ///
17390 /// Current thread does not hold a critical reference.
17391 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17392 ///
17393 /// `obj` must a valid and not already garbage collected.
17394 /// `methodID` must be valid, static and actually be a method of `obj` class and return a char
17395 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
17396 /// `args` union must contain types that match the java methods parameters.
17397 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
17398 ///
17399 pub unsafe fn CallStaticCharMethodA(&self, obj: jclass, methodID: jmethodID, args: *const jtype) -> jchar {
17400 unsafe {
17401 #[cfg(feature = "asserts")]
17402 {
17403 self.check_not_critical("CallStaticCharMethodA");
17404 self.check_no_exception("CallStaticCharMethodA");
17405 self.check_return_type_static("CallStaticCharMethodA", obj, methodID, "char");
17406 }
17407 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jchar>(125)(self.vtable, obj, methodID, args)
17408 }
17409 }
17410
17411 ///
17412 /// Calls a static java method that has 0 arguments and returns char
17413 ///
17414 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17415 ///
17416 ///
17417 /// # Arguments
17418 /// * `obj` - which object the method should be called on
17419 /// * must be valid
17420 /// * must not be null
17421 /// * must not be already garbage collected
17422 ///
17423 /// * `methodID` - method id of the method
17424 /// * must not be null
17425 /// * must be valid
17426 /// * must be a static
17427 /// * must actually be a method of `obj`
17428 /// * must refer to a method with 0 arguments
17429 ///
17430 /// # Returns
17431 /// Whatever the method returned or 0 if it threw
17432 ///
17433 /// # Throws Java Exception
17434 /// * Whatever the method threw
17435 ///
17436 ///
17437 /// # Panics
17438 /// if asserts feature is enabled and UB was detected
17439 ///
17440 /// # Safety
17441 ///
17442 /// Current thread must not be detached from JNI.
17443 ///
17444 /// Current thread must not be currently throwing an exception.
17445 ///
17446 /// Current thread does not hold a critical reference.
17447 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17448 ///
17449 /// `obj` must a valid and not already garbage collected.
17450 /// `methodID` must be valid, static and actually be a method of `obj`, return char and have 0 arguments
17451 ///
17452 pub unsafe fn CallStaticCharMethod0(&self, obj: jclass, methodID: jmethodID) -> jchar {
17453 unsafe {
17454 #[cfg(feature = "asserts")]
17455 {
17456 self.check_not_critical("CallStaticCharMethod");
17457 self.check_no_exception("CallStaticCharMethod");
17458 self.check_return_type_static("CallStaticCharMethod", obj, methodID, "char");
17459 }
17460 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jchar>(123)(self.vtable, obj, methodID)
17461 }
17462 }
17463
17464 ///
17465 /// Calls a static java method that has 1 arguments and returns char
17466 ///
17467 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17468 ///
17469 ///
17470 /// # Arguments
17471 /// * `obj` - which object the method should be called on
17472 /// * must be valid
17473 /// * must not be null
17474 /// * must not be already garbage collected
17475 ///
17476 /// * `methodID` - method id of the method
17477 /// * must not be null
17478 /// * must be valid
17479 /// * must be a static
17480 /// * must actually be a method of `obj`
17481 /// * must refer to a method with 1 arguments
17482 ///
17483 /// # Returns
17484 /// Whatever the method returned or 0 if it threw
17485 ///
17486 /// # Throws Java Exception
17487 /// * Whatever the method threw
17488 ///
17489 ///
17490 /// # Panics
17491 /// if asserts feature is enabled and UB was detected
17492 ///
17493 /// # Safety
17494 ///
17495 /// Current thread must not be detached from JNI.
17496 ///
17497 /// Current thread must not be currently throwing an exception.
17498 ///
17499 /// Current thread does not hold a critical reference.
17500 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17501 ///
17502 /// `obj` must a valid and not already garbage collected.
17503 /// `methodID` must be valid, static and actually be a method of `obj`, return char and have 1 arguments
17504 ///
17505 pub unsafe fn CallStaticCharMethod1<A: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A) -> jchar {
17506 unsafe {
17507 #[cfg(feature = "asserts")]
17508 {
17509 self.check_not_critical("CallStaticCharMethod");
17510 self.check_no_exception("CallStaticCharMethod");
17511 self.check_return_type_static("CallStaticCharMethod", obj, methodID, "char");
17512 self.check_parameter_types_static("CallStaticCharMethod", obj, methodID, arg1, 0, 1);
17513 }
17514 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jchar>(123)(self.vtable, obj, methodID, arg1)
17515 }
17516 }
17517
17518 ///
17519 /// Calls a static java method that has 2 arguments and returns char
17520 ///
17521 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17522 ///
17523 ///
17524 /// # Arguments
17525 /// * `obj` - which object the method should be called on
17526 /// * must be valid
17527 /// * must not be null
17528 /// * must not be already garbage collected
17529 ///
17530 /// * `methodID` - method id of the method
17531 /// * must not be null
17532 /// * must be valid
17533 /// * must be a static
17534 /// * must actually be a method of `obj`
17535 /// * must refer to a method with 2 arguments
17536 ///
17537 /// # Returns
17538 /// Whatever the method returned or 0 if it threw
17539 ///
17540 /// # Throws Java Exception
17541 /// * Whatever the method threw
17542 ///
17543 ///
17544 /// # Panics
17545 /// if asserts feature is enabled and UB was detected
17546 ///
17547 /// # Safety
17548 ///
17549 /// Current thread must not be detached from JNI.
17550 ///
17551 /// Current thread must not be currently throwing an exception.
17552 ///
17553 /// Current thread does not hold a critical reference.
17554 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17555 ///
17556 /// `obj` must a valid and not already garbage collected.
17557 /// `methodID` must be valid, static and actually be a method of `obj`, return char and have 2 arguments
17558 ///
17559 pub unsafe fn CallStaticCharMethod2<A: JType, B: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jchar {
17560 unsafe {
17561 #[cfg(feature = "asserts")]
17562 {
17563 self.check_not_critical("CallStaticCharMethod");
17564 self.check_no_exception("CallStaticCharMethod");
17565 self.check_return_type_static("CallStaticCharMethod", obj, methodID, "char");
17566 self.check_parameter_types_static("CallStaticCharMethod", obj, methodID, arg1, 0, 2);
17567 self.check_parameter_types_static("CallStaticCharMethod", obj, methodID, arg2, 1, 2);
17568 }
17569 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jchar>(123)(self.vtable, obj, methodID, arg1, arg2)
17570 }
17571 }
17572
17573 ///
17574 /// Calls a static java method that has 3 arguments and returns char
17575 ///
17576 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17577 ///
17578 ///
17579 /// # Arguments
17580 /// * `obj` - which object the method should be called on
17581 /// * must be valid
17582 /// * must not be null
17583 /// * must not be already garbage collected
17584 ///
17585 /// * `methodID` - method id of the method
17586 /// * must not be null
17587 /// * must be valid
17588 /// * must be a static
17589 /// * must actually be a method of `obj`
17590 /// * must refer to a method with 3 arguments
17591 ///
17592 /// # Returns
17593 /// Whatever the method returned or 0 if it threw
17594 ///
17595 /// # Throws Java Exception
17596 /// * Whatever the method threw
17597 ///
17598 ///
17599 /// # Panics
17600 /// if asserts feature is enabled and UB was detected
17601 ///
17602 /// # Safety
17603 ///
17604 /// Current thread must not be detached from JNI.
17605 ///
17606 /// Current thread must not be currently throwing an exception.
17607 ///
17608 /// Current thread does not hold a critical reference.
17609 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17610 ///
17611 /// `obj` must a valid and not already garbage collected.
17612 /// `methodID` must be valid, static and actually be a method of `obj`, return char and have 3 arguments
17613 ///
17614 pub unsafe fn CallStaticCharMethod3<A: JType, B: JType, C: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jchar {
17615 unsafe {
17616 #[cfg(feature = "asserts")]
17617 {
17618 self.check_not_critical("CallStaticCharMethod");
17619 self.check_no_exception("CallStaticCharMethod");
17620 self.check_return_type_static("CallStaticCharMethod", obj, methodID, "char");
17621 self.check_parameter_types_static("CallStaticCharMethod", obj, methodID, arg1, 0, 3);
17622 self.check_parameter_types_static("CallStaticCharMethod", obj, methodID, arg2, 1, 3);
17623 self.check_parameter_types_static("CallStaticCharMethod", obj, methodID, arg3, 2, 3);
17624 }
17625 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jchar>(123)(self.vtable, obj, methodID, arg1, arg2, arg3)
17626 }
17627 }
17628
17629 ///
17630 /// Calls a static java method that returns a short
17631 ///
17632 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17633 ///
17634 ///
17635 /// # Arguments
17636 /// * `obj` - which object the method should be called on
17637 /// * must be valid
17638 /// * must not be null
17639 /// * must not be already garbage collected
17640 ///
17641 /// * `methodID` - method id of the method
17642 /// * must not be null
17643 /// * must be valid
17644 /// * must not be a static
17645 /// * must actually be a method of `obj`
17646 ///
17647 /// * `args` - argument pointer
17648 /// * can be null if the method has no arguments
17649 /// * must not be null otherwise and point to the exact number of arguments the method expects
17650 ///
17651 /// # Returns
17652 /// Whatever the method returned or 0 if it threw
17653 ///
17654 /// # Throws Java Exception
17655 /// * Whatever the method threw
17656 ///
17657 ///
17658 /// # Panics
17659 /// if asserts feature is enabled and UB was detected
17660 ///
17661 /// # Safety
17662 ///
17663 /// Current thread must not be detached from JNI.
17664 ///
17665 /// Current thread must not be currently throwing an exception.
17666 ///
17667 /// Current thread does not hold a critical reference.
17668 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17669 ///
17670 /// `obj` must a valid and not already garbage collected.
17671 /// `methodID` must be valid, static and actually be a method of `obj` class and return a short
17672 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
17673 /// `args` union must contain types that match the java methods parameters.
17674 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
17675 ///
17676 pub unsafe fn CallStaticShortMethodA(&self, obj: jclass, methodID: jmethodID, args: *const jtype) -> jshort {
17677 unsafe {
17678 #[cfg(feature = "asserts")]
17679 {
17680 self.check_not_critical("CallStaticShortMethodA");
17681 self.check_no_exception("CallStaticShortMethodA");
17682 self.check_return_type_static("CallStaticShortMethodA", obj, methodID, "short");
17683 }
17684 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jshort>(128)(self.vtable, obj, methodID, args)
17685 }
17686 }
17687
17688 ///
17689 /// Calls a static java method that has 0 arguments and returns short
17690 ///
17691 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17692 ///
17693 ///
17694 /// # Arguments
17695 /// * `obj` - which object the method should be called on
17696 /// * must be valid
17697 /// * must not be null
17698 /// * must not be already garbage collected
17699 ///
17700 /// * `methodID` - method id of the method
17701 /// * must not be null
17702 /// * must be valid
17703 /// * must be a static
17704 /// * must actually be a method of `obj`
17705 /// * must refer to a method with 0 arguments
17706 ///
17707 /// # Returns
17708 /// Whatever the method returned or 0 if it threw
17709 ///
17710 /// # Throws Java Exception
17711 /// * Whatever the method threw
17712 ///
17713 ///
17714 /// # Panics
17715 /// if asserts feature is enabled and UB was detected
17716 ///
17717 /// # Safety
17718 ///
17719 /// Current thread must not be detached from JNI.
17720 ///
17721 /// Current thread must not be currently throwing an exception.
17722 ///
17723 /// Current thread does not hold a critical reference.
17724 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17725 ///
17726 /// `obj` must a valid and not already garbage collected.
17727 /// `methodID` must be valid, static and actually be a method of `obj`, return short and have 0 arguments
17728 ///
17729 pub unsafe fn CallStaticShortMethod0(&self, obj: jclass, methodID: jmethodID) -> jshort {
17730 unsafe {
17731 #[cfg(feature = "asserts")]
17732 {
17733 self.check_not_critical("CallStaticShortMethod");
17734 self.check_no_exception("CallStaticShortMethod");
17735 self.check_return_type_static("CallStaticShortMethod", obj, methodID, "short");
17736 }
17737 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jshort>(126)(self.vtable, obj, methodID)
17738 }
17739 }
17740
17741 ///
17742 /// Calls a static java method that has 1 arguments and returns short
17743 ///
17744 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17745 ///
17746 ///
17747 /// # Arguments
17748 /// * `obj` - which object the method should be called on
17749 /// * must be valid
17750 /// * must not be null
17751 /// * must not be already garbage collected
17752 ///
17753 /// * `methodID` - method id of the method
17754 /// * must not be null
17755 /// * must be valid
17756 /// * must be a static
17757 /// * must actually be a method of `obj`
17758 /// * must refer to a method with 1 arguments
17759 ///
17760 /// # Returns
17761 /// Whatever the method returned or 0 if it threw
17762 ///
17763 /// # Throws Java Exception
17764 /// * Whatever the method threw
17765 ///
17766 ///
17767 /// # Panics
17768 /// if asserts feature is enabled and UB was detected
17769 ///
17770 /// # Safety
17771 ///
17772 /// Current thread must not be detached from JNI.
17773 ///
17774 /// Current thread must not be currently throwing an exception.
17775 ///
17776 /// Current thread does not hold a critical reference.
17777 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17778 ///
17779 /// `obj` must a valid and not already garbage collected.
17780 /// `methodID` must be valid, static and actually be a method of `obj`, return short and have 1 arguments
17781 ///
17782 pub unsafe fn CallStaticShortMethod1<A: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A) -> jshort {
17783 unsafe {
17784 #[cfg(feature = "asserts")]
17785 {
17786 self.check_not_critical("CallStaticShortMethod");
17787 self.check_no_exception("CallStaticShortMethod");
17788 self.check_return_type_static("CallStaticShortMethod", obj, methodID, "short");
17789 self.check_parameter_types_static("CallStaticShortMethod", obj, methodID, arg1, 0, 1);
17790 }
17791 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jshort>(126)(self.vtable, obj, methodID, arg1)
17792 }
17793 }
17794
17795 ///
17796 /// Calls a static java method that has 2 arguments and returns short
17797 ///
17798 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17799 ///
17800 ///
17801 /// # Arguments
17802 /// * `obj` - which object the method should be called on
17803 /// * must be valid
17804 /// * must not be null
17805 /// * must not be already garbage collected
17806 ///
17807 /// * `methodID` - method id of the method
17808 /// * must not be null
17809 /// * must be valid
17810 /// * must be a static
17811 /// * must actually be a method of `obj`
17812 /// * must refer to a method with 2 arguments
17813 ///
17814 /// # Returns
17815 /// Whatever the method returned or 0 if it threw
17816 ///
17817 /// # Throws Java Exception
17818 /// * Whatever the method threw
17819 ///
17820 ///
17821 /// # Panics
17822 /// if asserts feature is enabled and UB was detected
17823 ///
17824 /// # Safety
17825 ///
17826 /// Current thread must not be detached from JNI.
17827 ///
17828 /// Current thread must not be currently throwing an exception.
17829 ///
17830 /// Current thread does not hold a critical reference.
17831 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17832 ///
17833 /// `obj` must a valid and not already garbage collected.
17834 /// `methodID` must be valid, static and actually be a method of `obj`, return short and have 2 arguments
17835 ///
17836 pub unsafe fn CallStaticShortMethod2<A: JType, B: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jshort {
17837 unsafe {
17838 #[cfg(feature = "asserts")]
17839 {
17840 self.check_not_critical("CallStaticShortMethod");
17841 self.check_no_exception("CallStaticShortMethod");
17842 self.check_return_type_static("CallStaticShortMethod", obj, methodID, "short");
17843 self.check_parameter_types_static("CallStaticShortMethod", obj, methodID, arg1, 0, 2);
17844 self.check_parameter_types_static("CallStaticShortMethod", obj, methodID, arg2, 1, 2);
17845 }
17846 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jshort>(126)(self.vtable, obj, methodID, arg1, arg2)
17847 }
17848 }
17849
17850 ///
17851 /// Calls a static java method that has 3 arguments and returns short
17852 ///
17853 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17854 ///
17855 ///
17856 /// # Arguments
17857 /// * `obj` - which object the method should be called on
17858 /// * must be valid
17859 /// * must not be null
17860 /// * must not be already garbage collected
17861 ///
17862 /// * `methodID` - method id of the method
17863 /// * must not be null
17864 /// * must be valid
17865 /// * must be a static
17866 /// * must actually be a method of `obj`
17867 /// * must refer to a method with 3 arguments
17868 ///
17869 /// # Returns
17870 /// Whatever the method returned or 0 if it threw
17871 ///
17872 /// # Throws Java Exception
17873 /// * Whatever the method threw
17874 ///
17875 ///
17876 /// # Panics
17877 /// if asserts feature is enabled and UB was detected
17878 ///
17879 /// # Safety
17880 ///
17881 /// Current thread must not be detached from JNI.
17882 ///
17883 /// Current thread must not be currently throwing an exception.
17884 ///
17885 /// Current thread does not hold a critical reference.
17886 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17887 ///
17888 /// `obj` must a valid and not already garbage collected.
17889 /// `methodID` must be valid, static and actually be a method of `obj`, return short and have 3 arguments
17890 ///
17891 pub unsafe fn CallStaticShortMethod3<A: JType, B: JType, C: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jshort {
17892 unsafe {
17893 #[cfg(feature = "asserts")]
17894 {
17895 self.check_not_critical("CallStaticShortMethod");
17896 self.check_no_exception("CallStaticShortMethod");
17897 self.check_return_type_static("CallStaticShortMethod", obj, methodID, "short");
17898 self.check_parameter_types_static("CallStaticShortMethod", obj, methodID, arg1, 0, 3);
17899 self.check_parameter_types_static("CallStaticShortMethod", obj, methodID, arg2, 1, 3);
17900 self.check_parameter_types_static("CallStaticShortMethod", obj, methodID, arg3, 2, 3);
17901 }
17902 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jshort>(126)(self.vtable, obj, methodID, arg1, arg2, arg3)
17903 }
17904 }
17905
17906 ///
17907 /// Calls a static java method that returns a int
17908 ///
17909 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17910 ///
17911 ///
17912 /// # Arguments
17913 /// * `obj` - which object the method should be called on
17914 /// * must be valid
17915 /// * must not be null
17916 /// * must not be already garbage collected
17917 ///
17918 /// * `methodID` - method id of the method
17919 /// * must not be null
17920 /// * must be valid
17921 /// * must not be a static
17922 /// * must actually be a method of `obj`
17923 ///
17924 /// * `args` - argument pointer
17925 /// * can be null if the method has no arguments
17926 /// * must not be null otherwise and point to the exact number of arguments the method expects
17927 ///
17928 /// # Returns
17929 /// Whatever the method returned or 0 if it threw
17930 ///
17931 /// # Throws Java Exception
17932 /// * Whatever the method threw
17933 ///
17934 ///
17935 /// # Panics
17936 /// if asserts feature is enabled and UB was detected
17937 ///
17938 /// # Safety
17939 ///
17940 /// Current thread must not be detached from JNI.
17941 ///
17942 /// Current thread must not be currently throwing an exception.
17943 ///
17944 /// Current thread does not hold a critical reference.
17945 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
17946 ///
17947 /// `obj` must a valid and not already garbage collected.
17948 /// `methodID` must be valid, static and actually be a method of `obj` class and return a int
17949 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
17950 /// `args` union must contain types that match the java methods parameters.
17951 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
17952 ///
17953 pub unsafe fn CallStaticIntMethodA(&self, obj: jclass, methodID: jmethodID, args: *const jtype) -> jint {
17954 unsafe {
17955 #[cfg(feature = "asserts")]
17956 {
17957 self.check_not_critical("CallStaticIntMethodA");
17958 self.check_no_exception("CallStaticIntMethodA");
17959 self.check_return_type_static("CallStaticIntMethodA", obj, methodID, "int");
17960 }
17961 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jint>(131)(self.vtable, obj, methodID, args)
17962 }
17963 }
17964
17965 ///
17966 /// Calls a static java method that has 0 arguments and returns int
17967 ///
17968 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
17969 ///
17970 ///
17971 /// # Arguments
17972 /// * `obj` - which object the method should be called on
17973 /// * must be valid
17974 /// * must not be null
17975 /// * must not be already garbage collected
17976 ///
17977 /// * `methodID` - method id of the method
17978 /// * must not be null
17979 /// * must be valid
17980 /// * must be a static
17981 /// * must actually be a method of `obj`
17982 /// * must refer to a method with 0 arguments
17983 ///
17984 /// # Returns
17985 /// Whatever the method returned or 0 if it threw
17986 ///
17987 /// # Throws Java Exception
17988 /// * Whatever the method threw
17989 ///
17990 ///
17991 /// # Panics
17992 /// if asserts feature is enabled and UB was detected
17993 ///
17994 /// # Safety
17995 ///
17996 /// Current thread must not be detached from JNI.
17997 ///
17998 /// Current thread must not be currently throwing an exception.
17999 ///
18000 /// Current thread does not hold a critical reference.
18001 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18002 ///
18003 /// `obj` must a valid and not already garbage collected.
18004 /// `methodID` must be valid, static and actually be a method of `obj`, return int and have 0 arguments
18005 ///
18006 pub unsafe fn CallStaticIntMethod0(&self, obj: jclass, methodID: jmethodID) -> jint {
18007 unsafe {
18008 #[cfg(feature = "asserts")]
18009 {
18010 self.check_not_critical("CallStaticIntMethod");
18011 self.check_no_exception("CallStaticIntMethod");
18012 self.check_return_type_static("CallStaticIntMethod", obj, methodID, "int");
18013 }
18014 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jint>(129)(self.vtable, obj, methodID)
18015 }
18016 }
18017
18018 ///
18019 /// Calls a static java method that has 1 arguments and returns int
18020 ///
18021 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18022 ///
18023 ///
18024 /// # Arguments
18025 /// * `obj` - which object the method should be called on
18026 /// * must be valid
18027 /// * must not be null
18028 /// * must not be already garbage collected
18029 ///
18030 /// * `methodID` - method id of the method
18031 /// * must not be null
18032 /// * must be valid
18033 /// * must be a static
18034 /// * must actually be a method of `obj`
18035 /// * must refer to a method with 1 arguments
18036 ///
18037 /// # Returns
18038 /// Whatever the method returned or 0 if it threw
18039 ///
18040 /// # Throws Java Exception
18041 /// * Whatever the method threw
18042 ///
18043 ///
18044 /// # Panics
18045 /// if asserts feature is enabled and UB was detected
18046 ///
18047 /// # Safety
18048 ///
18049 /// Current thread must not be detached from JNI.
18050 ///
18051 /// Current thread must not be currently throwing an exception.
18052 ///
18053 /// Current thread does not hold a critical reference.
18054 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18055 ///
18056 /// `obj` must a valid and not already garbage collected.
18057 /// `methodID` must be valid, static and actually be a method of `obj`, return int and have 1 arguments
18058 ///
18059 pub unsafe fn CallStaticIntMethod1<A: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A) -> jint {
18060 unsafe {
18061 #[cfg(feature = "asserts")]
18062 {
18063 self.check_not_critical("CallStaticIntMethod");
18064 self.check_no_exception("CallStaticIntMethod");
18065 self.check_return_type_static("CallStaticIntMethod", obj, methodID, "int");
18066 self.check_parameter_types_static("CallStaticIntMethod", obj, methodID, arg1, 0, 1);
18067 }
18068 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jint>(129)(self.vtable, obj, methodID, arg1)
18069 }
18070 }
18071
18072 ///
18073 /// Calls a static java method that has 2 arguments and returns int
18074 ///
18075 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18076 ///
18077 ///
18078 /// # Arguments
18079 /// * `obj` - which object the method should be called on
18080 /// * must be valid
18081 /// * must not be null
18082 /// * must not be already garbage collected
18083 ///
18084 /// * `methodID` - method id of the method
18085 /// * must not be null
18086 /// * must be valid
18087 /// * must be a static
18088 /// * must actually be a method of `obj`
18089 /// * must refer to a method with 2 arguments
18090 ///
18091 /// # Returns
18092 /// Whatever the method returned or 0 if it threw
18093 ///
18094 /// # Throws Java Exception
18095 /// * Whatever the method threw
18096 ///
18097 ///
18098 /// # Panics
18099 /// if asserts feature is enabled and UB was detected
18100 ///
18101 /// # Safety
18102 ///
18103 /// Current thread must not be detached from JNI.
18104 ///
18105 /// Current thread must not be currently throwing an exception.
18106 ///
18107 /// Current thread does not hold a critical reference.
18108 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18109 ///
18110 /// `obj` must a valid and not already garbage collected.
18111 /// `methodID` must be valid, static and actually be a method of `obj`, return int and have 2 arguments
18112 ///
18113 pub unsafe fn CallStaticIntMethod2<A: JType, B: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jint {
18114 unsafe {
18115 #[cfg(feature = "asserts")]
18116 {
18117 self.check_not_critical("CallStaticIntMethod");
18118 self.check_no_exception("CallStaticIntMethod");
18119 self.check_return_type_static("CallStaticIntMethod", obj, methodID, "int");
18120 self.check_parameter_types_static("CallStaticIntMethod", obj, methodID, arg1, 0, 2);
18121 self.check_parameter_types_static("CallStaticIntMethod", obj, methodID, arg2, 1, 2);
18122 }
18123 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jint>(129)(self.vtable, obj, methodID, arg1, arg2)
18124 }
18125 }
18126
18127 ///
18128 /// Calls a static java method that has 3 arguments and returns int
18129 ///
18130 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18131 ///
18132 ///
18133 /// # Arguments
18134 /// * `obj` - which object the method should be called on
18135 /// * must be valid
18136 /// * must not be null
18137 /// * must not be already garbage collected
18138 ///
18139 /// * `methodID` - method id of the method
18140 /// * must not be null
18141 /// * must be valid
18142 /// * must be a static
18143 /// * must actually be a method of `obj`
18144 /// * must refer to a method with 3 arguments
18145 ///
18146 /// # Returns
18147 /// Whatever the method returned or 0 if it threw
18148 ///
18149 /// # Throws Java Exception
18150 /// * Whatever the method threw
18151 ///
18152 ///
18153 /// # Panics
18154 /// if asserts feature is enabled and UB was detected
18155 ///
18156 /// # Safety
18157 ///
18158 /// Current thread must not be detached from JNI.
18159 ///
18160 /// Current thread must not be currently throwing an exception.
18161 ///
18162 /// Current thread does not hold a critical reference.
18163 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18164 ///
18165 /// `obj` must a valid and not already garbage collected.
18166 /// `methodID` must be valid, static and actually be a method of `obj`, return int and have 3 arguments
18167 ///
18168 pub unsafe fn CallStaticIntMethod3<A: JType, B: JType, C: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jint {
18169 unsafe {
18170 #[cfg(feature = "asserts")]
18171 {
18172 self.check_not_critical("CallStaticIntMethod");
18173 self.check_no_exception("CallStaticIntMethod");
18174 self.check_return_type_static("CallStaticIntMethod", obj, methodID, "int");
18175 self.check_parameter_types_static("CallStaticIntMethod", obj, methodID, arg1, 0, 3);
18176 self.check_parameter_types_static("CallStaticIntMethod", obj, methodID, arg2, 1, 3);
18177 self.check_parameter_types_static("CallStaticIntMethod", obj, methodID, arg3, 2, 3);
18178 }
18179 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jint>(129)(self.vtable, obj, methodID, arg1, arg2, arg3)
18180 }
18181 }
18182
18183 ///
18184 /// Calls a static java method that returns a long
18185 ///
18186 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18187 ///
18188 ///
18189 /// # Arguments
18190 /// * `obj` - which object the method should be called on
18191 /// * must be valid
18192 /// * must not be null
18193 /// * must not be already garbage collected
18194 ///
18195 /// * `methodID` - method id of the method
18196 /// * must not be null
18197 /// * must be valid
18198 /// * must not be a static
18199 /// * must actually be a method of `obj`
18200 ///
18201 /// * `args` - argument pointer
18202 /// * can be null if the method has no arguments
18203 /// * must not be null otherwise and point to the exact number of arguments the method expects
18204 ///
18205 /// # Returns
18206 /// Whatever the method returned or 0 if it threw
18207 ///
18208 /// # Throws Java Exception
18209 /// * Whatever the method threw
18210 ///
18211 ///
18212 /// # Panics
18213 /// if asserts feature is enabled and UB was detected
18214 ///
18215 /// # Safety
18216 ///
18217 /// Current thread must not be detached from JNI.
18218 ///
18219 /// Current thread must not be currently throwing an exception.
18220 ///
18221 /// Current thread does not hold a critical reference.
18222 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18223 ///
18224 /// `obj` must a valid and not already garbage collected.
18225 /// `methodID` must be valid, static and actually be a method of `obj` class and return a long
18226 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
18227 /// `args` union must contain types that match the java methods parameters.
18228 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
18229 ///
18230 pub unsafe fn CallStaticLongMethodA(&self, obj: jclass, methodID: jmethodID, args: *const jtype) -> jlong {
18231 unsafe {
18232 #[cfg(feature = "asserts")]
18233 {
18234 self.check_not_critical("CallStaticLongMethodA");
18235 self.check_no_exception("CallStaticLongMethodA");
18236 self.check_return_type_static("CallStaticLongMethodA", obj, methodID, "long");
18237 }
18238 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jlong>(134)(self.vtable, obj, methodID, args)
18239 }
18240 }
18241
18242 ///
18243 /// Calls a static java method that has 0 arguments and returns long
18244 ///
18245 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18246 ///
18247 ///
18248 /// # Arguments
18249 /// * `obj` - which object the method should be called on
18250 /// * must be valid
18251 /// * must not be null
18252 /// * must not be already garbage collected
18253 ///
18254 /// * `methodID` - method id of the method
18255 /// * must not be null
18256 /// * must be valid
18257 /// * must be a static
18258 /// * must actually be a method of `obj`
18259 /// * must refer to a method with 0 arguments
18260 ///
18261 /// # Returns
18262 /// Whatever the method returned or 0 if it threw
18263 ///
18264 /// # Throws Java Exception
18265 /// * Whatever the method threw
18266 ///
18267 ///
18268 /// # Panics
18269 /// if asserts feature is enabled and UB was detected
18270 ///
18271 /// # Safety
18272 ///
18273 /// Current thread must not be detached from JNI.
18274 ///
18275 /// Current thread must not be currently throwing an exception.
18276 ///
18277 /// Current thread does not hold a critical reference.
18278 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18279 ///
18280 /// `obj` must a valid and not already garbage collected.
18281 /// `methodID` must be valid, static and actually be a method of `obj`, return long and have 0 arguments
18282 ///
18283 pub unsafe fn CallStaticLongMethod0(&self, obj: jclass, methodID: jmethodID) -> jlong {
18284 unsafe {
18285 #[cfg(feature = "asserts")]
18286 {
18287 self.check_not_critical("CallStaticLongMethod");
18288 self.check_no_exception("CallStaticLongMethod");
18289 self.check_return_type_static("CallStaticLongMethod", obj, methodID, "long");
18290 }
18291 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jlong>(132)(self.vtable, obj, methodID)
18292 }
18293 }
18294
18295 ///
18296 /// Calls a static java method that has 1 arguments and returns long
18297 ///
18298 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18299 ///
18300 ///
18301 /// # Arguments
18302 /// * `obj` - which object the method should be called on
18303 /// * must be valid
18304 /// * must not be null
18305 /// * must not be already garbage collected
18306 ///
18307 /// * `methodID` - method id of the method
18308 /// * must not be null
18309 /// * must be valid
18310 /// * must be a static
18311 /// * must actually be a method of `obj`
18312 /// * must refer to a method with 1 arguments
18313 ///
18314 /// # Returns
18315 /// Whatever the method returned or 0 if it threw
18316 ///
18317 /// # Throws Java Exception
18318 /// * Whatever the method threw
18319 ///
18320 ///
18321 /// # Panics
18322 /// if asserts feature is enabled and UB was detected
18323 ///
18324 /// # Safety
18325 ///
18326 /// Current thread must not be detached from JNI.
18327 ///
18328 /// Current thread must not be currently throwing an exception.
18329 ///
18330 /// Current thread does not hold a critical reference.
18331 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18332 ///
18333 /// `obj` must a valid and not already garbage collected.
18334 /// `methodID` must be valid, static and actually be a method of `obj`, return long and have 1 arguments
18335 ///
18336 pub unsafe fn CallStaticLongMethod1<A: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A) -> jlong {
18337 unsafe {
18338 #[cfg(feature = "asserts")]
18339 {
18340 self.check_not_critical("CallStaticLongMethod");
18341 self.check_no_exception("CallStaticLongMethod");
18342 self.check_return_type_static("CallStaticLongMethod", obj, methodID, "long");
18343 self.check_parameter_types_static("CallStaticLongMethod", obj, methodID, arg1, 0, 1);
18344 }
18345 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jlong>(132)(self.vtable, obj, methodID, arg1)
18346 }
18347 }
18348
18349 ///
18350 /// Calls a static java method that has 2 arguments and returns long
18351 ///
18352 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18353 ///
18354 ///
18355 /// # Arguments
18356 /// * `obj` - which object the method should be called on
18357 /// * must be valid
18358 /// * must not be null
18359 /// * must not be already garbage collected
18360 ///
18361 /// * `methodID` - method id of the method
18362 /// * must not be null
18363 /// * must be valid
18364 /// * must be a static
18365 /// * must actually be a method of `obj`
18366 /// * must refer to a method with 2 arguments
18367 ///
18368 /// # Returns
18369 /// Whatever the method returned or 0 if it threw
18370 ///
18371 /// # Throws Java Exception
18372 /// * Whatever the method threw
18373 ///
18374 ///
18375 /// # Panics
18376 /// if asserts feature is enabled and UB was detected
18377 ///
18378 /// # Safety
18379 ///
18380 /// Current thread must not be detached from JNI.
18381 ///
18382 /// Current thread must not be currently throwing an exception.
18383 ///
18384 /// Current thread does not hold a critical reference.
18385 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18386 ///
18387 /// `obj` must a valid and not already garbage collected.
18388 /// `methodID` must be valid, static and actually be a method of `obj`, return long and have 2 arguments
18389 ///
18390 pub unsafe fn CallStaticLongMethod2<A: JType, B: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jlong {
18391 unsafe {
18392 #[cfg(feature = "asserts")]
18393 {
18394 self.check_not_critical("CallStaticLongMethod");
18395 self.check_no_exception("CallStaticLongMethod");
18396 self.check_return_type_static("CallStaticLongMethod", obj, methodID, "long");
18397 self.check_parameter_types_static("CallStaticLongMethod", obj, methodID, arg1, 0, 2);
18398 self.check_parameter_types_static("CallStaticLongMethod", obj, methodID, arg2, 1, 2);
18399 }
18400 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jlong>(132)(self.vtable, obj, methodID, arg1, arg2)
18401 }
18402 }
18403
18404 ///
18405 /// Calls a static java method that has 3 arguments and returns long
18406 ///
18407 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18408 ///
18409 ///
18410 /// # Arguments
18411 /// * `obj` - which object the method should be called on
18412 /// * must be valid
18413 /// * must not be null
18414 /// * must not be already garbage collected
18415 ///
18416 /// * `methodID` - method id of the method
18417 /// * must not be null
18418 /// * must be valid
18419 /// * must be a static
18420 /// * must actually be a method of `obj`
18421 /// * must refer to a method with 3 arguments
18422 ///
18423 /// # Returns
18424 /// Whatever the method returned or 0 if it threw
18425 ///
18426 /// # Throws Java Exception
18427 /// * Whatever the method threw
18428 ///
18429 ///
18430 /// # Panics
18431 /// if asserts feature is enabled and UB was detected
18432 ///
18433 /// # Safety
18434 ///
18435 /// Current thread must not be detached from JNI.
18436 ///
18437 /// Current thread must not be currently throwing an exception.
18438 ///
18439 /// Current thread does not hold a critical reference.
18440 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18441 ///
18442 /// `obj` must a valid and not already garbage collected.
18443 /// `methodID` must be valid, static and actually be a method of `obj`, return long and have 3 arguments
18444 ///
18445 pub unsafe fn CallStaticLongMethod3<A: JType, B: JType, C: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jlong {
18446 unsafe {
18447 #[cfg(feature = "asserts")]
18448 {
18449 self.check_not_critical("CallStaticLongMethod");
18450 self.check_no_exception("CallStaticLongMethod");
18451 self.check_return_type_static("CallStaticLongMethod", obj, methodID, "long");
18452 self.check_parameter_types_static("CallStaticLongMethod", obj, methodID, arg1, 0, 3);
18453 self.check_parameter_types_static("CallStaticLongMethod", obj, methodID, arg2, 1, 3);
18454 self.check_parameter_types_static("CallStaticLongMethod", obj, methodID, arg3, 2, 3);
18455 }
18456 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jlong>(132)(self.vtable, obj, methodID, arg1, arg2, arg3)
18457 }
18458 }
18459
18460 ///
18461 /// Calls a static java method that returns a float
18462 ///
18463 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18464 ///
18465 ///
18466 /// # Arguments
18467 /// * `obj` - which object the method should be called on
18468 /// * must be valid
18469 /// * must not be null
18470 /// * must not be already garbage collected
18471 ///
18472 /// * `methodID` - method id of the method
18473 /// * must not be null
18474 /// * must be valid
18475 /// * must not be a static
18476 /// * must actually be a method of `obj`
18477 ///
18478 /// * `args` - argument pointer
18479 /// * can be null if the method has no arguments
18480 /// * must not be null otherwise and point to the exact number of arguments the method expects
18481 ///
18482 /// # Returns
18483 /// Whatever the method returned or 0 if it threw
18484 ///
18485 /// # Throws Java Exception
18486 /// * Whatever the method threw
18487 ///
18488 ///
18489 /// # Panics
18490 /// if asserts feature is enabled and UB was detected
18491 ///
18492 /// # Safety
18493 ///
18494 /// Current thread must not be detached from JNI.
18495 ///
18496 /// Current thread must not be currently throwing an exception.
18497 ///
18498 /// Current thread does not hold a critical reference.
18499 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18500 ///
18501 /// `obj` must a valid and not already garbage collected.
18502 /// `methodID` must be valid, static and actually be a method of `obj` class and return a float
18503 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
18504 /// `args` union must contain types that match the java methods parameters.
18505 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
18506 ///
18507 pub unsafe fn CallStaticFloatMethodA(&self, obj: jclass, methodID: jmethodID, args: *const jtype) -> jfloat {
18508 unsafe {
18509 #[cfg(feature = "asserts")]
18510 {
18511 self.check_not_critical("CallStaticFloatMethodA");
18512 self.check_no_exception("CallStaticFloatMethodA");
18513 self.check_return_type_static("CallStaticFloatMethodA", obj, methodID, "float");
18514 }
18515 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jfloat>(137)(self.vtable, obj, methodID, args)
18516 }
18517 }
18518
18519 ///
18520 /// Calls a static java method that has 0 arguments and returns double
18521 ///
18522 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18523 ///
18524 ///
18525 /// # Arguments
18526 /// * `obj` - which object the method should be called on
18527 /// * must be valid
18528 /// * must not be null
18529 /// * must not be already garbage collected
18530 ///
18531 /// * `methodID` - method id of the method
18532 /// * must not be null
18533 /// * must be valid
18534 /// * must be a static
18535 /// * must actually be a method of `obj`
18536 /// * must refer to a method with 0 arguments
18537 ///
18538 /// # Returns
18539 /// Whatever the method returned or 0 if it threw
18540 ///
18541 /// # Throws Java Exception
18542 /// * Whatever the method threw
18543 ///
18544 ///
18545 /// # Panics
18546 /// if asserts feature is enabled and UB was detected
18547 ///
18548 /// # Safety
18549 ///
18550 /// Current thread must not be detached from JNI.
18551 ///
18552 /// Current thread must not be currently throwing an exception.
18553 ///
18554 /// Current thread does not hold a critical reference.
18555 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18556 ///
18557 /// `obj` must a valid and not already garbage collected.
18558 /// `methodID` must be valid, static and actually be a method of `obj`, return float and have 0 arguments
18559 ///
18560 pub unsafe fn CallStaticFloatMethod0(&self, obj: jclass, methodID: jmethodID) -> jfloat {
18561 unsafe {
18562 #[cfg(feature = "asserts")]
18563 {
18564 self.check_not_critical("CallStaticFloatMethod");
18565 self.check_no_exception("CallStaticFloatMethod");
18566 self.check_return_type_static("CallStaticFloatMethod", obj, methodID, "float");
18567 }
18568 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jfloat>(135)(self.vtable, obj, methodID)
18569 }
18570 }
18571
18572 ///
18573 /// Calls a static java method that has 1 arguments and returns double
18574 ///
18575 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18576 ///
18577 ///
18578 /// # Arguments
18579 /// * `obj` - which object the method should be called on
18580 /// * must be valid
18581 /// * must not be null
18582 /// * must not be already garbage collected
18583 ///
18584 /// * `methodID` - method id of the method
18585 /// * must not be null
18586 /// * must be valid
18587 /// * must be a static
18588 /// * must actually be a method of `obj`
18589 /// * must refer to a method with 1 arguments
18590 ///
18591 /// # Returns
18592 /// Whatever the method returned or 0 if it threw
18593 ///
18594 /// # Throws Java Exception
18595 /// * Whatever the method threw
18596 ///
18597 ///
18598 /// # Panics
18599 /// if asserts feature is enabled and UB was detected
18600 ///
18601 /// # Safety
18602 ///
18603 /// Current thread must not be detached from JNI.
18604 ///
18605 /// Current thread must not be currently throwing an exception.
18606 ///
18607 /// Current thread does not hold a critical reference.
18608 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18609 ///
18610 /// `obj` must a valid and not already garbage collected.
18611 /// `methodID` must be valid, static and actually be a method of `obj`, return float and have 1 arguments
18612 ///
18613 pub unsafe fn CallStaticFloatMethod1<A: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A) -> jfloat {
18614 unsafe {
18615 #[cfg(feature = "asserts")]
18616 {
18617 self.check_not_critical("CallStaticFloatMethod");
18618 self.check_no_exception("CallStaticFloatMethod");
18619 self.check_return_type_static("CallStaticFloatMethod", obj, methodID, "float");
18620 self.check_parameter_types_static("CallStaticFloatMethod", obj, methodID, arg1, 0, 1);
18621 }
18622 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jfloat>(135)(self.vtable, obj, methodID, arg1)
18623 }
18624 }
18625
18626 ///
18627 /// Calls a static java method that has 2 arguments and returns double
18628 ///
18629 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18630 ///
18631 ///
18632 /// # Arguments
18633 /// * `obj` - which object the method should be called on
18634 /// * must be valid
18635 /// * must not be null
18636 /// * must not be already garbage collected
18637 ///
18638 /// * `methodID` - method id of the method
18639 /// * must not be null
18640 /// * must be valid
18641 /// * must be a static
18642 /// * must actually be a method of `obj`
18643 /// * must refer to a method with 2 arguments
18644 ///
18645 /// # Returns
18646 /// Whatever the method returned or 0 if it threw
18647 ///
18648 /// # Throws Java Exception
18649 /// * Whatever the method threw
18650 ///
18651 ///
18652 /// # Panics
18653 /// if asserts feature is enabled and UB was detected
18654 ///
18655 /// # Safety
18656 ///
18657 /// Current thread must not be detached from JNI.
18658 ///
18659 /// Current thread must not be currently throwing an exception.
18660 ///
18661 /// Current thread does not hold a critical reference.
18662 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18663 ///
18664 /// `obj` must a valid and not already garbage collected.
18665 /// `methodID` must be valid, static and actually be a method of `obj`, return float and have 2 arguments
18666 ///
18667 pub unsafe fn CallStaticFloatMethod2<A: JType, B: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jfloat {
18668 unsafe {
18669 #[cfg(feature = "asserts")]
18670 {
18671 self.check_not_critical("CallStaticFloatMethod");
18672 self.check_no_exception("CallStaticFloatMethod");
18673 self.check_return_type_static("CallStaticFloatMethod", obj, methodID, "float");
18674 self.check_parameter_types_static("CallStaticFloatMethod", obj, methodID, arg1, 0, 2);
18675 self.check_parameter_types_static("CallStaticFloatMethod", obj, methodID, arg2, 1, 2);
18676 }
18677 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jfloat>(135)(self.vtable, obj, methodID, arg1, arg2)
18678 }
18679 }
18680
18681 ///
18682 /// Calls a static java method that has 3 arguments and returns double
18683 ///
18684 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18685 ///
18686 ///
18687 /// # Arguments
18688 /// * `obj` - which object the method should be called on
18689 /// * must be valid
18690 /// * must not be null
18691 /// * must not be already garbage collected
18692 ///
18693 /// * `methodID` - method id of the method
18694 /// * must not be null
18695 /// * must be valid
18696 /// * must be a static
18697 /// * must actually be a method of `obj`
18698 /// * must refer to a method with 3 arguments
18699 ///
18700 /// # Returns
18701 /// Whatever the method returned or 0 if it threw
18702 ///
18703 /// # Throws Java Exception
18704 /// * Whatever the method threw
18705 ///
18706 ///
18707 /// # Panics
18708 /// if asserts feature is enabled and UB was detected
18709 ///
18710 /// # Safety
18711 ///
18712 /// Current thread must not be detached from JNI.
18713 ///
18714 /// Current thread must not be currently throwing an exception.
18715 ///
18716 /// Current thread does not hold a critical reference.
18717 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18718 ///
18719 /// `obj` must a valid and not already garbage collected.
18720 /// `methodID` must be valid, static and actually be a method of `obj`, return float and have 3 arguments
18721 ///
18722 pub unsafe fn CallStaticFloatMethod3<A: JType, B: JType, C: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jfloat {
18723 unsafe {
18724 #[cfg(feature = "asserts")]
18725 {
18726 self.check_not_critical("CallStaticFloatMethod");
18727 self.check_no_exception("CallStaticFloatMethod");
18728 self.check_return_type_static("CallStaticFloatMethod", obj, methodID, "float");
18729 self.check_parameter_types_static("CallStaticFloatMethod", obj, methodID, arg1, 0, 3);
18730 self.check_parameter_types_static("CallStaticFloatMethod", obj, methodID, arg2, 1, 3);
18731 self.check_parameter_types_static("CallStaticFloatMethod", obj, methodID, arg3, 2, 3);
18732 }
18733 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jfloat>(135)(self.vtable, obj, methodID, arg1, arg2, arg3)
18734 }
18735 }
18736
18737 ///
18738 /// Calls a static java method that returns a double
18739 ///
18740 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18741 ///
18742 ///
18743 /// # Arguments
18744 /// * `obj` - which object the method should be called on
18745 /// * must be valid
18746 /// * must not be null
18747 /// * must not be already garbage collected
18748 ///
18749 /// * `methodID` - method id of the method
18750 /// * must not be null
18751 /// * must be valid
18752 /// * must not be a static
18753 /// * must actually be a method of `obj`
18754 ///
18755 /// * `args` - argument pointer
18756 /// * can be null if the method has no arguments
18757 /// * must not be null otherwise and point to the exact number of arguments the method expects
18758 ///
18759 /// # Returns
18760 /// Whatever the method returned or 0 if it threw
18761 ///
18762 /// # Throws Java Exception
18763 /// * Whatever the method threw
18764 ///
18765 ///
18766 /// # Panics
18767 /// if asserts feature is enabled and UB was detected
18768 ///
18769 /// # Safety
18770 ///
18771 /// Current thread must not be detached from JNI.
18772 ///
18773 /// Current thread must not be currently throwing an exception.
18774 ///
18775 /// Current thread does not hold a critical reference.
18776 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18777 ///
18778 /// `obj` must a valid and not already garbage collected.
18779 /// `methodID` must be valid, static and actually be a method of `obj` class and return a double
18780 /// `args` must have sufficient length to contain the amount of parameter required by the java method.
18781 /// `args` union must contain types that match the java methods parameters.
18782 /// (i.e. do not use a float instead of an object as parameter, beware of java boxed types)
18783 ///
18784 pub unsafe fn CallStaticDoubleMethodA(&self, obj: jclass, methodID: jmethodID, args: *const jtype) -> jdouble {
18785 unsafe {
18786 #[cfg(feature = "asserts")]
18787 {
18788 self.check_not_critical("CallStaticDoubleMethodA");
18789 self.check_no_exception("CallStaticDoubleMethodA");
18790 self.check_return_type_static("CallStaticDoubleMethodA", obj, methodID, "double");
18791 }
18792 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jdouble>(140)(self.vtable, obj, methodID, args)
18793 }
18794 }
18795
18796 ///
18797 /// Calls a static java method that has 0 arguments and returns double
18798 ///
18799 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18800 ///
18801 ///
18802 /// # Arguments
18803 /// * `obj` - which object the method should be called on
18804 /// * must be valid
18805 /// * must not be null
18806 /// * must not be already garbage collected
18807 ///
18808 /// * `methodID` - method id of the method
18809 /// * must not be null
18810 /// * must be valid
18811 /// * must be a static
18812 /// * must actually be a method of `obj`
18813 /// * must refer to a method with 0 arguments
18814 ///
18815 /// # Returns
18816 /// Whatever the method returned or 0 if it threw
18817 ///
18818 /// # Throws Java Exception
18819 /// * Whatever the method threw
18820 ///
18821 ///
18822 /// # Panics
18823 /// if asserts feature is enabled and UB was detected
18824 ///
18825 /// # Safety
18826 ///
18827 /// Current thread must not be detached from JNI.
18828 ///
18829 /// Current thread must not be currently throwing an exception.
18830 ///
18831 /// Current thread does not hold a critical reference.
18832 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18833 ///
18834 /// `obj` must a valid and not already garbage collected.
18835 /// `methodID` must be valid, static and actually be a method of `obj`, return double and have 0 arguments
18836 ///
18837 pub unsafe fn CallStaticDoubleMethod0(&self, obj: jclass, methodID: jmethodID) -> jdouble {
18838 unsafe {
18839 #[cfg(feature = "asserts")]
18840 {
18841 self.check_not_critical("CallStaticDoubleMethod");
18842 self.check_no_exception("CallStaticDoubleMethod");
18843 self.check_return_type_static("CallStaticDoubleMethod", obj, methodID, "double");
18844 }
18845 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID) -> jdouble>(138)(self.vtable, obj, methodID)
18846 }
18847 }
18848
18849 ///
18850 /// Calls a static java method that has 1 arguments and returns double
18851 ///
18852 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18853 ///
18854 ///
18855 /// # Arguments
18856 /// * `obj` - which object the method should be called on
18857 /// * must be valid
18858 /// * must not be null
18859 /// * must not be already garbage collected
18860 ///
18861 /// * `methodID` - method id of the method
18862 /// * must not be null
18863 /// * must be valid
18864 /// * must be a static
18865 /// * must actually be a method of `obj`
18866 /// * must refer to a method with 1 arguments
18867 ///
18868 /// # Returns
18869 /// Whatever the method returned or 0 if it threw
18870 ///
18871 /// # Throws Java Exception
18872 /// * Whatever the method threw
18873 ///
18874 ///
18875 /// # Panics
18876 /// if asserts feature is enabled and UB was detected
18877 ///
18878 /// # Safety
18879 ///
18880 /// Current thread must not be detached from JNI.
18881 ///
18882 /// Current thread must not be currently throwing an exception.
18883 ///
18884 /// Current thread does not hold a critical reference.
18885 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18886 ///
18887 /// `obj` must a valid and not already garbage collected.
18888 /// `methodID` must be valid, static and actually be a method of `obj`, return double and have 1 arguments
18889 ///
18890 pub unsafe fn CallStaticDoubleMethod1<A: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A) -> jdouble {
18891 unsafe {
18892 #[cfg(feature = "asserts")]
18893 {
18894 self.check_not_critical("CallStaticDoubleMethod");
18895 self.check_no_exception("CallStaticDoubleMethod");
18896 self.check_return_type_static("CallStaticDoubleMethod", obj, methodID, "double");
18897 self.check_parameter_types_static("CallStaticDoubleMethod", obj, methodID, arg1, 0, 1);
18898 }
18899 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jdouble>(138)(self.vtable, obj, methodID, arg1)
18900 }
18901 }
18902
18903 ///
18904 /// Calls a static java method that has 2 arguments and returns double
18905 ///
18906 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18907 ///
18908 ///
18909 /// # Arguments
18910 /// * `obj` - which object the method should be called on
18911 /// * must be valid
18912 /// * must not be null
18913 /// * must not be already garbage collected
18914 ///
18915 /// * `methodID` - method id of the method
18916 /// * must not be null
18917 /// * must be valid
18918 /// * must be a static
18919 /// * must actually be a method of `obj`
18920 /// * must refer to a method with 2 arguments
18921 ///
18922 /// # Returns
18923 /// Whatever the method returned or 0 if it threw
18924 ///
18925 /// # Throws Java Exception
18926 /// * Whatever the method threw
18927 ///
18928 ///
18929 /// # Panics
18930 /// if asserts feature is enabled and UB was detected
18931 ///
18932 /// # Safety
18933 ///
18934 /// Current thread must not be detached from JNI.
18935 ///
18936 /// Current thread must not be currently throwing an exception.
18937 ///
18938 /// Current thread does not hold a critical reference.
18939 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18940 ///
18941 /// `obj` must a valid and not already garbage collected.
18942 /// `methodID` must be valid, static and actually be a method of `obj`, return double and have 2 arguments
18943 ///
18944 pub unsafe fn CallStaticDoubleMethod2<A: JType, B: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B) -> jdouble {
18945 unsafe {
18946 #[cfg(feature = "asserts")]
18947 {
18948 self.check_not_critical("CallStaticDoubleMethod");
18949 self.check_no_exception("CallStaticDoubleMethod");
18950 self.check_return_type_static("CallStaticDoubleMethod", obj, methodID, "double");
18951 self.check_parameter_types_static("CallStaticDoubleMethod", obj, methodID, arg1, 0, 2);
18952 self.check_parameter_types_static("CallStaticDoubleMethod", obj, methodID, arg2, 1, 2);
18953 }
18954 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jdouble>(138)(self.vtable, obj, methodID, arg1, arg2)
18955 }
18956 }
18957
18958 ///
18959 /// Calls a static java method that has 3 arguments and returns double
18960 ///
18961 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#CallStatic_type_Method_routines>
18962 ///
18963 ///
18964 /// # Arguments
18965 /// * `obj` - which object the method should be called on
18966 /// * must be valid
18967 /// * must not be null
18968 /// * must not be already garbage collected
18969 ///
18970 /// * `methodID` - method id of the method
18971 /// * must not be null
18972 /// * must be valid
18973 /// * must be a static
18974 /// * must actually be a method of `obj`
18975 /// * must refer to a method with 3 arguments
18976 ///
18977 /// # Returns
18978 /// Whatever the method returned or 0 if it threw
18979 ///
18980 /// # Throws Java Exception
18981 /// * Whatever the method threw
18982 ///
18983 ///
18984 /// # Panics
18985 /// if asserts feature is enabled and UB was detected
18986 ///
18987 /// # Safety
18988 ///
18989 /// Current thread must not be detached from JNI.
18990 ///
18991 /// Current thread must not be currently throwing an exception.
18992 ///
18993 /// Current thread does not hold a critical reference.
18994 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
18995 ///
18996 /// `obj` must a valid and not already garbage collected.
18997 /// `methodID` must be valid, static and actually be a method of `obj`, return double and have 3 arguments
18998 ///
18999 pub unsafe fn CallStaticDoubleMethod3<A: JType, B: JType, C: JType>(&self, obj: jclass, methodID: jmethodID, arg1: A, arg2: B, arg3: C) -> jdouble {
19000 unsafe {
19001 #[cfg(feature = "asserts")]
19002 {
19003 self.check_not_critical("CallStaticDoubleMethod");
19004 self.check_no_exception("CallStaticDoubleMethod");
19005 self.check_return_type_static("CallStaticDoubleMethod", obj, methodID, "double");
19006 self.check_parameter_types_static("CallStaticDoubleMethod", obj, methodID, arg1, 0, 3);
19007 self.check_parameter_types_static("CallStaticDoubleMethod", obj, methodID, arg2, 1, 3);
19008 self.check_parameter_types_static("CallStaticDoubleMethod", obj, methodID, arg3, 2, 3);
19009 }
19010 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID, ...) -> jdouble>(138)(self.vtable, obj, methodID, arg1, arg2, arg3)
19011 }
19012 }
19013
19014 ///
19015 /// Create a new String form a jchar array.
19016 ///
19017 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewString>
19018 ///
19019 ///
19020 /// # Arguments
19021 /// * `unicodeChars` - pointer to the jchar array
19022 /// * must not be null
19023 /// * `len` - amount of elements in the jchar array
19024 ///
19025 /// # Returns
19026 /// A local reference to the newly created String or null on error
19027 ///
19028 /// # Throws Java Exception
19029 /// * `OutOfMemoryError` - if the jvm ran out of memory allocating the String
19030 ///
19031 ///
19032 /// # Panics
19033 /// if asserts feature is enabled and UB was detected
19034 ///
19035 /// # Safety
19036 ///
19037 /// Current thread must not be detached from JNI.
19038 ///
19039 /// Current thread must not be currently throwing an exception.
19040 ///
19041 /// Current thread does not hold a critical reference.
19042 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19043 ///
19044 /// `unicodeChars` must not be 0.
19045 /// `unicodeChars` must be equal or larger than `len` suggests.
19046 ///
19047 #[must_use]
19048 pub unsafe fn NewString(&self, unicodeChars: *const jchar, len: jsize) -> jstring {
19049 unsafe {
19050 #[cfg(feature = "asserts")]
19051 {
19052 self.check_not_critical("NewString");
19053 self.check_no_exception("NewString");
19054 assert!(!unicodeChars.is_null(), "NewString string must not be null");
19055 assert!(len >= 0, "NewString len must not be negative");
19056 }
19057 self.jni::<extern "system" fn(JNIEnvVTable, *const jchar, jsize) -> jstring>(163)(self.vtable, unicodeChars, len)
19058 }
19059 }
19060
19061 /// Convenience function to create a `jstring` from any rust string.
19062 ///
19063 /// This function will, after performing some transformations, call `NewString`.
19064 /// This function is quite slow compared to all other alternatives but unlike for example `NewStringUTF`,
19065 /// it works with strings that contain 0 characters or supplementary characters.
19066 ///
19067 /// This function will always be slower than `NewStringUTF`.
19068 ///
19069 /// # Returns
19070 /// return value of `NewString`
19071 ///
19072 /// # Safety
19073 /// Same as the `NewString` fn
19074 ///
19075 /// # Panics
19076 /// If the string is too long to be represented in Java:
19077 /// * This always the case if the `string.chars().count()` is more than `i32::MAX`.
19078 /// * This might be the case if `string.chars().count()` is between `i32::MAX` and `i32::MAX / 2`
19079 /// if the string contains enough characters that would require 32 bit encoding in utf-16.
19080 /// * This is never the case if `string.chars().count()` is less than `i32::MAX / 2`.
19081 ///
19082 /// Sidenote: This function does not call `string.chars().count()`.
19083 ///
19084 /// # Example
19085 /// ```rust
19086 /// use jni_simple::{jstring, JNIEnv};
19087 ///
19088 /// fn example(env: JNIEnv) {
19089 /// unsafe {
19090 /// let my_string = "𝕊"; //U+1D54A MATHEMATICAL DOUBLE-STRUCK CAPITAL S
19091 /// let java_string: jstring = env.NewString_from_str(my_string);
19092 /// let and_back_again: String = env.GetStringChars_as_string(java_string).unwrap();
19093 /// assert_eq!(my_string, and_back_again.as_str());
19094 /// }
19095 /// }
19096 /// ```
19097 ///
19098 pub unsafe fn NewString_from_str(&self, string: impl AsRef<str>) -> jstring {
19099 let mut utf16 = Vec::new();
19100 let str = string.as_ref();
19101
19102 //This over allocates up to 4 times capacity depending on how many 2,3,4 byte utf-8 charactes the string contains.
19103 //We cap the allocation at 64k (128k bytes) just in case.
19104 utf16.reserve(str.len().min(0x1_00_00));
19105
19106 for utf in string.as_ref().encode_utf16() {
19107 utf16.push(utf);
19108 }
19109
19110 let len = utf16.len();
19111 let Ok(len) = jsize::try_from(len) else {
19112 panic!(
19113 "string was too long to represent in java. It requires {len} utf-16 characters to represent, but java only supports up to {} characters in a String.",
19114 jsize::MAX
19115 );
19116 };
19117
19118 unsafe { self.NewString(utf16.as_ptr(), len) }
19119 }
19120
19121 ///
19122 /// Returns the string length in jchar's. This is neither the amount of bytes in utf-8 encoding nor the amount of characters.
19123 /// 3 and 4 byte utf-8 characters take 2 jchars to encode. This is equivalent to calling `String.length()` in java.
19124 ///
19125 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStringLength>
19126 ///
19127 /// # Arguments
19128 /// * `string`
19129 /// * must not be null
19130 /// * must refer to a string
19131 /// * must not be already garbage collected
19132 ///
19133 /// # Returns
19134 /// the amount of jchar's in the String
19135 ///
19136 ///
19137 /// # Panics
19138 /// if asserts feature is enabled and UB was detected
19139 ///
19140 /// # Safety
19141 ///
19142 /// Current thread must not be detached from JNI.
19143 ///
19144 /// Current thread must not be currently throwing an exception.
19145 ///
19146 /// Current thread does not hold a critical reference.
19147 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19148 ///
19149 /// `string` must be a valid reference that is not yet garbage collected and refer to a String.
19150 ///
19151 pub unsafe fn GetStringLength(&self, string: jstring) -> jsize {
19152 unsafe {
19153 #[cfg(feature = "asserts")]
19154 {
19155 self.check_not_critical("GetStringLength");
19156 self.check_no_exception("GetStringLength");
19157 assert!(!string.is_null(), "GetStringLength string must not be null");
19158 self.check_if_arg_is_string("GetStringLength", string);
19159 }
19160 self.jni::<extern "system" fn(JNIEnvVTable, jstring) -> jsize>(164)(self.vtable, string)
19161 }
19162 }
19163
19164 ///
19165 /// Returns the string's jchar arrays representation.
19166 ///
19167 /// Note: This fn will almost always to return a copy of the data for newer JVM's.
19168 ///
19169 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStringChars>
19170 ///
19171 /// # Arguments
19172 /// * `string`
19173 /// * must not be null
19174 /// * must refer to a string
19175 /// * must not be already garbage collected
19176 /// * `isCopy` - optional pointer to a boolean flag for the vm to indicate if it copied the data or not.
19177 /// * may be null
19178 ///
19179 /// # Returns
19180 /// a pointer to index 0 of a jchar array.
19181 ///
19182 ///
19183 /// # Panics
19184 /// if asserts feature is enabled and UB was detected
19185 ///
19186 /// # Safety
19187 ///
19188 /// Current thread must not be detached from JNI.
19189 ///
19190 /// Current thread must not be currently throwing an exception.
19191 ///
19192 /// Current thread does not hold a critical reference.
19193 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19194 ///
19195 /// `string` must be a valid reference that is not yet garbage collected and refer to a String.
19196 /// `isCopy` must be null or valid.
19197 ///
19198 pub unsafe fn GetStringChars(&self, string: jstring, isCopy: impl JBooleanMutPtr) -> *const jchar {
19199 unsafe {
19200 #[cfg(feature = "asserts")]
19201 {
19202 self.check_not_critical("GetStringChars");
19203 self.check_no_exception("GetStringChars");
19204 assert!(!string.is_null(), "GetStringChars string must not be null");
19205 self.check_if_arg_is_string("GetStringChars", string);
19206 }
19207 isCopy.use_jboolean_mut(|isCopy| self.jni::<extern "system" fn(JNIEnvVTable, jstring, *mut jboolean) -> *const jchar>(165)(self.vtable, string, isCopy))
19208 }
19209 }
19210
19211 /// Convenience method that calls `GetStringChars` & `GetStringLength`, copies the result
19212 /// into a rust String and then calls `ReleaseStringChars`.
19213 ///
19214 /// This function calls `ReleaseStringChars` in all error cases where it has to be called!
19215 ///
19216 /// # Returns
19217 /// On failure this method return None.
19218 /// There are 3 different causes for returning None:
19219 /// 1. `GetStringLength` returns a negative number.
19220 /// * This is unlikely unless something has gone horribly wrong.
19221 /// 2. `GetStringChars` fails, in this case more information should be gathered from `ExceptionCheck`.
19222 /// 3. The characters returned by the JVM are not valid utf-16. In this case `ExceptionCheck` should yield None.
19223 ///
19224 /// # Panics
19225 /// if asserts feature is enabled and UB was detected
19226 ///
19227 /// # Safety
19228 /// Current thread must not be detached from JNI.
19229 ///
19230 /// Current thread must not be currently throwing an exception.
19231 ///
19232 /// Current thread does not hold a critical reference.
19233 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19234 ///
19235 /// `string` must not be null, must refer to a string and not already be garbage collected.
19236 ///
19237 pub unsafe fn GetStringChars_as_string(&self, string: jstring) -> Option<String> {
19238 unsafe {
19239 #[cfg(feature = "asserts")]
19240 {
19241 self.check_not_critical("GetStringChars_as_string");
19242 self.check_no_exception("GetStringChars_as_string");
19243 assert!(!string.is_null(), "GetStringChars_as_string string must not be null");
19244 self.check_if_arg_is_string("GetStringChars_as_string", string);
19245 }
19246
19247 let Ok(len) = usize::try_from(self.GetStringLength(string)) else {
19248 //Unlikely
19249 return None;
19250 };
19251
19252 if len == 0 {
19253 //Empty string, we are done.
19254 return Some(String::new());
19255 }
19256
19257 let str = self.GetStringChars(string, ());
19258 if str.is_null() {
19259 return None;
19260 }
19261
19262 let parsed = String::from_utf16(core::slice::from_raw_parts(str, len));
19263 self.ReleaseStringChars(string, str);
19264 parsed.ok()
19265 }
19266 }
19267
19268 ///
19269 /// Frees a char array returned by `GetStringChars`.
19270 ///
19271 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ReleaseStringChars>
19272 ///
19273 /// # Arguments
19274 /// * `string`
19275 /// * must not be null
19276 /// * must refer to a string
19277 /// * must not be already garbage collected
19278 /// * `chars` - the pointer returned by `GetStringChars`
19279 /// * must not be null
19280 ///
19281 ///
19282 /// # Panics
19283 /// if asserts feature is enabled and UB was detected
19284 ///
19285 /// # Safety
19286 ///
19287 /// Current thread must not be detached from JNI.
19288 ///
19289 /// Current thread does not hold a critical reference.
19290 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19291 ///
19292 /// `string` must be a valid reference that is not yet garbage collected and refer to a String.
19293 /// `chars` must not be null.
19294 /// `chars` must be the result of a call to `GetStringChars` of the String `string`
19295 ///
19296 pub unsafe fn ReleaseStringChars(&self, string: jstring, chars: *const jchar) {
19297 unsafe {
19298 #[cfg(feature = "asserts")]
19299 {
19300 self.check_not_critical("ReleaseStringChars");
19301 assert!(!string.is_null(), "ReleaseStringChars string must not be null");
19302 assert!(!chars.is_null(), "ReleaseStringChars chars must not be null");
19303 self.check_if_arg_is_string("ReleaseStringChars", string);
19304 }
19305 self.jni::<extern "system" fn(JNIEnvVTable, jstring, *const jchar)>(166)(self.vtable, string, chars);
19306 }
19307 }
19308
19309 ///
19310 /// Create a new String form a utf-8 zero terminated c string.
19311 ///
19312 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewString>
19313 ///
19314 /// # IMPORTANT
19315 /// Java uses a modified utf-8 encoding for strings. If your rust string contains any
19316 /// supplementary characters then the resulting java string will not contain the same characters.
19317 /// If this is a concern for you use the much slower method `NewString_from_str` which
19318 /// will properly handle all characters. Using this method despite it containing
19319 /// supplementary does NOT cause UB, it just creates a java string that contains 'random'
19320 /// characters.
19321 ///
19322 /// # Arguments
19323 /// * `bytes` - pointer to the c like zero terminated utf-8 string
19324 /// * must not be null
19325 ///
19326 /// # Returns
19327 /// A local reference to the newly created String or null on error
19328 ///
19329 /// # Throws Java Exception
19330 /// * `OutOfMemoryError` - if the jvm ran out of memory allocating the String
19331 ///
19332 ///
19333 /// # Panics
19334 /// if asserts feature is enabled and UB was detected
19335 ///
19336 /// # Safety
19337 ///
19338 /// Current thread must not be detached from JNI.
19339 ///
19340 /// Current thread must not be currently throwing an exception.
19341 ///
19342 /// Current thread does not hold a critical reference.
19343 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19344 ///
19345 /// `bytes` must not be null.
19346 /// `bytes` must be zero terminated.
19347 ///
19348 pub unsafe fn NewStringUTF(&self, bytes: impl UseCString) -> jstring {
19349 unsafe {
19350 bytes.use_as_const_c_char(|bytes| {
19351 #[cfg(feature = "asserts")]
19352 {
19353 self.check_not_critical("NewStringUTF");
19354 self.check_no_exception("NewStringUTF");
19355 assert!(!bytes.is_null(), "NewStringUTF string must not be null");
19356 }
19357 self.jni::<extern "system" fn(JNIEnvVTable, *const c_char) -> jstring>(167)(self.vtable, bytes)
19358 })
19359 }
19360 }
19361
19362 ///
19363 /// Returns the length of a String in bytes if it were to be used with `GetStringUTFChars`.
19364 ///
19365 /// Note: For Java 24 or newer this function is deprecated. use `GetStringUTFLengthAsLong` instead.
19366 ///
19367 /// Note: Usage of this function should be carefully evaluated. For most jvms (especially for JVMS older than Java 17)
19368 /// it is faster to just call `GetStringUTFChars` and use a function equivalent to the c function `strlen()` on its return value.
19369 /// Some newer jvm's may, depending on how the vm was started, know this value for most strings,
19370 /// and therefore it is faster to call this fn than to do
19371 /// the approach above if you do not also need the `UTFChars` themselves.
19372 ///
19373 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStringUTFLength>
19374 ///
19375 ///
19376 /// # Arguments
19377 /// * `string`
19378 /// * must not be null
19379 /// * must refer to a string
19380 /// * must not be already garbage collected
19381 ///
19382 /// # Returns
19383 /// The amount of bytes the array returned by `GetStringUTFChars` would have for this string.
19384 ///
19385 ///
19386 /// # Panics
19387 /// if asserts feature is enabled and UB was detected
19388 ///
19389 /// # Safety
19390 ///
19391 /// Current thread must not be detached from JNI.
19392 ///
19393 /// Current thread must not be currently throwing an exception.
19394 ///
19395 /// Current thread does not hold a critical reference.
19396 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19397 ///
19398 /// `string` must not be null, must refer to a string and not already be garbage collected.
19399 ///
19400 pub unsafe fn GetStringUTFLength(&self, string: jstring) -> jsize {
19401 unsafe {
19402 #[cfg(feature = "asserts")]
19403 {
19404 self.check_not_critical("GetStringUTFLength");
19405 self.check_no_exception("GetStringUTFLength");
19406 assert!(!string.is_null(), "GetStringUTFLength string must not be null");
19407 self.check_if_arg_is_string("GetStringUTFLength", string);
19408 }
19409
19410 self.jni::<extern "system" fn(JNIEnvVTable, jstring) -> jsize>(168)(self.vtable, string)
19411 }
19412 }
19413
19414 ///
19415 /// Returns the length of a String in bytes if it were to be used with `GetStringUTFChars`.
19416 /// Beware that this function is only available on Java 24 or newer!
19417 ///
19418 /// <https://docs.oracle.com/en/java/javase/24/docs/specs/jni/functions.html#getstringutflengthaslong>
19419 ///
19420 ///
19421 /// # Arguments
19422 /// * `string`
19423 /// * must not be null
19424 /// * must refer to a string
19425 /// * must not be already garbage collected
19426 ///
19427 /// # Returns
19428 /// The amount of bytes the array returned by `GetStringUTFChars` would have for this string.
19429 ///
19430 /// # Panics
19431 /// if asserts feature is enabled and UB was detected
19432 ///
19433 /// # Safety
19434 ///
19435 /// Current thread must not be detached from JNI.
19436 ///
19437 /// Current thread must not be currently throwing an exception.
19438 ///
19439 /// Current thread does not hold a critical reference.
19440 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19441 ///
19442 /// `string` must not be null, must refer to a string and not already be garbage collected.
19443 ///
19444 /// The JVM must be a Java 24 VM or newer
19445 ///
19446 pub unsafe fn GetStringUTFLengthAsLong(&self, string: jstring) -> jsize {
19447 unsafe {
19448 #[cfg(feature = "asserts")]
19449 {
19450 self.check_not_critical("GetStringUTFLengthAsLong");
19451 self.check_no_exception("GetStringUTFLengthAsLong");
19452 assert!(!string.is_null(), "GetStringUTFLengthAsLong string must not be null");
19453 self.check_if_arg_is_string("GetStringUTFLengthAsLong", string);
19454 assert!(self.GetVersion() >= JNI_VERSION_24);
19455 }
19456
19457 self.jni::<extern "system" fn(JNIEnvVTable, jstring) -> jsize>(235)(self.vtable, string)
19458 }
19459 }
19460
19461 ///
19462 /// Returns the 0 terminated utf-8 representation of the String.
19463 /// The returned string can be used with the "rust" `CStr` struct from the `std::ffi` module.
19464 ///
19465 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStringUTFChars>
19466 ///
19467 ///
19468 /// # Arguments
19469 /// * `string`
19470 /// * must not be null
19471 /// * must refer to a string
19472 /// * must not be already garbage collected
19473 /// * `isCopy` - optional flag for the jvm to indicate if the string is a copy of the data or not.
19474 /// * can be null
19475 ///
19476 /// # Returns
19477 /// A pointer to the zero terminated utf-8 string or null on error.
19478 ///
19479 /// # Throws Java Exception
19480 /// * `OutOfMemoryError` - if the jvm ran out of memory allocating the utf-8 string
19481 ///
19482 ///
19483 /// # Panics
19484 /// if asserts feature is enabled and UB was detected
19485 ///
19486 /// # Safety
19487 ///
19488 /// Current thread must not be detached from JNI.
19489 ///
19490 /// Current thread must not be currently throwing an exception.
19491 ///
19492 /// Current thread does not hold a critical reference.
19493 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19494 ///
19495 /// `string` must not be null, must refer to a string and not already be garbage collected.
19496 ///
19497 pub unsafe fn GetStringUTFChars(&self, string: jstring, isCopy: impl JBooleanMutPtr) -> *const c_char {
19498 unsafe {
19499 #[cfg(feature = "asserts")]
19500 {
19501 self.check_not_critical("GetStringUTFChars");
19502 assert!(!string.is_null(), "GetStringUTFChars string must not be null");
19503 self.check_if_arg_is_string("GetStringUTFChars", string);
19504 }
19505 isCopy.use_jboolean_mut(|isCopy| self.jni::<extern "system" fn(JNIEnvVTable, jstring, *mut jboolean) -> *const c_char>(169)(self.vtable, string, isCopy))
19506 }
19507 }
19508
19509 /// Convenience method that calls `GetStringUTFChars`, copies the result
19510 /// into a rust String and then calls `ReleaseStringUTFChars`.
19511 ///
19512 /// This function calls `ReleaseStringUTFChars` in all error cases where it has to be called!
19513 ///
19514 /// # IMPORTANT
19515 /// This function parses the bytes using `CStr::from_ptr(...).to_str()`
19516 ///
19517 /// This function may return None or rust strings that contain
19518 /// unexpected characters which are not actually present in the Java String. <br>
19519 /// This happens when the utf-8 and the modified-utf-8 encoding differ.<br>
19520 /// See <https://docs.oracle.com/en/java/javase/23/docs/api/java.base/java/io/DataInput.html#modified-utf-8> <br>
19521 /// This is the case when the string contains one of the following characters:
19522 /// * \0, null character 0 byte.
19523 /// * any supplementary character. (Any character that would require 4 bytes in normal utf-8 encoding)
19524 ///
19525 /// While this may cause an unexpected return value, it will still never cause UB regardless
19526 /// of what characters the java string contains. Only use this function if you have understood this caveat.
19527 ///
19528 /// An alternative, but slower version of this function is called `GetStringChars_as_string` which does not have this problem
19529 /// because instead of using the utf-8 representation of the string it uses the utf-16 representation,
19530 /// but it is much slower than this function with java 17 or newer. If your application is expected to process Strings containing
19531 /// the problematic characters then accepting the performance penalty is probably worth it.
19532 ///
19533 /// # Returns
19534 /// On failure this method return None.
19535 /// There are 2 different causes for returning None:
19536 /// 1. `GetStringUTFChars` fails, in this case more information should be gathered from `ExceptionCheck`.
19537 /// 2. The String returned by the JVM is not valid utf-8. In this case `ExceptionCheck` should yield None.
19538 /// * see the IMPORTANT section for when this happens.
19539 ///
19540 /// # Panics
19541 /// if asserts feature is enabled and UB was detected
19542 ///
19543 /// # Safety
19544 /// Current thread must not be detached from JNI.
19545 ///
19546 /// Current thread must not be currently throwing an exception.
19547 ///
19548 /// Current thread does not hold a critical reference.
19549 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19550 ///
19551 /// `string` must not be null, must refer to a string and not already be garbage collected.
19552 ///
19553 pub unsafe fn GetStringUTFChars_as_string(&self, string: jstring) -> Option<String> {
19554 unsafe {
19555 #[cfg(feature = "asserts")]
19556 {
19557 self.check_not_critical("GetStringUTFChars_as_string");
19558 self.check_no_exception("GetStringUTFChars_as_string");
19559 assert!(!string.is_null(), "GetStringUTFChars_as_string string must not be null");
19560 self.check_if_arg_is_string("GetStringUTFChars_as_string", string);
19561 }
19562
19563 let str = self.GetStringUTFChars(string, ());
19564 if str.is_null() {
19565 return None;
19566 }
19567
19568 let parsed = CStr::from_ptr(str).to_str();
19569 if let Ok(parsed) = parsed {
19570 let copy = parsed.to_string();
19571 self.ReleaseStringUTFChars(string, str);
19572 return Some(copy);
19573 }
19574
19575 self.ReleaseStringUTFChars(string, str);
19576 None
19577 }
19578 }
19579
19580 ///
19581 /// Frees the utf-8 string returned by `GetStringUTFChars`.
19582 /// After this method is called the pointer returned by `GetStringUTFChars` becomes invalid
19583 ///
19584 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStringUTFChars>
19585 ///
19586 ///
19587 /// # Arguments
19588 /// * `string` - the string refercence used in `GetStringUTFChars`
19589 /// * must not be null
19590 /// * must refer to a string
19591 /// * must not be already garbage collected
19592 /// * `utf` - the raw utf8 data returned by `GetStringUTFChars`
19593 /// * must not be null
19594 /// * must be the exact return value of `GetStringUTFChars`
19595 ///
19596 ///
19597 /// # Panics
19598 /// if asserts feature is enabled and UB was detected
19599 ///
19600 /// # Safety
19601 ///
19602 /// Current thread must not be detached from JNI.
19603 ///
19604 /// Current thread does not hold a critical reference.
19605 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19606 ///
19607 /// `string` must not be null, must refer to a string and not already be garbage collected.
19608 ///
19609 pub unsafe fn ReleaseStringUTFChars(&self, string: jstring, utf: *const c_char) {
19610 unsafe {
19611 #[cfg(feature = "asserts")]
19612 {
19613 self.check_not_critical("ReleaseStringUTFChars");
19614 assert!(!string.is_null(), "ReleaseStringUTFChars string must not be null");
19615 assert!(!utf.is_null(), "ReleaseStringUTFChars utf must not be null");
19616 self.check_if_arg_is_string("ReleaseStringUTFChars", string);
19617 }
19618
19619 self.jni::<extern "system" fn(JNIEnvVTable, jstring, *const c_char)>(170)(self.vtable, string, utf);
19620 }
19621 }
19622
19623 ///
19624 /// Copies a part of the string into a provided jchar buffer
19625 ///
19626 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStringRegion>
19627 ///
19628 ///
19629 /// # Arguments
19630 /// * `string` - the string reference used in `GetStringUTFChars`
19631 /// * must not be null
19632 /// * must refer to a string
19633 /// * must not be already garbage collected
19634 /// * `start` - the index of the first jchar to copy
19635 /// * `len` - the amount of jchar's to copy
19636 /// * if len is 0 then the function will not fail unless `start` is larger than the length of the string.
19637 /// * `buffer` - the target buffer where the jchar's should be copied to
19638 /// * must not be null
19639 ///
19640 /// # Throws Java Exception
19641 /// * `StringIndexOutOfBoundsException` - if start or start + len is out of bounds
19642 /// * The state of the output buffer is undefined if this exception is thrown.
19643 ///
19644 ///
19645 /// # Panics
19646 /// if asserts feature is enabled and UB was detected
19647 ///
19648 /// # Safety
19649 ///
19650 /// Current thread must not be detached from JNI.
19651 ///
19652 /// Current thread must not be currently throwing an exception.
19653 ///
19654 /// Current thread does not hold a critical reference.
19655 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19656 ///
19657 /// `string` must not be null, must refer to a string and not already be garbage collected.
19658 /// `buffer` must be valid
19659 /// `buffer` must be aligned to jchar
19660 /// `buffer` must be large enough to hold the requested amount of jchar's
19661 ///
19662 pub unsafe fn GetStringRegion(&self, string: jstring, start: jsize, len: jsize, buffer: *mut jchar) {
19663 unsafe {
19664 #[cfg(feature = "asserts")]
19665 {
19666 self.check_not_critical("GetStringRegion");
19667 self.check_no_exception("GetStringRegion");
19668 assert!(!string.is_null(), "GetStringRegion string must not be null");
19669 assert!(!buffer.is_null(), "GetStringRegion buffer must not be null");
19670 assert!(buffer.is_aligned(), "GetStringRegion buffer is not aligned properly!");
19671 self.check_if_arg_is_string("GetStringRegion", string);
19672 }
19673
19674 self.jni::<extern "system" fn(JNIEnvVTable, jstring, jsize, jsize, *mut jchar)>(220)(self.vtable, string, start, len, buffer);
19675 }
19676 }
19677
19678 ///
19679 /// Copies a part of the string into a provided jchar buffer
19680 ///
19681 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStringRegion>
19682 ///
19683 ///
19684 /// # Arguments
19685 /// * `string` - the string reference used in `GetStringUTFChars`
19686 /// * must not be null
19687 /// * must refer to a string
19688 /// * must not be already garbage collected
19689 /// * `start` - the index of the first jchar to copy
19690 /// * `buffer` - the target buffer where the jchar's should be copied to
19691 ///
19692 /// # Throws Java Exception
19693 /// * `StringIndexOutOfBoundsException` - if start or start + `buffer.len()` is out of bounds
19694 /// * The state of the output buffer is undefined if this exception is thrown.
19695 ///
19696 ///
19697 /// # Panics
19698 /// if asserts feature is enabled and UB was detected
19699 ///
19700 /// # Safety
19701 ///
19702 /// Current thread must not be detached from JNI.
19703 ///
19704 /// Current thread must not be currently throwing an exception.
19705 ///
19706 /// Current thread does not hold a critical reference.
19707 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19708 ///
19709 /// `string` must not be null, must refer to a string and not already be garbage collected.
19710 ///
19711 pub unsafe fn GetStringRegion_into_slice(&self, string: jstring, start: jsize, buffer: &mut [jchar]) {
19712 unsafe {
19713 self.GetStringRegion(string, start, jsize::try_from(buffer.len()).expect("buf.len() > jsize::MAX"), buffer.as_mut_ptr());
19714 }
19715 }
19716
19717 ///
19718 /// Copies a part of the string into a provided `c_char` buffer
19719 /// This fn always appends a '0' byte to the output `c_char` buffer!
19720 ///
19721 /// This fn is not recommended for use. It is prone for out of bounds problems because
19722 /// the size of the buffer cannot be predicted easily because the `len` parameter is the amount of jchar's
19723 /// to copy and each jchar may turn into 1-4 bytes of output.
19724 /// The only "safe" way to call this fn is to ensure buffer is len*4+1 bytes large. +1 for the trailing 0 byte.
19725 ///
19726 /// The speed of this fn is also questionable on newer jvm's (at least since java17)
19727 /// as their internal represetation of String makes perform this operation very expensive.
19728 ///
19729 /// This fn may be usefull on newer jvm's if you need to copy from the start of the string as that should be reasonably efficient,
19730 /// and you can predict the buffer sizes with certaining because you know the requrested characters are only ascii for example.
19731 ///
19732 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetStringUTFRegion>
19733 ///
19734 ///
19735 /// # Arguments
19736 /// * `string` - the string reference used in `GetStringUTFChars`
19737 /// * must not be null
19738 /// * must refer to a string
19739 /// * must not be already garbage collected
19740 /// * `start` - the index of the first jchar to copy
19741 /// * `len` - the amount of java chars to copy. This has no relation to the output buffer size.
19742 /// * `buffer` - the target buffer where the jchar's should be copied to as utf-8
19743 ///
19744 /// # Throws Java Exception
19745 /// * `StringIndexOutOfBoundsException` - if start or start + len is out of bounds
19746 /// * The state of the output buffer is undefined if this exception is thrown.
19747 ///
19748 ///
19749 /// # Panics
19750 /// if asserts feature is enabled and UB was detected
19751 ///
19752 /// # Safety
19753 ///
19754 /// Current thread must not be detached from JNI.
19755 ///
19756 /// Current thread must not be currently throwing an exception.
19757 ///
19758 /// Current thread does not hold a critical reference.
19759 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19760 ///
19761 /// `string` must not be null, must refer to a string and not already be garbage collected.
19762 /// `buffer` must be valid
19763 /// `buffer` must be large enough to hold the requested amount of jchar's
19764 ///
19765 pub unsafe fn GetStringUTFRegion(&self, string: jstring, start: jsize, len: jsize, buffer: *mut c_char) {
19766 unsafe {
19767 #[cfg(feature = "asserts")]
19768 {
19769 self.check_not_critical("GetStringUTFRegion");
19770 self.check_no_exception("GetStringUTFRegion");
19771 assert!(!string.is_null(), "GetStringUTFRegion string must not be null");
19772 self.check_if_arg_is_string("GetStringUTFRegion", string);
19773 }
19774
19775 self.jni::<extern "system" fn(JNIEnvVTable, jstring, jsize, jsize, *mut c_char)>(221)(self.vtable, string, start, len, buffer);
19776 }
19777 }
19778
19779 #[cfg(feature = "asserts")]
19780 #[cfg(feature = "std")]
19781 std::thread_local! {
19782 //The "Critical Section" created by GetStringCritical has a lot of restrictions placed upon it.
19783 //This attempts to track "some" of them on a best effort basis.
19784 static CRITICAL_STRINGS: core::cell::RefCell<std::collections::HashMap<*const jchar, usize>> = core::cell::RefCell::new(std::collections::HashMap::new());
19785 }
19786
19787 ///
19788 /// Obtains a critical pointer into a primitive java String.
19789 /// This pointer must be released by calling `ReleaseStringCritical`.
19790 /// No other JNI functions can be called in the current thread.
19791 /// The only exception being multiple consecutive calls to `GetStringCritical` & `GetPrimitiveArrayCritical` to obtain multiple critical
19792 /// pointers at the same time.
19793 ///
19794 /// This method will return NULL to indicate error.
19795 /// The JVM will most likely throw an Exception, probably an `OOMError`.
19796 /// If you obtain multiple critical pointers, you MUST release all successfully obtained critical pointers
19797 /// before being able to check for the exception.
19798 ///
19799 /// Special care must be taken to avoid blocking the current thread with a dependency on another JVM thread.
19800 /// I.e. Do not read from a pipe that is filled by another JVM thread for example.
19801 ///
19802 /// It is also ill-advised to hold onto critical pointers for long periods of time even if no dependency on another JVM Thread is made.
19803 /// The JVM may decide among other things to suspend garbage collection while a critical pointer is held.
19804 /// So reading from a Socket with a long timeout while holding a critical pointer is unlikely to be a good idea.
19805 /// As it may cause unintended side effects in the rest of the JVM (like running out of memory because the GC doesn't run)
19806 ///
19807 /// Failure to release critical pointers before returning execution back to Java Code should be treated as UB
19808 /// even tho the JVM spec fails to mention this detail.
19809 ///
19810 /// Releasing critical pointers in another thread other than the thread that created it should be treated as UB
19811 /// even tho the JVM spec only mentions this detail indirectly.
19812 ///
19813 /// I recommend against using this method for almost every use case.
19814 /// Due to newer JVM's using UTF-8 internal representation this method is likely slower than
19815 /// just copying out the UTF-8 string directly for newer JVMs.
19816 ///
19817 /// # Returns
19818 /// A pointer to the jchar array of the string.
19819 ///
19820 ///
19821 /// # Panics
19822 /// if asserts feature is enabled and UB was detected
19823 ///
19824 /// # Safety
19825 /// Writing to the returned `*const jchar` in any way is UB.
19826 /// `string` must be non-null, valid, actually refer to a string and not yet be garbage collected.
19827 ///
19828 pub unsafe fn GetStringCritical(&self, string: jstring, isCopy: impl JBooleanMutPtr) -> *const jchar {
19829 unsafe {
19830 #[cfg(feature = "asserts")]
19831 {
19832 assert!(!string.is_null(), "GetStringCritical string must not be null");
19833 #[cfg(feature = "std")]
19834 {
19835 Self::CRITICAL_POINTERS.with(|set| {
19836 if set.borrow().is_empty() {
19837 Self::CRITICAL_STRINGS.with(|strings| {
19838 if strings.borrow().is_empty() {
19839 //We can only do this check if we have not yet obtained a unreleased critical on the current thread.
19840 //For subsequent calls we cannot do this check.
19841 self.check_no_exception("GetStringCritical");
19842 self.check_if_arg_is_string("GetStringCritical", string);
19843 }
19844 });
19845 }
19846 });
19847 }
19848 }
19849
19850 let crit = isCopy.use_jboolean_mut(|isCopy| self.jni::<extern "system" fn(JNIEnvVTable, jstring, *mut jboolean) -> *const jchar>(224)(self.vtable, string, isCopy));
19851
19852 #[cfg(all(feature = "asserts", feature = "std"))]
19853 {
19854 if !crit.is_null() {
19855 Self::CRITICAL_STRINGS.with(|set| {
19856 let mut rm = set.borrow_mut();
19857 let n = rm.remove(&crit).unwrap_or(0) + 1;
19858 rm.insert(crit, n);
19859 });
19860 }
19861 }
19862
19863 crit
19864 }
19865 }
19866
19867 ///
19868 /// This fn ends a critical string section.
19869 /// After the call ends the underlying jchar array may be freed, moved by the jvm or garbage collected.
19870 ///
19871 ///
19872 /// # Panics
19873 /// if asserts feature is enabled and UB was detected
19874 ///
19875 /// # Safety
19876 /// `string` must be non-null and valid
19877 /// `cstring` must be non-null and the result of a `GetStringCritical` call
19878 ///
19879 pub unsafe fn ReleaseStringCritical(&self, string: jstring, cstring: *const jchar) {
19880 unsafe {
19881 #[cfg(feature = "asserts")]
19882 {
19883 assert!(!string.is_null(), "ReleaseStringCritical string must not be null");
19884 assert!(!cstring.is_null(), "ReleaseStringCritical cstring must not be null");
19885 #[cfg(feature = "std")]
19886 {
19887 Self::CRITICAL_STRINGS.with(|set| {
19888 let mut rm = set.borrow_mut();
19889 let mut n = rm.remove(&cstring).expect("ReleaseStringCritical cstring is not valid");
19890 if n == 0 {
19891 unreachable!();
19892 }
19893
19894 n -= 1;
19895
19896 if n >= 1 {
19897 rm.insert(cstring, n);
19898 }
19899 });
19900 }
19901 }
19902
19903 self.jni::<extern "system" fn(JNIEnvVTable, jstring, *const jchar)>(225)(self.vtable, string, cstring);
19904 }
19905 }
19906
19907 ///
19908 /// Returns the size of an array
19909 ///
19910 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetArrayLength>
19911 ///
19912 ///
19913 /// # Arguments
19914 /// * `array`
19915 /// * must not be null
19916 /// * must refer to an array of any primitve type or Object[]
19917 /// * must not be already garbage collected
19918 /// # Returns
19919 /// the size of the array in elements
19920 ///
19921 ///
19922 /// # Panics
19923 /// if asserts feature is enabled and UB was detected
19924 ///
19925 /// # Safety
19926 ///
19927 /// Current thread must not be detached from JNI.
19928 ///
19929 /// Current thread must not be currently throwing an exception.
19930 ///
19931 /// Current thread does not hold a critical reference.
19932 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19933 ///
19934 /// `array` must not be null, must refer to a array and not already be garbage collected.
19935 ///
19936 pub unsafe fn GetArrayLength(&self, array: jarray) -> jsize {
19937 unsafe {
19938 #[cfg(feature = "asserts")]
19939 {
19940 self.check_not_critical("GetArrayLength");
19941 self.check_no_exception("GetArrayLength");
19942 assert!(!array.is_null(), "GetArrayLength array must not be null");
19943 self.check_is_array(array, "GetArrayLength");
19944 }
19945
19946 self.jni::<extern "system" fn(JNIEnvVTable, jarray) -> jsize>(171)(self.vtable, array)
19947 }
19948 }
19949
19950 ///
19951 /// Creates a new array of Objects
19952 ///
19953 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewObjectArray>
19954 ///
19955 /// # Arguments
19956 /// * `len` - capcity of the new array
19957 /// * must not be negative
19958 /// * `elementClass` - the class of the elements in the array
19959 /// * must not be null
19960 /// * must refer to a class
19961 /// * must not be already garbage collected
19962 /// * `initialElement` - the initial value of all elements in the array
19963 /// * may be null
19964 /// * must be an instance of the class referred to by `elementClass`
19965 /// * must not be already garbage collected
19966 ///
19967 ///
19968 /// # Returns
19969 /// A reference to the new array or null on failure
19970 ///
19971 /// # Throws Java Exception
19972 /// `OutOfMemoryError` - if the jvm runs out of memory allocating the array.
19973 ///
19974 /// # Panics
19975 /// if asserts feature is enabled and UB was detected
19976 ///
19977 /// # Safety
19978 ///
19979 /// Current thread must not be detached from JNI.
19980 ///
19981 /// Current thread must not be currently throwing an exception.
19982 ///
19983 /// Current thread does not hold a critical reference.
19984 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
19985 ///
19986 /// `elementClass` must not be null, must refer to a class and not already be garbage collected.
19987 /// `len` must not be negative
19988 /// `initialElement` must be null or an instance of the class referred to by `elementClass` and not already be garbage collected.
19989 ///
19990 pub unsafe fn NewObjectArray(&self, len: jsize, elementClass: jclass, initialElement: jobject) -> jobjectArray {
19991 unsafe {
19992 #[cfg(feature = "asserts")]
19993 {
19994 self.check_not_critical("NewObjectArray");
19995 self.check_no_exception("NewObjectArray");
19996 assert!(!elementClass.is_null(), "NewObjectArray elementClass must not be null");
19997 assert!(len >= 0, "NewObjectArray len mot not be negative {len}");
19998 }
19999
20000 self.jni::<extern "system" fn(JNIEnvVTable, jsize, jclass, jobject) -> jobjectArray>(172)(self.vtable, len, elementClass, initialElement)
20001 }
20002 }
20003
20004 ///
20005 /// Returns a local reference to a single element in the given object array.
20006 ///
20007 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetObjectArrayElement>
20008 ///
20009 /// # Arguments
20010 /// * `array` - the object array
20011 /// * must not be null
20012 /// * must be an array
20013 /// * must not already be garbage collected
20014 /// * `index` - the index of the element to get
20015 ///
20016 /// # Returns
20017 /// A local reference to the element at the index in the array or null if the element was null or an error occured.
20018 ///
20019 /// # Throws Java Exception
20020 /// * `ArrayIndexOutOfBoundsException` - if the index is out of bounds
20021 ///
20022 /// # Panics
20023 /// if asserts feature is enabled and UB was detected
20024 ///
20025 /// # Safety
20026 ///
20027 /// Current thread must not be detached from JNI.
20028 ///
20029 /// Current thread must not be currently throwing an exception.
20030 ///
20031 /// Current thread does not hold a critical reference.
20032 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20033 ///
20034 /// `array` must not be null, must refer to a array and not already be garbage collected.
20035 ///
20036 pub unsafe fn GetObjectArrayElement(&self, array: jobjectArray, index: jsize) -> jobject {
20037 unsafe {
20038 #[cfg(feature = "asserts")]
20039 {
20040 self.check_not_critical("GetObjectArrayElement");
20041 self.check_no_exception("GetObjectArrayElement");
20042 assert!(!array.is_null(), "GetObjectArrayElement array must not be null");
20043 }
20044
20045 self.jni::<extern "system" fn(JNIEnvVTable, jobjectArray, jsize) -> jobject>(173)(self.vtable, array, index)
20046 }
20047 }
20048
20049 ///
20050 /// Set a single element in a object array
20051 ///
20052 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetObjectArrayElement>
20053 ///
20054 /// # Arguments
20055 /// * `array` - the object array
20056 /// * must not be null
20057 /// * must be an array
20058 /// * must not already be garbage collected
20059 /// * `index` - the index of the element to get
20060 /// * `value` - the new value of the element
20061 /// * may be null
20062 /// * must match the type of the array
20063 /// * must not be already garbage collected
20064 ///
20065 /// # Throws Java Exception
20066 /// * `ArrayIndexOutOfBoundsException` - if the index is out of bounds
20067 ///
20068 /// # Panics
20069 /// if asserts feature is enabled and UB was detected
20070 ///
20071 /// # Safety
20072 ///
20073 /// Current thread must not be detached from JNI.
20074 ///
20075 /// Current thread must not be currently throwing an exception.
20076 ///
20077 /// Current thread does not hold a critical reference.
20078 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20079 ///
20080 /// `array` must not be null, must refer to a array and not already be garbage collected.
20081 /// `value` must be null or an instance of the type contained inside the array and not already be garbage collected.
20082 ///
20083 pub unsafe fn SetObjectArrayElement(&self, array: jobjectArray, index: jsize, value: jobject) {
20084 unsafe {
20085 #[cfg(feature = "asserts")]
20086 {
20087 self.check_not_critical("SetObjectArrayElement");
20088 self.check_no_exception("SetObjectArrayElement");
20089 assert!(!array.is_null(), "SetObjectArrayElement array must not be null");
20090 //TODO check array component type matches value
20091 }
20092
20093 self.jni::<extern "system" fn(JNIEnvVTable, jobjectArray, jsize, jobject)>(174)(self.vtable, array, index, value);
20094 }
20095 }
20096
20097 ///
20098 /// Creates a new boolean array
20099 ///
20100 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewBooleanArray>
20101 ///
20102 /// # Arguments
20103 /// * `size` - capacity of the new array
20104 /// * must not be negative
20105 ///
20106 ///
20107 /// # Returns
20108 /// A reference to the new array or null on failure
20109 ///
20110 /// # Throws Java Exception
20111 /// `OutOfMemoryError` - if the jvm runs out of memory allocating the array.
20112 ///
20113 /// # Panics
20114 /// if asserts feature is enabled and UB was detected
20115 ///
20116 /// # Safety
20117 ///
20118 /// Current thread must not be detached from JNI.
20119 ///
20120 /// Current thread must not be currently throwing an exception.
20121 ///
20122 /// Current thread does not hold a critical reference.
20123 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20124 ///
20125 /// `size` must not be negative
20126 ///
20127 #[must_use]
20128 pub unsafe fn NewBooleanArray(&self, size: jsize) -> jbooleanArray {
20129 unsafe {
20130 #[cfg(feature = "asserts")]
20131 {
20132 self.check_not_critical("NewBooleanArray");
20133 self.check_no_exception("NewBooleanArray");
20134 assert!(size >= 0, "NewBooleanArray size must not be negative {size}");
20135 }
20136
20137 self.jni::<extern "system" fn(JNIEnvVTable, jsize) -> jobject>(175)(self.vtable, size)
20138 }
20139 }
20140
20141 ///
20142 /// Creates a new byte array
20143 ///
20144 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewByteArray>
20145 ///
20146 /// # Arguments
20147 /// * `size` - capacity of the new array
20148 /// * must not be negative
20149 ///
20150 ///
20151 /// # Returns
20152 /// A reference to the new array or null on failure
20153 ///
20154 /// # Throws Java Exception
20155 /// `OutOfMemoryError` - if the jvm runs out of memory allocating the array.
20156 ///
20157 /// # Panics
20158 /// if asserts feature is enabled and UB was detected
20159 ///
20160 /// # Safety
20161 ///
20162 /// Current thread must not be detached from JNI.
20163 ///
20164 /// Current thread must not be currently throwing an exception.
20165 ///
20166 /// Current thread does not hold a critical reference.
20167 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20168 ///
20169 /// `size` must not be negative
20170 ///
20171 #[must_use]
20172 pub unsafe fn NewByteArray(&self, size: jsize) -> jbyteArray {
20173 unsafe {
20174 #[cfg(feature = "asserts")]
20175 {
20176 self.check_not_critical("NewByteArray");
20177 self.check_no_exception("NewByteArray");
20178 assert!(size >= 0, "NewByteArray size must not be negative {size}");
20179 }
20180
20181 self.jni::<extern "system" fn(JNIEnvVTable, jsize) -> jbyteArray>(176)(self.vtable, size)
20182 }
20183 }
20184
20185 ///
20186 /// Creates a new char array
20187 ///
20188 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewCharArray>
20189 ///
20190 /// # Arguments
20191 /// * `size` - capacity of the new array
20192 /// * must not be negative
20193 ///
20194 ///
20195 /// # Returns
20196 /// A reference to the new array or null on failure
20197 ///
20198 /// # Throws Java Exception
20199 /// `OutOfMemoryError` - if the jvm runs out of memory allocating the array.
20200 ///
20201 /// # Panics
20202 /// if asserts feature is enabled and UB was detected
20203 ///
20204 /// # Safety
20205 ///
20206 /// Current thread must not be detached from JNI.
20207 ///
20208 /// Current thread must not be currently throwing an exception.
20209 ///
20210 /// Current thread does not hold a critical reference.
20211 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20212 ///
20213 /// `size` must not be negative
20214 ///
20215 #[must_use]
20216 pub unsafe fn NewCharArray(&self, size: jsize) -> jcharArray {
20217 unsafe {
20218 #[cfg(feature = "asserts")]
20219 {
20220 self.check_not_critical("NewCharArray");
20221 self.check_no_exception("NewCharArray");
20222 assert!(size >= 0, "NewCharArray size must not be negative {size}");
20223 }
20224
20225 self.jni::<extern "system" fn(JNIEnvVTable, jsize) -> jcharArray>(177)(self.vtable, size)
20226 }
20227 }
20228
20229 ///
20230 /// Creates a new short array
20231 ///
20232 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewShortArray>
20233 ///
20234 /// # Arguments
20235 /// * `size` - capacity of the new array
20236 /// * must not be negative
20237 ///
20238 ///
20239 /// # Returns
20240 /// A reference to the new array or null on failure
20241 ///
20242 /// # Throws Java Exception
20243 /// `OutOfMemoryError` - if the jvm runs out of memory allocating the array.
20244 ///
20245 /// # Panics
20246 /// if asserts feature is enabled and UB was detected
20247 ///
20248 /// # Safety
20249 ///
20250 /// Current thread must not be detached from JNI.
20251 ///
20252 /// Current thread must not be currently throwing an exception.
20253 ///
20254 /// Current thread does not hold a critical reference.
20255 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20256 ///
20257 /// `size` must not be negative
20258 ///
20259 #[must_use]
20260 pub unsafe fn NewShortArray(&self, size: jsize) -> jshortArray {
20261 unsafe {
20262 #[cfg(feature = "asserts")]
20263 {
20264 self.check_not_critical("NewShortArray");
20265 self.check_no_exception("NewShortArray");
20266 assert!(size >= 0, "NewShortArray size must not be negative {size}");
20267 }
20268
20269 self.jni::<extern "system" fn(JNIEnvVTable, jsize) -> jshortArray>(178)(self.vtable, size)
20270 }
20271 }
20272
20273 ///
20274 /// Creates a new int array
20275 ///
20276 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewIntArray>
20277 ///
20278 /// # Arguments
20279 /// * `size` - capacity of the new array
20280 /// * must not be negative
20281 ///
20282 ///
20283 /// # Returns
20284 /// A reference to the new array or null on failure
20285 ///
20286 /// # Throws Java Exception
20287 /// `OutOfMemoryError` - if the jvm runs out of memory allocating the array.
20288 ///
20289 /// # Panics
20290 /// if asserts feature is enabled and UB was detected
20291 ///
20292 /// # Safety
20293 ///
20294 /// Current thread must not be detached from JNI.
20295 ///
20296 /// Current thread must not be currently throwing an exception.
20297 ///
20298 /// Current thread does not hold a critical reference.
20299 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20300 ///
20301 /// `size` must not be negative
20302 ///
20303 #[must_use]
20304 pub unsafe fn NewIntArray(&self, size: jsize) -> jintArray {
20305 unsafe {
20306 #[cfg(feature = "asserts")]
20307 {
20308 self.check_not_critical("NewIntArray");
20309 self.check_no_exception("NewIntArray");
20310 assert!(size >= 0, "NewIntArray size must not be negative {size}");
20311 }
20312
20313 self.jni::<extern "system" fn(JNIEnvVTable, jsize) -> jintArray>(179)(self.vtable, size)
20314 }
20315 }
20316
20317 ///
20318 /// Creates a new long array
20319 ///
20320 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewLongArray>
20321 ///
20322 /// # Arguments
20323 /// * `size` - capacity of the new array
20324 /// * must not be negative
20325 ///
20326 ///
20327 /// # Returns
20328 /// A reference to the new array or null on failure
20329 ///
20330 /// # Throws Java Exception
20331 /// `OutOfMemoryError` - if the jvm runs out of memory allocating the array.
20332 ///
20333 /// # Panics
20334 /// if asserts feature is enabled and UB was detected
20335 ///
20336 /// # Safety
20337 ///
20338 /// Current thread must not be detached from JNI.
20339 ///
20340 /// Current thread must not be currently throwing an exception.
20341 ///
20342 /// Current thread does not hold a critical reference.
20343 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20344 ///
20345 /// `size` must not be negative
20346 ///
20347 #[must_use]
20348 pub unsafe fn NewLongArray(&self, size: jsize) -> jlongArray {
20349 unsafe {
20350 #[cfg(feature = "asserts")]
20351 {
20352 self.check_not_critical("NewLongArray");
20353 self.check_no_exception("NewLongArray");
20354 assert!(size >= 0, "NewLongArray size must not be negative {size}");
20355 }
20356
20357 self.jni::<extern "system" fn(JNIEnvVTable, jsize) -> jlongArray>(180)(self.vtable, size)
20358 }
20359 }
20360
20361 ///
20362 /// Creates a new float array
20363 ///
20364 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewFloatArray>
20365 ///
20366 /// # Arguments
20367 /// * `size` - capacity of the new array
20368 /// * must not be negative
20369 ///
20370 ///
20371 /// # Returns
20372 /// A reference to the new array or null on failure
20373 ///
20374 /// # Throws Java Exception
20375 /// `OutOfMemoryError` - if the jvm runs out of memory allocating the array.
20376 ///
20377 /// # Panics
20378 /// if asserts feature is enabled and UB was detected
20379 ///
20380 /// # Safety
20381 ///
20382 /// Current thread must not be detached from JNI.
20383 ///
20384 /// Current thread must not be currently throwing an exception.
20385 ///
20386 /// Current thread does not hold a critical reference.
20387 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20388 ///
20389 /// `size` must not be negative
20390 ///
20391 #[must_use]
20392 pub unsafe fn NewFloatArray(&self, size: jsize) -> jfloatArray {
20393 unsafe {
20394 #[cfg(feature = "asserts")]
20395 {
20396 self.check_not_critical("NewFloatArray");
20397 self.check_no_exception("NewFloatArray");
20398 assert!(size >= 0, "NewFloatArray size must not be negative {size}");
20399 }
20400
20401 self.jni::<extern "system" fn(JNIEnvVTable, jsize) -> jfloatArray>(181)(self.vtable, size)
20402 }
20403 }
20404
20405 ///
20406 /// Creates a new double array
20407 ///
20408 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewDoubleArray>
20409 ///
20410 /// # Arguments
20411 /// * `size` - capacity of the new array
20412 /// * must not be negative
20413 ///
20414 ///
20415 /// # Returns
20416 /// A reference to the new array or null on failure
20417 ///
20418 /// # Throws Java Exception
20419 /// `OutOfMemoryError` - if the jvm runs out of memory allocating the array.
20420 ///
20421 /// # Panics
20422 /// if asserts feature is enabled and UB was detected
20423 ///
20424 /// # Safety
20425 ///
20426 /// Current thread must not be detached from JNI.
20427 ///
20428 /// Current thread must not be currently throwing an exception.
20429 ///
20430 /// Current thread does not hold a critical reference.
20431 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20432 ///
20433 /// `size` must not be negative
20434 ///
20435 #[must_use]
20436 pub unsafe fn NewDoubleArray(&self, size: jsize) -> jdoubleArray {
20437 unsafe {
20438 #[cfg(feature = "asserts")]
20439 {
20440 self.check_not_critical("NewDoubleArray");
20441 self.check_no_exception("NewDoubleArray");
20442 assert!(size >= 0, "NewDoubleArray size must not be negative {size}");
20443 }
20444
20445 self.jni::<extern "system" fn(JNIEnvVTable, jsize) -> jdoubleArray>(182)(self.vtable, size)
20446 }
20447 }
20448
20449 ///
20450 /// Get the boolean content inside the array
20451 ///
20452 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetBooleanArrayElements>
20453 ///
20454 /// # Arguments
20455 /// * `array` - the array
20456 /// * must not be null
20457 /// * must be an array
20458 /// * must not already be garbage collected
20459 /// * `isCopy` - optional flag for the jvm to indicate if the data is a copy or not.
20460 /// * can be null
20461 ///
20462 /// # Returns
20463 /// A pointer to the elements or null if an error occured.
20464 ///
20465 /// # Throws Java Exception
20466 /// * `OutOfMemoryError` - if the jvm ran out of memory.
20467 ///
20468 /// # Panics
20469 /// if asserts feature is enabled and UB was detected
20470 ///
20471 /// # Safety
20472 ///
20473 /// Current thread must not be detached from JNI.
20474 ///
20475 /// Current thread must not be currently throwing an exception.
20476 ///
20477 /// Current thread does not hold a critical reference.
20478 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20479 ///
20480 /// `array` must not be null, must refer to a array and not already be garbage collected.
20481 ///
20482 pub unsafe fn GetBooleanArrayElements(&self, array: jbooleanArray, is_copy: impl JBooleanMutPtr) -> *mut jboolean {
20483 unsafe {
20484 #[cfg(feature = "asserts")]
20485 {
20486 self.check_not_critical("GetBooleanArrayElements");
20487 self.check_no_exception("GetBooleanArrayElements");
20488 assert!(!array.is_null(), "GetBooleanArrayElements jarray must not be null");
20489 }
20490 is_copy.use_jboolean_mut(|is_copy| self.jni::<extern "system" fn(JNIEnvVTable, jbooleanArray, *mut jboolean) -> *mut jboolean>(183)(self.vtable, array, is_copy))
20491 }
20492 }
20493
20494 ///
20495 /// Get the byte content inside the array
20496 ///
20497 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetByteArrayElements>
20498 ///
20499 /// # Arguments
20500 /// * `array` - the array
20501 /// * must not be null
20502 /// * must be an array
20503 /// * must not already be garbage collected
20504 /// * `isCopy` - optional flag for the jvm to indicate if the data is a copy or not.
20505 /// * can be null
20506 ///
20507 /// # Returns
20508 /// A pointer to the elements or null if an error occured.
20509 ///
20510 /// # Throws Java Exception
20511 /// * `OutOfMemoryError` - if the jvm ran out of memory.
20512 ///
20513 /// # Panics
20514 /// if asserts feature is enabled and UB was detected
20515 ///
20516 /// # Safety
20517 ///
20518 /// Current thread must not be detached from JNI.
20519 ///
20520 /// Current thread must not be currently throwing an exception.
20521 ///
20522 /// Current thread does not hold a critical reference.
20523 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20524 ///
20525 /// `array` must not be null, must refer to a array and not already be garbage collected.
20526 ///
20527 pub unsafe fn GetByteArrayElements(&self, array: jbyteArray, is_copy: impl JBooleanMutPtr) -> *mut jbyte {
20528 unsafe {
20529 #[cfg(feature = "asserts")]
20530 {
20531 self.check_not_critical("GetByteArrayElements");
20532 self.check_no_exception("GetByteArrayElements");
20533 assert!(!array.is_null(), "GetByteArrayElements jarray must not be null");
20534 }
20535
20536 is_copy.use_jboolean_mut(|is_copy| self.jni::<extern "system" fn(JNIEnvVTable, jbyteArray, *mut jboolean) -> *mut jbyte>(184)(self.vtable, array, is_copy))
20537 }
20538 }
20539
20540 ///
20541 /// Get the char content inside the array
20542 ///
20543 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetCharArrayElements>
20544 ///
20545 /// # Arguments
20546 /// * `array` - the array
20547 /// * must not be null
20548 /// * must be an array
20549 /// * must not already be garbage collected
20550 /// * `isCopy` - optional flag for the jvm to indicate if the data is a copy or not.
20551 /// * can be null
20552 ///
20553 /// # Returns
20554 /// A pointer to the elements or null if an error occured.
20555 ///
20556 /// # Throws Java Exception
20557 /// * `OutOfMemoryError` - if the jvm ran out of memory.
20558 ///
20559 /// # Panics
20560 /// if asserts feature is enabled and UB was detected
20561 ///
20562 /// # Safety
20563 ///
20564 /// Current thread must not be detached from JNI.
20565 ///
20566 /// Current thread must not be currently throwing an exception.
20567 ///
20568 /// Current thread does not hold a critical reference.
20569 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20570 ///
20571 /// `array` must not be null, must refer to a array and not already be garbage collected.
20572 ///
20573 pub unsafe fn GetCharArrayElements(&self, array: jcharArray, is_copy: impl JBooleanMutPtr) -> *mut jchar {
20574 unsafe {
20575 #[cfg(feature = "asserts")]
20576 {
20577 self.check_not_critical("GetCharArrayElements");
20578 self.check_no_exception("GetCharArrayElements");
20579 assert!(!array.is_null(), "GetCharArrayElements jarray must not be null");
20580 }
20581
20582 is_copy.use_jboolean_mut(|is_copy| self.jni::<extern "system" fn(JNIEnvVTable, jcharArray, *mut jboolean) -> *mut jchar>(185)(self.vtable, array, is_copy))
20583 }
20584 }
20585
20586 ///
20587 /// Get the short content inside the array
20588 ///
20589 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetShortArrayElements>
20590 ///
20591 /// # Arguments
20592 /// * `array` - the array
20593 /// * must not be null
20594 /// * must be an array
20595 /// * must not already be garbage collected
20596 /// * `isCopy` - optional flag for the jvm to indicate if the data is a copy or not.
20597 /// * can be null
20598 ///
20599 /// # Returns
20600 /// A pointer to the elements or null if an error occured.
20601 ///
20602 /// # Throws Java Exception
20603 /// * `OutOfMemoryError` - if the jvm ran out of memory.
20604 ///
20605 /// # Panics
20606 /// if asserts feature is enabled and UB was detected
20607 ///
20608 /// # Safety
20609 ///
20610 /// Current thread must not be detached from JNI.
20611 ///
20612 /// Current thread must not be currently throwing an exception.
20613 ///
20614 /// Current thread does not hold a critical reference.
20615 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20616 ///
20617 /// `array` must not be null, must refer to a array and not already be garbage collected.
20618 ///
20619 pub unsafe fn GetShortArrayElements(&self, array: jshortArray, is_copy: impl JBooleanMutPtr) -> *mut jshort {
20620 unsafe {
20621 #[cfg(feature = "asserts")]
20622 {
20623 self.check_not_critical("GetShortArrayElements");
20624 self.check_no_exception("GetShortArrayElements");
20625 assert!(!array.is_null(), "GetShortArrayElements jarray must not be null");
20626 }
20627
20628 is_copy.use_jboolean_mut(|is_copy| self.jni::<extern "system" fn(JNIEnvVTable, jshortArray, *mut jboolean) -> *mut jshort>(186)(self.vtable, array, is_copy))
20629 }
20630 }
20631
20632 ///
20633 /// Get the int content inside the array
20634 ///
20635 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetIntArrayElements>
20636 ///
20637 /// # Arguments
20638 /// * `array` - the array
20639 /// * must not be null
20640 /// * must be an array
20641 /// * must not already be garbage collected
20642 /// * `isCopy` - optional flag for the jvm to indicate if the data is a copy or not.
20643 /// * can be null
20644 ///
20645 /// # Returns
20646 /// A pointer to the elements or null if an error occured.
20647 ///
20648 /// # Throws Java Exception
20649 /// * `OutOfMemoryError` - if the jvm ran out of memory.
20650 ///
20651 /// # Panics
20652 /// if asserts feature is enabled and UB was detected
20653 ///
20654 /// # Safety
20655 ///
20656 /// Current thread must not be detached from JNI.
20657 ///
20658 /// Current thread must not be currently throwing an exception.
20659 ///
20660 /// Current thread does not hold a critical reference.
20661 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20662 ///
20663 /// `array` must not be null, must refer to a array and not already be garbage collected.
20664 ///
20665 pub unsafe fn GetIntArrayElements(&self, array: jintArray, is_copy: impl JBooleanMutPtr) -> *mut jint {
20666 unsafe {
20667 #[cfg(feature = "asserts")]
20668 {
20669 self.check_not_critical("GetIntArrayElements");
20670 self.check_no_exception("GetIntArrayElements");
20671 assert!(!array.is_null(), "GetIntArrayElements jarray must not be null");
20672 }
20673
20674 is_copy.use_jboolean_mut(|is_copy| self.jni::<extern "system" fn(JNIEnvVTable, jintArray, *mut jboolean) -> *mut jint>(187)(self.vtable, array, is_copy))
20675 }
20676 }
20677
20678 ///
20679 /// Get the long content inside the array
20680 ///
20681 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetLongArrayElements>
20682 ///
20683 /// # Arguments
20684 /// * `array` - the array
20685 /// * must not be null
20686 /// * must be an array
20687 /// * must not already be garbage collected
20688 /// * `isCopy` - optional flag for the jvm to indicate if the data is a copy or not.
20689 /// * can be null
20690 ///
20691 /// # Returns
20692 /// A pointer to the elements or null if an error occured.
20693 ///
20694 /// # Throws Java Exception
20695 /// * `OutOfMemoryError` - if the jvm ran out of memory.
20696 ///
20697 /// # Panics
20698 /// if asserts feature is enabled and UB was detected
20699 ///
20700 /// # Safety
20701 ///
20702 /// Current thread must not be detached from JNI.
20703 ///
20704 /// Current thread must not be currently throwing an exception.
20705 ///
20706 /// Current thread does not hold a critical reference.
20707 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20708 ///
20709 /// `array` must not be null, must refer to a array and not already be garbage collected.
20710 ///
20711 pub unsafe fn GetLongArrayElements(&self, array: jlongArray, is_copy: impl JBooleanMutPtr) -> *mut jlong {
20712 unsafe {
20713 #[cfg(feature = "asserts")]
20714 {
20715 self.check_not_critical("GetLongArrayElements");
20716 self.check_no_exception("GetLongArrayElements");
20717 assert!(!array.is_null(), "GetLongArrayElements jarray must not be null");
20718 }
20719
20720 is_copy.use_jboolean_mut(|is_copy| self.jni::<extern "system" fn(JNIEnvVTable, jlongArray, *mut jboolean) -> *mut jlong>(188)(self.vtable, array, is_copy))
20721 }
20722 }
20723
20724 ///
20725 /// Get the float content inside the array
20726 ///
20727 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetFloatArrayElements>
20728 ///
20729 /// # Arguments
20730 /// * `array` - the array
20731 /// * must not be null
20732 /// * must be an array
20733 /// * must not already be garbage collected
20734 /// * `isCopy` - optional flag for the jvm to indicate if the data is a copy or not.
20735 /// * can be null
20736 ///
20737 /// # Returns
20738 /// A pointer to the elements or null if an error occured.
20739 ///
20740 /// # Throws Java Exception
20741 /// * `OutOfMemoryError` - if the jvm ran out of memory.
20742 ///
20743 /// # Panics
20744 /// if asserts feature is enabled and UB was detected
20745 ///
20746 /// # Safety
20747 ///
20748 /// Current thread must not be detached from JNI.
20749 ///
20750 /// Current thread must not be currently throwing an exception.
20751 ///
20752 /// Current thread does not hold a critical reference.
20753 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20754 ///
20755 /// `array` must not be null, must refer to a array and not already be garbage collected.
20756 ///
20757 pub unsafe fn GetFloatArrayElements(&self, array: jfloatArray, is_copy: impl JBooleanMutPtr) -> *mut jfloat {
20758 unsafe {
20759 #[cfg(feature = "asserts")]
20760 {
20761 self.check_not_critical("GetFloatArrayElements");
20762 self.check_no_exception("GetFloatArrayElements");
20763 assert!(!array.is_null(), "GetFloatArrayElements jarray must not be null");
20764 }
20765
20766 is_copy.use_jboolean_mut(|is_copy| self.jni::<extern "system" fn(JNIEnvVTable, jfloatArray, *mut jboolean) -> *mut jfloat>(189)(self.vtable, array, is_copy))
20767 }
20768 }
20769
20770 ///
20771 /// Get the double content inside the array
20772 ///
20773 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetDoubleArrayElements>
20774 ///
20775 /// # Arguments
20776 /// * `array` - the array
20777 /// * must not be null
20778 /// * must be an array
20779 /// * must not already be garbage collected
20780 /// * `isCopy` - optional flag for the jvm to indicate if the data is a copy or not.
20781 /// * can be null
20782 ///
20783 /// # Returns
20784 /// A pointer to the elements or null if an error occured.
20785 ///
20786 /// # Throws Java Exception
20787 /// * `OutOfMemoryError` - if the jvm ran out of memory.
20788 ///
20789 /// # Panics
20790 /// if asserts feature is enabled and UB was detected
20791 ///
20792 /// # Safety
20793 ///
20794 /// Current thread must not be detached from JNI.
20795 ///
20796 /// Current thread must not be currently throwing an exception.
20797 ///
20798 /// Current thread does not hold a critical reference.
20799 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20800 ///
20801 /// `array` must not be null, must refer to a array and not already be garbage collected.
20802 ///
20803 pub unsafe fn GetDoubleArrayElements(&self, array: jdoubleArray, is_copy: impl JBooleanMutPtr) -> *mut jdouble {
20804 unsafe {
20805 #[cfg(feature = "asserts")]
20806 {
20807 self.check_not_critical("GetDoubleArrayElements");
20808 self.check_no_exception("GetDoubleArrayElements");
20809 assert!(!array.is_null(), "GetDoubleArrayElements jarray must not be null");
20810 }
20811
20812 is_copy.use_jboolean_mut(|is_copy| self.jni::<extern "system" fn(JNIEnvVTable, jdoubleArray, *mut jboolean) -> *mut jdouble>(190)(self.vtable, array, is_copy))
20813 }
20814 }
20815
20816 ///
20817 /// Releases the boolean array elements back to the jvm
20818 ///
20819 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ReleaseBooleanArrayElements>
20820 ///
20821 /// # Arguments
20822 /// * `array` - the array
20823 /// * must not be null
20824 /// * must be an array
20825 /// * must not already be garbage collected
20826 /// * `elems`
20827 /// * must not be null
20828 /// * `mode`
20829 /// * must be one of the following constants:
20830 /// * `JNI_OK` - release the array, copy back the contents into the internal buffer if it was a copy
20831 /// * `JNI_COMMIT` - do not release the array, copy back the contents into the internal buffer if it was a copy
20832 /// * `JNI_ABORT` - release the array, do not copy back the contents into the internal buffer if it was a copy
20833 /// * Note: if data was not a copy then `JNI_OK` and `JNI_ABORT` do the same.
20834 ///
20835 /// # Panics
20836 /// if asserts feature is enabled and UB was detected
20837 ///
20838 /// # Safety
20839 ///
20840 /// Current thread must not be detached from JNI.
20841 ///
20842 /// Current thread does not hold a critical reference.
20843 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20844 ///
20845 /// `array` must not be null, must refer to a array and not already be garbage collected.
20846 /// `elems` must be the buffer of the same `array` reference
20847 /// `mode` must be one of the constants
20848 ///
20849 pub unsafe fn ReleaseBooleanArrayElements(&self, array: jbooleanArray, elems: *mut jboolean, mode: jint) {
20850 unsafe {
20851 #[cfg(feature = "asserts")]
20852 {
20853 self.check_not_critical("ReleaseBooleanArrayElements");
20854 assert!(!array.is_null(), "ReleaseBooleanArrayElements jarray must not be null");
20855 assert!(!elems.is_null(), "ReleaseBooleanArrayElements elems must not be null");
20856 assert!(
20857 mode == JNI_OK || mode == JNI_COMMIT || mode == JNI_ABORT,
20858 "ReleaseBooleanArrayElements mode is invalid {mode}"
20859 );
20860 }
20861
20862 self.jni::<extern "system" fn(JNIEnvVTable, jbooleanArray, *mut jboolean, jint)>(191)(self.vtable, array, elems, mode);
20863 }
20864 }
20865
20866 ///
20867 /// Releases the byte array elements back to the jvm
20868 ///
20869 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ReleaseByteArrayElements>
20870 ///
20871 /// # Arguments
20872 /// * `array` - the array
20873 /// * must not be null
20874 /// * must be an array
20875 /// * must not already be garbage collected
20876 /// * `elems`
20877 /// * must not be null
20878 /// * `mode`
20879 /// * must be one of the following constants:
20880 /// * `JNI_OK` - release the array, copy back the contents into the internal buffer if it was a copy
20881 /// * `JNI_COMMIT` - do not release the array, copy back the contents into the internal buffer if it was a copy
20882 /// * `JNI_ABORT` - release the array, do not copy back the contents into the internal buffer if it was a copy
20883 /// * Note: if data was not a copy then `JNI_OK` and `JNI_ABORT` do the same.
20884 ///
20885 /// # Panics
20886 /// if asserts feature is enabled and UB was detected
20887 ///
20888 /// # Safety
20889 ///
20890 /// Current thread must not be detached from JNI.
20891 ///
20892 /// Current thread does not hold a critical reference.
20893 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20894 ///
20895 /// `array` must not be null, must refer to a array and not already be garbage collected.
20896 /// `elems` must be the buffer of the same `array` reference
20897 /// `mode` must be one of the constants
20898 ///
20899 pub unsafe fn ReleaseByteArrayElements(&self, array: jbyteArray, elems: *mut jbyte, mode: jint) {
20900 unsafe {
20901 #[cfg(feature = "asserts")]
20902 {
20903 self.check_not_critical("ReleaseByteArrayElements");
20904 assert!(!array.is_null(), "ReleaseByteArrayElements jarray must not be null");
20905 assert!(!elems.is_null(), "ReleaseByteArrayElements elems must not be null");
20906 assert!(mode == JNI_OK || mode == JNI_COMMIT || mode == JNI_ABORT, "ReleaseByteArrayElements mode is invalid {mode}");
20907 }
20908
20909 self.jni::<extern "system" fn(JNIEnvVTable, jbyteArray, *mut jbyte, jint)>(192)(self.vtable, array, elems, mode);
20910 }
20911 }
20912
20913 ///
20914 /// Releases the char array elements back to the jvm
20915 ///
20916 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ReleaseCharArrayElements>
20917 ///
20918 /// # Arguments
20919 /// * `array` - the array
20920 /// * must not be null
20921 /// * must be an array
20922 /// * must not already be garbage collected
20923 /// * `elems`
20924 /// * must not be null
20925 /// * `mode`
20926 /// * must be one of the following constants:
20927 /// * `JNI_OK` - release the array, copy back the contents into the internal buffer if it was a copy
20928 /// * `JNI_COMMIT` - do not release the array, copy back the contents into the internal buffer if it was a copy
20929 /// * `JNI_ABORT` - release the array, do not copy back the contents into the internal buffer if it was a copy
20930 /// * Note: if data was not a copy then `JNI_OK` and `JNI_ABORT` do the same.
20931 ///
20932 ///
20933 /// # Panics
20934 /// if asserts feature is enabled and UB was detected
20935 ///
20936 /// # Safety
20937 ///
20938 /// Current thread must not be detached from JNI.
20939 ///
20940 /// Current thread does not hold a critical reference.
20941 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20942 ///
20943 /// `array` must not be null, must refer to a array and not already be garbage collected.
20944 /// `elems` must be the buffer of the same `array` reference
20945 /// `mode` must be one of the constants
20946 ///
20947 pub unsafe fn ReleaseCharArrayElements(&self, array: jcharArray, elems: *mut jchar, mode: jint) {
20948 unsafe {
20949 #[cfg(feature = "asserts")]
20950 {
20951 self.check_not_critical("ReleaseCharArrayElements");
20952 assert!(!array.is_null(), "ReleaseCharArrayElements jarray must not be null");
20953 assert!(!elems.is_null(), "ReleaseCharArrayElements elems must not be null");
20954 assert!(mode == JNI_OK || mode == JNI_COMMIT || mode == JNI_ABORT, "ReleaseCharArrayElements mode is invalid {mode}");
20955 }
20956
20957 self.jni::<extern "system" fn(JNIEnvVTable, jcharArray, *mut jchar, jint)>(193)(self.vtable, array, elems, mode);
20958 }
20959 }
20960
20961 ///
20962 /// Releases the short array elements back to the jvm
20963 ///
20964 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ReleaseShortArrayElements>
20965 ///
20966 /// # Arguments
20967 /// * `array` - the array
20968 /// * must not be null
20969 /// * must be an array
20970 /// * must not already be garbage collected
20971 /// * `elems`
20972 /// * must not be null
20973 /// * `mode`
20974 /// * must be one of the following constants:
20975 /// * `JNI_OK` - release the array, copy back the contents into the internal buffer if it was a copy
20976 /// * `JNI_COMMIT` - do not release the array, copy back the contents into the internal buffer if it was a copy
20977 /// * `JNI_ABORT` - release the array, do not copy back the contents into the internal buffer if it was a copy
20978 /// * Note: if data was not a copy then `JNI_OK` and `JNI_ABORT` do the same.
20979 ///
20980 ///
20981 /// # Panics
20982 /// if asserts feature is enabled and UB was detected
20983 ///
20984 /// # Safety
20985 ///
20986 /// Current thread must not be detached from JNI.
20987 ///
20988 /// Current thread does not hold a critical reference.
20989 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
20990 ///
20991 /// `array` must not be null, must refer to a array and not already be garbage collected.
20992 /// `elems` must be the buffer of the same `array` reference
20993 /// `mode` must be one of the constants
20994 ///
20995 pub unsafe fn ReleaseShortArrayElements(&self, array: jshortArray, elems: *mut jshort, mode: jint) {
20996 unsafe {
20997 #[cfg(feature = "asserts")]
20998 {
20999 self.check_not_critical("ReleaseShortArrayElements");
21000 assert!(!array.is_null(), "ReleaseShortArrayElements jarray must not be null");
21001 assert!(!elems.is_null(), "ReleaseShortArrayElements elems must not be null");
21002 assert!(
21003 mode == JNI_OK || mode == JNI_COMMIT || mode == JNI_ABORT,
21004 "ReleaseShortArrayElements mode is invalid {mode}"
21005 );
21006 }
21007
21008 self.jni::<extern "system" fn(JNIEnvVTable, jshortArray, *mut jshort, jint)>(194)(self.vtable, array, elems, mode);
21009 }
21010 }
21011
21012 ///
21013 /// Releases the int array elements back to the jvm
21014 ///
21015 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ReleaseIntArrayElements>
21016 ///
21017 /// # Arguments
21018 /// * `array` - the array
21019 /// * must not be null
21020 /// * must be an array
21021 /// * must not already be garbage collected
21022 /// * `elems`
21023 /// * must not be null
21024 /// * `mode`
21025 /// * must be one of the following constants:
21026 /// * `JNI_OK` - release the array, copy back the contents into the internal buffer if it was a copy
21027 /// * `JNI_COMMIT` - do not release the array, copy back the contents into the internal buffer if it was a copy
21028 /// * `JNI_ABORT` - release the array, do not copy back the contents into the internal buffer if it was a copy
21029 /// * Note: if data was not a copy then `JNI_OK` and `JNI_ABORT` do the same.
21030 ///
21031 ///
21032 /// # Panics
21033 /// if asserts feature is enabled and UB was detected
21034 ///
21035 /// # Safety
21036 ///
21037 /// Current thread must not be detached from JNI.
21038 ///
21039 /// Current thread does not hold a critical reference.
21040 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21041 ///
21042 /// `array` must not be null, must refer to a array and not already be garbage collected.
21043 /// `elems` must be the buffer of the same `array` reference
21044 /// `mode` must be one of the constants
21045 ///
21046 pub unsafe fn ReleaseIntArrayElements(&self, array: jintArray, elems: *mut jint, mode: jint) {
21047 unsafe {
21048 #[cfg(feature = "asserts")]
21049 {
21050 self.check_not_critical("ReleaseIntArrayElements");
21051 assert!(!array.is_null(), "ReleaseIntArrayElements jarray must not be null");
21052 assert!(!elems.is_null(), "ReleaseIntArrayElements elems must not be null");
21053 assert!(mode == JNI_OK || mode == JNI_COMMIT || mode == JNI_ABORT, "ReleaseIntArrayElements mode is invalid {mode}");
21054 }
21055
21056 self.jni::<extern "system" fn(JNIEnvVTable, jintArray, *mut jint, jint)>(195)(self.vtable, array, elems, mode);
21057 }
21058 }
21059
21060 ///
21061 /// Releases the long array elements back to the jvm
21062 ///
21063 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ReleaseLongArrayElements>
21064 ///
21065 /// # Arguments
21066 /// * `array` - the array
21067 /// * must not be null
21068 /// * must be an array
21069 /// * must not already be garbage collected
21070 /// * `elems`
21071 /// * must not be null
21072 /// * `mode`
21073 /// * must be one of the following constants:
21074 /// * `JNI_OK` - release the array, copy back the contents into the internal buffer if it was a copy
21075 /// * `JNI_COMMIT` - do not release the array, copy back the contents into the internal buffer if it was a copy
21076 /// * `JNI_ABORT` - release the array, do not copy back the contents into the internal buffer if it was a copy
21077 /// * Note: if data was not a copy then `JNI_OK` and `JNI_ABORT` do the same.
21078 ///
21079 ///
21080 /// # Panics
21081 /// if asserts feature is enabled and UB was detected
21082 ///
21083 /// # Safety
21084 ///
21085 /// Current thread must not be detached from JNI.
21086 ///
21087 /// Current thread does not hold a critical reference.
21088 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21089 ///
21090 /// `array` must not be null, must refer to a array and not already be garbage collected.
21091 /// `elems` must be the buffer of the same `array` reference
21092 /// `mode` must be one of the constants
21093 ///
21094 pub unsafe fn ReleaseLongArrayElements(&self, array: jlongArray, elems: *mut jlong, mode: jint) {
21095 unsafe {
21096 #[cfg(feature = "asserts")]
21097 {
21098 self.check_not_critical("ReleaseLongArrayElements");
21099 assert!(!array.is_null(), "ReleaseLongArrayElements jarray must not be null");
21100 assert!(!elems.is_null(), "ReleaseLongArrayElements elems must not be null");
21101 assert!(mode == JNI_OK || mode == JNI_COMMIT || mode == JNI_ABORT, "ReleaseLongArrayElements mode is invalid {mode}");
21102 }
21103
21104 self.jni::<extern "system" fn(JNIEnvVTable, jlongArray, *mut jlong, jint)>(196)(self.vtable, array, elems, mode);
21105 }
21106 }
21107
21108 ///
21109 /// Releases the float array elements back to the jvm
21110 ///
21111 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ReleaseFloatArrayElements>
21112 ///
21113 /// # Arguments
21114 /// * `array` - the array
21115 /// * must not be null
21116 /// * must be an array
21117 /// * must not already be garbage collected
21118 /// * `elems`
21119 /// * must not be null
21120 /// * `mode`
21121 /// * must be one of the following constants:
21122 /// * `JNI_OK` - release the array, copy back the contents into the internal buffer if it was a copy
21123 /// * `JNI_COMMIT` - do not release the array, copy back the contents into the internal buffer if it was a copy
21124 /// * `JNI_ABORT` - release the array, do not copy back the contents into the internal buffer if it was a copy
21125 /// * Note: if data was not a copy then `JNI_OK` and `JNI_ABORT` do the same.
21126 ///
21127 ///
21128 /// # Panics
21129 /// if asserts feature is enabled and UB was detected
21130 ///
21131 /// # Safety
21132 ///
21133 /// Current thread must not be detached from JNI.
21134 ///
21135 /// Current thread does not hold a critical reference.
21136 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21137 ///
21138 /// `array` must not be null, must refer to a array and not already be garbage collected.
21139 /// `elems` must be the buffer of the same `array` reference
21140 /// `mode` must be one of the constants
21141 ///
21142 pub unsafe fn ReleaseFloatArrayElements(&self, array: jfloatArray, elems: *mut jfloat, mode: jint) {
21143 unsafe {
21144 #[cfg(feature = "asserts")]
21145 {
21146 self.check_not_critical("ReleaseFloatArrayElements");
21147 assert!(!array.is_null(), "ReleaseFloatArrayElements jarray must not be null");
21148 assert!(!elems.is_null(), "ReleaseFloatArrayElements elems must not be null");
21149 assert!(
21150 mode == JNI_OK || mode == JNI_COMMIT || mode == JNI_ABORT,
21151 "ReleaseFloatArrayElements mode is invalid {mode}"
21152 );
21153 }
21154
21155 self.jni::<extern "system" fn(JNIEnvVTable, jfloatArray, *mut jfloat, jint)>(197)(self.vtable, array, elems, mode);
21156 }
21157 }
21158
21159 ///
21160 /// Releases the double array elements back to the jvm
21161 ///
21162 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#ReleaseDoubleArrayElements>
21163 ///
21164 /// # Arguments
21165 /// * `array` - the array
21166 /// * must not be null
21167 /// * must be an array
21168 /// * must not already be garbage collected
21169 /// * `elems`
21170 /// * must not be null
21171 /// * `mode`
21172 /// * must be one of the following constants:
21173 /// * `JNI_OK` - release the array, copy back the contents into the internal buffer if it was a copy
21174 /// * `JNI_COMMIT` - do not release the array, copy back the contents into the internal buffer if it was a copy
21175 /// * `JNI_ABORT` - release the array, do not copy back the contents into the internal buffer if it was a copy
21176 /// * Note: if data was not a copy then `JNI_OK` and `JNI_ABORT` do the same.
21177 ///
21178 ///
21179 /// # Panics
21180 /// if asserts feature is enabled and UB was detected
21181 ///
21182 /// # Safety
21183 ///
21184 /// Current thread must not be detached from JNI.
21185 ///
21186 /// Current thread does not hold a critical reference.
21187 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21188 ///
21189 /// `array` must not be null, must refer to a array and not already be garbage collected.
21190 /// `elems` must be the buffer of the same `array` reference
21191 /// `mode` must be one of the constants
21192 ///
21193 pub unsafe fn ReleaseDoubleArrayElements(&self, array: jdoubleArray, elems: *mut jdouble, mode: jint) {
21194 unsafe {
21195 #[cfg(feature = "asserts")]
21196 {
21197 self.check_not_critical("ReleaseDoubleArrayElements");
21198 assert!(!array.is_null(), "ReleaseDoubleArrayElements jarray must not be null");
21199 assert!(!elems.is_null(), "ReleaseDoubleArrayElements elems must not be null");
21200 assert!(
21201 mode == JNI_OK || mode == JNI_COMMIT || mode == JNI_ABORT,
21202 "ReleaseDoubleArrayElements mode is invalid {mode}"
21203 );
21204 }
21205
21206 self.jni::<extern "system" fn(JNIEnvVTable, jdoubleArray, *mut jdouble, jint)>(198)(self.vtable, array, elems, mode);
21207 }
21208 }
21209
21210 ///
21211 /// Copies data from the jbooleanArray `array` starting from the given `start` index into the slice `buf`.
21212 ///
21213 /// # Arguments
21214 /// * `array` - handle to a Java jbooleanArray.
21215 /// * `start` - the index of the first element to copy in the Java jbooleanArray
21216 /// * `buf` - the slice to copy data into
21217 ///
21218 /// # Throws Java Exception:
21219 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
21220 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
21221 ///
21222 /// It is JVM implementation specific what is stored inside buf if this function throws an exception.
21223 /// * Data partially written
21224 /// * No data written
21225 ///
21226 /// # Panics
21227 /// if asserts feature is enabled and UB was detected
21228 /// if the `buf.len()` is larger than `jsize::MAX`
21229 ///
21230 /// # Safety
21231 /// Current thread must not be detached from JNI.
21232 ///
21233 /// Current thread must not be currently throwing an exception.
21234 ///
21235 /// Current thread does not hold a critical reference.
21236 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21237 ///
21238 /// `array` must be a valid non-null reference to a jbooleanArray.
21239 ///
21240 /// # Example
21241 /// ```rust
21242 /// use jni_simple::{*};
21243 ///
21244 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
21245 /// array: jbooleanArray, chunk_buffer: &mut [jboolean], chunk_offset: usize) -> bool {
21246 /// if array.is_null() {
21247 /// panic!("Java Array is null")
21248 /// }
21249 ///
21250 /// env.GetBooleanArrayRegion_into_slice(array, chunk_offset as jsize, chunk_buffer);
21251 /// if env.ExceptionCheck() {
21252 /// //ArrayIndexOutOfBoundsException
21253 /// env.ExceptionClear();
21254 /// return false;
21255 /// }
21256 /// true
21257 /// }
21258 /// ```
21259 ///
21260 pub unsafe fn GetBooleanArrayRegion_into_slice(&self, array: jbooleanArray, start: jsize, buf: &mut [jboolean]) {
21261 unsafe {
21262 self.GetBooleanArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_mut_ptr());
21263 }
21264 }
21265
21266 ///
21267 /// Copies data from the slice `buf` into the jbooleanArray `array` starting at the given `start` index.
21268 ///
21269 /// # Arguments
21270 /// * `array` - handle to a Java jbooleanArray.
21271 /// * `start` - the index where the first element should be coped into in the Java jybteArray
21272 /// * `buf` - the slice where data is copied from
21273 ///
21274 /// # Throws Java Exception:
21275 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
21276 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
21277 ///
21278 /// It is JVM implementation specific what is stored inside `array` if this function throws an exception.
21279 /// * Data partially written
21280 /// * No data written
21281 ///
21282 /// # Panics
21283 /// if asserts feature is enabled and UB was detected
21284 ///
21285 /// # Safety
21286 /// Current thread must not be detached from JNI.
21287 ///
21288 /// Current thread must not be currently throwing an exception.
21289 ///
21290 /// Current thread does not hold a critical reference.
21291 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21292 ///
21293 /// `array` must be a valid non-null reference to a jbooleanArray.
21294 ///
21295 /// # Example
21296 /// ```rust
21297 /// use jni_simple::{*};
21298 ///
21299 /// unsafe fn copy_chunk_from_rust_to_java(env: JNIEnv,
21300 /// array: jbooleanArray, chunk_buffer: &[i8], chunk_offset: usize) -> bool {
21301 /// if array.is_null() {
21302 /// panic!("Java Array is null")
21303 /// }
21304 ///
21305 /// env.SetByteArrayRegion_from_slice(array, chunk_offset as jsize, chunk_buffer);
21306 /// if env.ExceptionCheck() {
21307 /// //ArrayIndexOutOfBoundsException
21308 /// env.ExceptionClear();
21309 /// return false;
21310 /// }
21311 /// true
21312 /// }
21313 /// ```
21314 ///
21315 pub unsafe fn SetBooleanArrayRegion_from_slice(&self, array: jbooleanArray, start: jsize, buf: &[impl JBooleanInputLayout]) {
21316 let ptr: *const jboolean = buf.as_ptr().cast();
21317 unsafe {
21318 self.SetBooleanArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), ptr);
21319 }
21320 }
21321
21322 ///
21323 /// Copies data from a Java jbooleanArray `array` into a new `Vec<jboolean>`
21324 ///
21325 /// # Arguments
21326 /// * `array` - handle to a Java jbooleanArray.
21327 /// * `start` - the index of the first element to copy in the Java jbooleanArray
21328 /// * `len` - the amount of data that should be copied. If `None` then all remaining elements in the array are copied.
21329 ///
21330 /// # Returns:
21331 /// a new `Vec<jboolean>` that contains the copied data.
21332 ///
21333 /// # Returns empty Vec:
21334 /// * When the array in fact was empty or len was zero.
21335 /// * When this function throws a Java Exception.
21336 ///
21337 /// # Throws Java Exception:
21338 /// * `ArrayIndexOutOfBoundsException` - if `len` is negative.
21339 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the array.
21340 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative.
21341 /// * `ArrayIndexOutOfBoundsException` - if `start` is larget than `env.GetArrayLength(array)`.
21342 /// * `ArrayIndexOutOfBoundsException` - if `start` equals env.GetArrayLength(array) and `len` is larger than 0.
21343 ///
21344 /// # Panics
21345 /// if asserts feature is enabled and UB was detected
21346 ///
21347 /// # Safety
21348 /// Current thread must not be detached from JNI.
21349 ///
21350 /// Current thread must not be currently throwing an exception.
21351 ///
21352 /// Current thread does not hold a critical reference.
21353 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21354 ///
21355 /// `array` must be a valid non-null reference to a jbooleanArray.
21356 ///
21357 /// # Example
21358 /// ```rust
21359 /// use jni_simple::{*};
21360 ///
21361 /// unsafe fn copy_entire_java_array_to_rust(env: JNIEnv, array: jbooleanArray) -> Vec<jboolean> {
21362 /// if array.is_null() {
21363 /// panic!("Java Array is null")
21364 /// }
21365 /// env.GetBooleanArrayRegion_as_vec(array, 0, None)
21366 /// }
21367 /// ```
21368 ///
21369 pub unsafe fn GetBooleanArrayRegion_as_vec(&self, array: jbyteArray, start: jsize, len: Option<jsize>) -> Vec<jboolean> {
21370 unsafe {
21371 let len = len.unwrap_or_else(|| self.GetArrayLength(array).saturating_sub(start.max(0)).max(0));
21372 if let Ok(len) = usize::try_from(len) {
21373 let mut data = vec![jboolean::FALSE; len]; //We could un-init this, but better play it safe...
21374 self.GetBooleanArrayRegion_into_slice(array, start, data.as_mut_slice());
21375 if self.ExceptionCheck() {
21376 return Vec::new();
21377 }
21378 return data;
21379 }
21380
21381 //Negative len
21382 let mut sentinel_buffer = [jboolean::FALSE];
21383 self.GetBooleanArrayRegion(array, start, len.min(-1), sentinel_buffer.as_mut_ptr());
21384 Vec::new()
21385 }
21386 }
21387
21388 ///
21389 /// Copies data from a Java jbooleanArray `array` into a new `Vec<bool>`
21390 ///
21391 /// # Arguments
21392 /// * `array` - handle to a Java jbooleanArray.
21393 /// * `start` - the index of the first element to copy in the Java jbooleanArray
21394 /// * `len` - the amount of data that should be copied. If `None` then all remaining elements in the array are copied.
21395 ///
21396 /// # Returns:
21397 /// a new `Vec<bool>` that contains the copied data.
21398 ///
21399 /// # Returns empty Vec:
21400 /// * When the array in fact was empty or len was zero.
21401 /// * When this function throws a Java Exception.
21402 ///
21403 /// # Throws Java Exception:
21404 /// * `ArrayIndexOutOfBoundsException` - if `len` is negative.
21405 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the array.
21406 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative.
21407 /// * `ArrayIndexOutOfBoundsException` - if `start` is larget than `env.GetArrayLength(array)`.
21408 /// * `ArrayIndexOutOfBoundsException` - if `start` equals env.GetArrayLength(array) and `len` is larger than 0.
21409 ///
21410 /// # Panics
21411 /// if asserts feature is enabled and UB was detected
21412 ///
21413 /// # Safety
21414 /// Current thread must not be detached from JNI.
21415 ///
21416 /// Current thread must not be currently throwing an exception.
21417 ///
21418 /// Current thread does not hold a critical reference.
21419 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21420 ///
21421 /// `array` must be a valid non-null reference to a jbooleanArray.
21422 ///
21423 /// # Example
21424 /// ```rust
21425 /// use jni_simple::{*};
21426 ///
21427 /// unsafe fn copy_entire_java_array_to_rust(env: JNIEnv, array: jbooleanArray) -> Vec<bool> {
21428 /// if array.is_null() {
21429 /// panic!("Java Array is null")
21430 /// }
21431 /// env.GetBooleanArrayRegion_as_bool_vec(array, 0, None)
21432 /// }
21433 /// ```
21434 ///
21435 pub unsafe fn GetBooleanArrayRegion_as_bool_vec(&self, array: jbyteArray, start: jsize, len: Option<jsize>) -> Vec<bool> {
21436 unsafe {
21437 let len = len.unwrap_or_else(|| self.GetArrayLength(array).saturating_sub(start.max(0)).max(0));
21438 if let Ok(len) = usize::try_from(len) {
21439 let mut data = vec![jboolean::FALSE; len]; //We could un-init this, but better play it safe...
21440 self.GetBooleanArrayRegion_into_slice(array, start, data.as_mut_slice());
21441 if self.ExceptionCheck() {
21442 return Vec::new();
21443 }
21444
21445 return jboolean::narrow_vec(data);
21446 }
21447
21448 //Negative len
21449 let mut sentinel_buffer = [jboolean::FALSE];
21450 self.GetBooleanArrayRegion(array, start, len.min(-1), sentinel_buffer.as_mut_ptr());
21451 Vec::new()
21452 }
21453 }
21454
21455 ///
21456 /// Copies data from the jbooleanArray `array` starting from the given `start` index into the memory pointed to by `buf`.
21457 ///
21458 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_PrimitiveType_ArrayRegion_routines>
21459 ///
21460 /// # Arguments
21461 /// * `array` - handle to a Java jbooleanArray
21462 /// * `start` - the index of the first element to copy in the Java jbooleanArray
21463 /// * `len` - amount of data to be copied
21464 /// * `buf` - pointer to memory where the data should be copied to
21465 ///
21466 /// # Throws Java Exception:
21467 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the `array`.
21468 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
21469 ///
21470 /// It is JVM implementation specific what is written into `buf` if this function throws an exception.
21471 /// * Data partially written
21472 /// * No data written
21473 ///
21474 /// # Panics
21475 /// if asserts feature is enabled and UB was detected
21476 ///
21477 /// # Safety
21478 /// Current thread must not be detached from JNI.
21479 ///
21480 /// Current thread must not be currently throwing an exception.
21481 ///
21482 /// Current thread does not hold a critical reference.
21483 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21484 ///
21485 /// `array` must be a valid non-null reference to a jbooleanArray.
21486 /// `buf` must be valid non-null pointer to memory with enough capacity to store `len` bytes.
21487 ///
21488 /// # Example
21489 /// ```rust
21490 /// use jni_simple::{*};
21491 ///
21492 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
21493 /// array: jbooleanArray, chunk_buffer: &mut [jboolean], chunk_offset: usize) -> bool {
21494 /// if array.is_null() {
21495 /// panic!("Java Array is null")
21496 /// }
21497 /// env.GetBooleanArrayRegion(array, chunk_offset as jsize, chunk_buffer.len() as jsize, chunk_buffer.as_mut_ptr());
21498 /// if env.ExceptionCheck() {
21499 /// //ArrayIndexOutOfBoundsException
21500 /// env.ExceptionClear();
21501 /// return false;
21502 /// }
21503 /// true
21504 /// }
21505 /// ```
21506 ///
21507 pub unsafe fn GetBooleanArrayRegion(&self, array: jbooleanArray, start: jsize, len: jsize, buf: *mut jboolean) {
21508 unsafe {
21509 #[cfg(feature = "asserts")]
21510 {
21511 self.check_not_critical("GetBooleanArrayRegion");
21512 self.check_no_exception("GetBooleanArrayRegion");
21513 assert!(!array.is_null(), "GetBooleanArrayRegion jarray must not be null");
21514 assert!(!buf.is_null(), "GetBooleanArrayRegion buf must not be null");
21515 }
21516 self.jni::<extern "system" fn(JNIEnvVTable, jbooleanArray, jsize, jsize, *mut jboolean)>(199)(self.vtable, array, start, len, buf);
21517 }
21518 }
21519
21520 ///
21521 /// Copies data from the jbyteArray `array` starting from the given `start` index into the memory pointed to by `buf`.
21522 ///
21523 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_PrimitiveType_ArrayRegion_routines>
21524 ///
21525 /// # Arguments
21526 /// * `array` - handle to a Java jbyteArray
21527 /// * `start` - the index of the first element to copy in the Java jbyteArray
21528 /// * `len` - amount of data to be copied
21529 /// * `buf` - pointer to memory where the data should be copied to
21530 ///
21531 /// # Throws Java Exception:
21532 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the `array`.
21533 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
21534 ///
21535 /// It is JVM implementation specific what is written into `buf` if this function throws an exception.
21536 /// * Data partially written
21537 /// * No data written
21538 ///
21539 /// # Panics
21540 /// if asserts feature is enabled and UB was detected
21541 ///
21542 /// # Safety
21543 /// Current thread must not be detached from JNI.
21544 ///
21545 /// Current thread must not be currently throwing an exception.
21546 ///
21547 /// Current thread does not hold a critical reference.
21548 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21549 ///
21550 /// `array` must be a valid non-null reference to a jbyteArray.
21551 /// `buf` must be valid non-null pointer to memory with enough capacity to store `len` bytes.
21552 ///
21553 /// # Example
21554 /// ```rust
21555 /// use jni_simple::{*};
21556 ///
21557 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
21558 /// array: jbyteArray, chunk_buffer: &mut [i8], chunk_offset: usize) -> bool {
21559 /// if array.is_null() {
21560 /// panic!("Java Array is null")
21561 /// }
21562 ///
21563 /// env.GetByteArrayRegion(array, chunk_offset as jsize, chunk_buffer.len() as jsize, chunk_buffer.as_mut_ptr());
21564 /// if env.ExceptionCheck() {
21565 /// //ArrayIndexOutOfBoundsException
21566 /// env.ExceptionClear();
21567 /// return false;
21568 /// }
21569 /// true
21570 /// }
21571 /// ```
21572 ///
21573 pub unsafe fn GetByteArrayRegion(&self, array: jbyteArray, start: jsize, len: jsize, buf: *mut jbyte) {
21574 unsafe {
21575 #[cfg(feature = "asserts")]
21576 {
21577 self.check_not_critical("GetByteArrayRegion");
21578 self.check_no_exception("GetByteArrayRegion");
21579 assert!(!array.is_null(), "GetByteArrayRegion jarray must not be null");
21580 assert!(!buf.is_null(), "GetByteArrayRegion buf must not be null");
21581 }
21582
21583 self.jni::<extern "system" fn(JNIEnvVTable, jbooleanArray, jsize, jsize, *mut jbyte)>(200)(self.vtable, array, start, len, buf);
21584 }
21585 }
21586
21587 ///
21588 /// Copies data from the jbyteArray `array` starting from the given `start` index into the slice `buf`.
21589 ///
21590 /// # Arguments
21591 /// * `array` - handle to a Java jbyteArray.
21592 /// * `start` - the index of the first element to copy in the Java jbyteArray
21593 /// * `buf` - the slice to copy data into
21594 ///
21595 /// # Throws Java Exception:
21596 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
21597 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
21598 ///
21599 /// It is JVM implementation specific what is stored inside buf if this function throws an exception.
21600 /// * Data partially written
21601 /// * No data written
21602 ///
21603 /// # Panics
21604 /// if asserts feature is enabled and UB was detected
21605 /// if the `buf.len()` is larger than `jsize::MAX`
21606 ///
21607 /// # Safety
21608 /// Current thread must not be detached from JNI.
21609 ///
21610 /// Current thread must not be currently throwing an exception.
21611 ///
21612 /// Current thread does not hold a critical reference.
21613 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21614 ///
21615 /// `array` must be a valid non-null reference to a jbyteArray.
21616 ///
21617 /// # Example
21618 /// ```rust
21619 /// use jni_simple::{*};
21620 ///
21621 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
21622 /// array: jbyteArray, chunk_buffer: &mut [jbyte], chunk_offset: usize) -> bool {
21623 /// if array.is_null() {
21624 /// panic!("Java Array is null")
21625 /// }
21626 ///
21627 /// env.GetByteArrayRegion_into_slice(array, chunk_offset as jsize, chunk_buffer);
21628 /// if env.ExceptionCheck() {
21629 /// //ArrayIndexOutOfBoundsException
21630 /// env.ExceptionClear();
21631 /// return false;
21632 /// }
21633 /// true
21634 /// }
21635 /// ```
21636 ///
21637 pub unsafe fn GetByteArrayRegion_into_slice(&self, array: jbyteArray, start: jsize, buf: &mut [jbyte]) {
21638 unsafe {
21639 self.GetByteArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_mut_ptr());
21640 }
21641 }
21642
21643 ///
21644 /// Copies data from the slice `buf` into the jbyteArray `array` starting at the given `start` index.
21645 ///
21646 /// # Arguments
21647 /// * `array` - handle to a Java jbyteArray.
21648 /// * `start` - the index where the first element should be coped into in the Java jybteArray
21649 /// * `buf` - the slice where data is copied from
21650 ///
21651 /// # Throws Java Exception:
21652 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
21653 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
21654 ///
21655 /// It is JVM implementation specific what is stored inside `array` if this function throws an exception.
21656 /// * Data partially written
21657 /// * No data written
21658 ///
21659 /// # Panics
21660 /// if asserts feature is enabled and UB was detected
21661 ///
21662 /// # Safety
21663 /// Current thread must not be detached from JNI.
21664 ///
21665 /// Current thread must not be currently throwing an exception.
21666 ///
21667 /// Current thread does not hold a critical reference.
21668 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21669 ///
21670 /// `array` must be a valid non-null reference to a jbyteArray.
21671 ///
21672 /// # Example
21673 /// ```rust
21674 /// use jni_simple::{*};
21675 ///
21676 /// unsafe fn copy_chunk_from_rust_to_java(env: JNIEnv,
21677 /// array: jbyteArray, chunk_buffer: &[jbyte], chunk_offset: usize) -> bool {
21678 /// if array.is_null() {
21679 /// panic!("Java Array is null")
21680 /// }
21681 ///
21682 /// env.SetByteArrayRegion_from_slice(array, chunk_offset as jsize, chunk_buffer);
21683 /// if env.ExceptionCheck() {
21684 /// //ArrayIndexOutOfBoundsException
21685 /// env.ExceptionClear();
21686 /// return false;
21687 /// }
21688 /// true
21689 /// }
21690 /// ```
21691 ///
21692 pub unsafe fn SetByteArrayRegion_from_slice(&self, array: jbyteArray, start: jsize, buf: &[jbyte]) {
21693 unsafe {
21694 self.SetByteArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_ptr());
21695 }
21696 }
21697
21698 ///
21699 /// Copies data from a Java jbyteArray `array` into a new `Vec<jbyte>`
21700 ///
21701 /// # Arguments
21702 /// * `array` - handle to a Java jbyteArray.
21703 /// * `start` - the index of the first element to copy in the Java jbyteArray
21704 /// * `len` - the amount of data that should be copied. If `None` then all remaining elements in the array are copied.
21705 ///
21706 /// # Returns:
21707 /// a new `Vec<jbyte>` that contains the copied data.
21708 ///
21709 /// # Returns empty Vec:
21710 /// * When the array in fact was empty or len was zero.
21711 /// * When this function throws a Java Exception.
21712 ///
21713 /// # Throws Java Exception:
21714 /// * `ArrayIndexOutOfBoundsException` - if `len` is negative.
21715 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the array.
21716 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative.
21717 /// * `ArrayIndexOutOfBoundsException` - if `start` is larget than `env.GetArrayLength(array)`.
21718 /// * `ArrayIndexOutOfBoundsException` - if `start` equals env.GetArrayLength(array) and `len` is larger than 0.
21719 ///
21720 /// # Panics
21721 /// if asserts feature is enabled and UB was detected
21722 ///
21723 /// # Safety
21724 /// Current thread must not be detached from JNI.
21725 ///
21726 /// Current thread must not be currently throwing an exception.
21727 ///
21728 /// Current thread does not hold a critical reference.
21729 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21730 ///
21731 /// `array` must be a valid non-null reference to a jbyteArray.
21732 ///
21733 /// # Example
21734 /// ```rust
21735 /// use jni_simple::{*};
21736 ///
21737 /// unsafe fn copy_entire_java_array_to_rust(env: JNIEnv, array: jbyteArray) -> Vec<jbyte> {
21738 /// if array.is_null() {
21739 /// panic!("Java Array is null")
21740 /// }
21741 /// env.GetByteArrayRegion_as_vec(array, 0, None)
21742 /// }
21743 /// ```
21744 ///
21745 pub unsafe fn GetByteArrayRegion_as_vec(&self, array: jbyteArray, start: jsize, len: Option<jsize>) -> Vec<jbyte> {
21746 unsafe {
21747 let len = len.unwrap_or_else(|| self.GetArrayLength(array).saturating_sub(start.max(0)).max(0));
21748 if let Ok(len) = usize::try_from(len) {
21749 let mut data = vec![0i8; len]; //We could un-init this, but better play it safe...
21750 self.GetByteArrayRegion_into_slice(array, start, data.as_mut_slice());
21751 if self.ExceptionCheck() {
21752 return Vec::new();
21753 }
21754 return data;
21755 }
21756
21757 //Negative len
21758 let mut sentinel_buffer = [0];
21759 self.GetByteArrayRegion(array, start, len.min(-1), sentinel_buffer.as_mut_ptr());
21760 Vec::new()
21761 }
21762 }
21763
21764 ///
21765 /// Copies data from the jcharArray `array` starting from the given `start` index into the memory pointed to by `buf`.
21766 ///
21767 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_PrimitiveType_ArrayRegion_routines>
21768 ///
21769 /// # Arguments
21770 /// * `array` - handle to a Java jcharArray
21771 /// * `start` - the index of the first element to copy in the Java jcharArray
21772 /// * `len` - amount of data to be copied
21773 /// * `buf` - pointer to memory where the data should be copied to
21774 ///
21775 /// # Throws Java Exception:
21776 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the `array`.
21777 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
21778 ///
21779 /// It is JVM implementation specific what is written into `buf` if this function throws an exception.
21780 /// * Data partially written
21781 /// * No data written
21782 ///
21783 /// # Panics
21784 /// if asserts feature is enabled and UB was detected
21785 ///
21786 /// # Safety
21787 /// Current thread must not be detached from JNI.
21788 ///
21789 /// Current thread must not be currently throwing an exception.
21790 ///
21791 /// Current thread does not hold a critical reference.
21792 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21793 ///
21794 /// `array` must be a valid non-null reference to a jcharArray.
21795 /// `buf` must be valid non-null pointer to memory with enough capacity and proper alignment to store `len` jchar's.
21796 ///
21797 /// # Example
21798 /// ```rust
21799 /// use jni_simple::{*};
21800 ///
21801 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
21802 /// array: jcharArray, chunk_buffer: &mut [jchar], chunk_offset: usize) -> bool {
21803 /// if array.is_null() {
21804 /// panic!("Java Array is null")
21805 /// }
21806 ///
21807 /// env.GetCharArrayRegion(array, chunk_offset as jsize, chunk_buffer.len() as jsize, chunk_buffer.as_mut_ptr());
21808 /// if env.ExceptionCheck() {
21809 /// //ArrayIndexOutOfBoundsException
21810 /// env.ExceptionClear();
21811 /// return false;
21812 /// }
21813 /// true
21814 /// }
21815 /// ```
21816 ///
21817 pub unsafe fn GetCharArrayRegion(&self, array: jcharArray, start: jsize, len: jsize, buf: *mut jchar) {
21818 unsafe {
21819 #[cfg(feature = "asserts")]
21820 {
21821 self.check_not_critical("GetCharArrayRegion");
21822 self.check_no_exception("GetCharArrayRegion");
21823 assert!(!array.is_null(), "GetCharArrayRegion jarray must not be null");
21824 assert!(!buf.is_null(), "GetCharArrayRegion buf must not be null");
21825 assert_eq!(0, buf.align_offset(align_of::<jchar>()), "GetCharArrayRegion buf pointer is not aligned");
21826 }
21827
21828 self.jni::<extern "system" fn(JNIEnvVTable, jbooleanArray, jsize, jsize, *mut jchar)>(201)(self.vtable, array, start, len, buf);
21829 }
21830 }
21831
21832 ///
21833 /// Copies data from the jcharArray `array` starting from the given `start` index into the slice `buf`.
21834 ///
21835 /// # Arguments
21836 /// * `array` - handle to a Java jcharArray.
21837 /// * `start` - the index of the first element to copy in the Java jcharArray
21838 /// * `buf` - the slice to copy data into
21839 ///
21840 /// # Throws Java Exception:
21841 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
21842 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
21843 ///
21844 /// It is JVM implementation specific what is stored inside buf if this function throws an exception.
21845 /// * Data partially written
21846 /// * No data written
21847 ///
21848 /// # Panics
21849 /// if asserts feature is enabled and UB was detected
21850 /// if the `buf.len()` is larger than `jsize::MAX`
21851 ///
21852 /// # Safety
21853 /// Current thread must not be detached from JNI.
21854 ///
21855 /// Current thread must not be currently throwing an exception.
21856 ///
21857 /// Current thread does not hold a critical reference.
21858 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21859 ///
21860 /// `array` must be a valid non-null reference to a jcharArray.
21861 ///
21862 /// # Example
21863 /// ```rust
21864 /// use jni_simple::{*};
21865 ///
21866 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
21867 /// array: jcharArray, chunk_buffer: &mut [jchar], chunk_offset: usize) -> bool {
21868 /// if array.is_null() {
21869 /// panic!("Java Array is null")
21870 /// }
21871 ///
21872 /// env.GetCharArrayRegion_into_slice(array, chunk_offset as jsize, chunk_buffer);
21873 /// if env.ExceptionCheck() {
21874 /// //ArrayIndexOutOfBoundsException
21875 /// env.ExceptionClear();
21876 /// return false;
21877 /// }
21878 /// true
21879 /// }
21880 /// ```
21881 ///
21882 pub unsafe fn GetCharArrayRegion_into_slice(&self, array: jcharArray, start: jsize, buf: &mut [jchar]) {
21883 unsafe {
21884 self.GetCharArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_mut_ptr());
21885 }
21886 }
21887
21888 ///
21889 /// Copies data from the slice `buf` into the jcharArray `array` starting at the given `start` index.
21890 ///
21891 /// # Arguments
21892 /// * `array` - handle to a Java jcharArray.
21893 /// * `start` - the index where the first element should be coped into in the Java jcharArray
21894 /// * `buf` - the slice where data is copied from
21895 ///
21896 /// # Throws Java Exception:
21897 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
21898 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
21899 ///
21900 /// It is JVM implementation specific what is stored inside `array` if this function throws an exception.
21901 /// * Data partially written
21902 /// * No data written
21903 ///
21904 /// # Panics
21905 /// if asserts feature is enabled and UB was detected
21906 ///
21907 /// # Safety
21908 /// Current thread must not be detached from JNI.
21909 ///
21910 /// Current thread must not be currently throwing an exception.
21911 ///
21912 /// Current thread does not hold a critical reference.
21913 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21914 ///
21915 /// `array` must be a valid non-null reference to a jcharArray.
21916 ///
21917 /// # Example
21918 /// ```rust
21919 /// use jni_simple::{*};
21920 ///
21921 /// unsafe fn copy_chunk_from_rust_to_java(env: JNIEnv,
21922 /// array: jcharArray, chunk_buffer: &[u16], chunk_offset: usize) -> bool {
21923 /// if array.is_null() {
21924 /// panic!("Java Array is null")
21925 /// }
21926 ///
21927 /// env.SetCharArrayRegion_from_slice(array, chunk_offset as jsize, chunk_buffer);
21928 /// if env.ExceptionCheck() {
21929 /// //ArrayIndexOutOfBoundsException
21930 /// env.ExceptionClear();
21931 /// return false;
21932 /// }
21933 /// true
21934 /// }
21935 /// ```
21936 ///
21937 pub unsafe fn SetCharArrayRegion_from_slice(&self, array: jcharArray, start: jsize, buf: &[jchar]) {
21938 unsafe {
21939 self.SetCharArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_ptr());
21940 }
21941 }
21942
21943 ///
21944 /// Copies data from a Java jcharArray `array` into a new `Vec<jchar>`
21945 ///
21946 /// # Arguments
21947 /// * `array` - handle to a Java jcharArray.
21948 /// * `start` - the index of the first element to copy in the Java jcharArray
21949 /// * `len` - the amount of data that should be copied. If `None` then all remaining elements in the array are copied.
21950 ///
21951 /// # Returns:
21952 /// a new `Vec<jchar>` that contains the copied data.
21953 ///
21954 /// # Returns empty Vec:
21955 /// * When the array in fact was empty or len was zero.
21956 /// * When this function throws a Java Exception.
21957 ///
21958 /// # Throws Java Exception:
21959 /// * `ArrayIndexOutOfBoundsException` - if `len` is negative.
21960 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the array.
21961 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative.
21962 /// * `ArrayIndexOutOfBoundsException` - if `start` is larget than `env.GetArrayLength(array)`.
21963 /// * `ArrayIndexOutOfBoundsException` - if `start` equals env.GetArrayLength(array) and `len` is larger than 0.
21964 ///
21965 /// # Panics
21966 /// if asserts feature is enabled and UB was detected
21967 ///
21968 /// # Safety
21969 /// Current thread must not be detached from JNI.
21970 ///
21971 /// Current thread must not be currently throwing an exception.
21972 ///
21973 /// Current thread does not hold a critical reference.
21974 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
21975 ///
21976 /// `array` must be a valid non-null reference to a jcharArray.
21977 ///
21978 /// # Example
21979 /// ```rust
21980 /// use jni_simple::{*};
21981 ///
21982 /// unsafe fn copy_entire_java_array_to_rust(env: JNIEnv, array: jcharArray) -> Vec<jchar> {
21983 /// if array.is_null() {
21984 /// panic!("Java Array is null")
21985 /// }
21986 /// env.GetCharArrayRegion_as_vec(array, 0, None)
21987 /// }
21988 /// ```
21989 ///
21990 pub unsafe fn GetCharArrayRegion_as_vec(&self, array: jcharArray, start: jsize, len: Option<jsize>) -> Vec<jchar> {
21991 unsafe {
21992 let len = len.unwrap_or_else(|| self.GetArrayLength(array).saturating_sub(start.max(0)).max(0));
21993 if let Ok(len) = usize::try_from(len) {
21994 let mut data = vec![0u16; len]; //We could un-init this, but better play it safe...
21995 self.GetCharArrayRegion_into_slice(array, start, data.as_mut_slice());
21996 if self.ExceptionCheck() {
21997 return Vec::new();
21998 }
21999 return data;
22000 }
22001
22002 //Negative len
22003 let mut sentinel_buffer = [0];
22004 self.GetCharArrayRegion(array, start, len.min(-1), sentinel_buffer.as_mut_ptr());
22005 Vec::new()
22006 }
22007 }
22008
22009 ///
22010 /// Copies data from the jshortArray `array` starting from the given `start` index into the memory pointed to by `buf`.
22011 ///
22012 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_PrimitiveType_ArrayRegion_routines>
22013 ///
22014 /// # Arguments
22015 /// * `array` - handle to a Java jshortArray
22016 /// * `start` - the index of the first element to copy in the Java jshortArray
22017 /// * `len` - amount of data to be copied
22018 /// * `buf` - pointer to memory where the data should be copied to
22019 ///
22020 /// # Throws Java Exception:
22021 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the `array`.
22022 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22023 ///
22024 /// It is JVM implementation specific what is written into `buf` if this function throws an exception.
22025 /// * Data partially written
22026 /// * No data written
22027 ///
22028 /// # Panics
22029 /// if asserts feature is enabled and UB was detected
22030 ///
22031 /// # Safety
22032 /// Current thread must not be detached from JNI.
22033 ///
22034 /// Current thread must not be currently throwing an exception.
22035 ///
22036 /// Current thread does not hold a critical reference.
22037 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22038 ///
22039 /// `array` must be a valid non-null reference to a jshortArray.
22040 /// `buf` must be valid non-null pointer to memory with enough capacity and proper alignment to store `len` jshort's.
22041 ///
22042 /// # Example
22043 /// ```rust
22044 /// use jni_simple::{*};
22045 ///
22046 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
22047 /// array: jshortArray, chunk_buffer: &mut [jshort], chunk_offset: usize) -> bool {
22048 /// if array.is_null() {
22049 /// panic!("Java Array is null")
22050 /// }
22051 ///
22052 /// env.GetShortArrayRegion(array, chunk_offset as jsize, chunk_buffer.len() as jsize, chunk_buffer.as_mut_ptr());
22053 /// if env.ExceptionCheck() {
22054 /// //ArrayIndexOutOfBoundsException
22055 /// env.ExceptionClear();
22056 /// return false;
22057 /// }
22058 /// true
22059 /// }
22060 /// ```
22061 ///
22062 pub unsafe fn GetShortArrayRegion(&self, array: jshortArray, start: jsize, len: jsize, buf: *mut jshort) {
22063 unsafe {
22064 #[cfg(feature = "asserts")]
22065 {
22066 self.check_not_critical("GetShortArrayRegion");
22067 self.check_no_exception("GetShortArrayRegion");
22068 assert!(!array.is_null(), "GetShortArrayRegion jarray must not be null");
22069 assert!(!buf.is_null(), "GetShortArrayRegion buf must not be null");
22070 assert_eq!(0, buf.align_offset(align_of::<jshort>()), "GetShortArrayRegion buf pointer is not aligned");
22071 }
22072
22073 self.jni::<extern "system" fn(JNIEnvVTable, jbooleanArray, jsize, jsize, *mut jshort)>(202)(self.vtable, array, start, len, buf);
22074 }
22075 }
22076
22077 ///
22078 /// Copies data from the jshortArray `array` starting from the given `start` index into the slice `buf`.
22079 ///
22080 /// # Arguments
22081 /// * `array` - handle to a Java jshortArray.
22082 /// * `start` - the index of the first element to copy in the Java jshortArray
22083 /// * `buf` - the slice to copy data into
22084 ///
22085 /// # Throws Java Exception:
22086 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
22087 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22088 ///
22089 /// It is JVM implementation specific what is stored inside buf if this function throws an exception.
22090 /// * Data partially written
22091 /// * No data written
22092 ///
22093 /// # Panics
22094 /// if asserts feature is enabled and UB was detected
22095 /// if the `buf.len()` is larger than `jsize::MAX`
22096 ///
22097 /// # Safety
22098 /// Current thread must not be detached from JNI.
22099 ///
22100 /// Current thread must not be currently throwing an exception.
22101 ///
22102 /// Current thread does not hold a critical reference.
22103 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22104 ///
22105 /// `array` must be a valid non-null reference to a jshortArray.
22106 ///
22107 /// # Example
22108 /// ```rust
22109 /// use jni_simple::{*};
22110 ///
22111 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
22112 /// array: jshortArray, chunk_buffer: &mut [jshort], chunk_offset: usize) -> bool {
22113 /// if array.is_null() {
22114 /// panic!("Java Array is null")
22115 /// }
22116 ///
22117 /// env.GetShortArrayRegion_into_slice(array, chunk_offset as jsize, chunk_buffer);
22118 /// if env.ExceptionCheck() {
22119 /// //ArrayIndexOutOfBoundsException
22120 /// env.ExceptionClear();
22121 /// return false;
22122 /// }
22123 /// true
22124 /// }
22125 /// ```
22126 ///
22127 pub unsafe fn GetShortArrayRegion_into_slice(&self, array: jshortArray, start: jsize, buf: &mut [jshort]) {
22128 unsafe {
22129 self.GetShortArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_mut_ptr());
22130 }
22131 }
22132
22133 ///
22134 /// Copies data from the slice `buf` into the jshortArray `array` starting at the given `start` index.
22135 ///
22136 /// # Arguments
22137 /// * `array` - handle to a Java jshortArray.
22138 /// * `start` - the index where the first element should be coped into in the Java jshortArray
22139 /// * `buf` - the slice where data is copied from
22140 ///
22141 /// # Throws Java Exception:
22142 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
22143 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22144 ///
22145 /// It is JVM implementation specific what is stored inside `array` if this function throws an exception.
22146 /// * Data partially written
22147 /// * No data written
22148 ///
22149 /// # Panics
22150 /// if asserts feature is enabled and UB was detected
22151 ///
22152 /// # Safety
22153 /// Current thread must not be detached from JNI.
22154 ///
22155 /// Current thread must not be currently throwing an exception.
22156 ///
22157 /// Current thread does not hold a critical reference.
22158 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22159 ///
22160 /// `array` must be a valid non-null reference to a jshortArray.
22161 ///
22162 /// # Example
22163 /// ```rust
22164 /// use jni_simple::{*};
22165 ///
22166 /// unsafe fn copy_chunk_from_rust_to_java(env: JNIEnv,
22167 /// array: jshortArray, chunk_buffer: &[jshort], chunk_offset: usize) -> bool {
22168 /// if array.is_null() {
22169 /// panic!("Java Array is null")
22170 /// }
22171 ///
22172 /// env.SetShortArrayRegion_from_slice(array, chunk_offset as jsize, chunk_buffer);
22173 /// if env.ExceptionCheck() {
22174 /// //ArrayIndexOutOfBoundsException
22175 /// env.ExceptionClear();
22176 /// return false;
22177 /// }
22178 /// true
22179 /// }
22180 /// ```
22181 ///
22182 pub unsafe fn SetShortArrayRegion_from_slice(&self, array: jshortArray, start: jsize, buf: &[jshort]) {
22183 unsafe {
22184 self.SetShortArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_ptr());
22185 }
22186 }
22187
22188 ///
22189 /// Copies data from a Java jshortArray `array` into a new `Vec<jshort>`
22190 ///
22191 /// # Arguments
22192 /// * `array` - handle to a Java jshortArray.
22193 /// * `start` - the index of the first element to copy in the Java jshortArray
22194 /// * `len` - the amount of data that should be copied. If `None` then all remaining elements in the array are copied.
22195 ///
22196 /// # Returns:
22197 /// a new `Vec<jshort>` that contains the copied data.
22198 ///
22199 /// # Returns empty Vec:
22200 /// * When the array in fact was empty or len was zero.
22201 /// * When this function throws a Java Exception.
22202 ///
22203 /// # Throws Java Exception:
22204 /// * `ArrayIndexOutOfBoundsException` - if `len` is negative.
22205 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the array.
22206 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative.
22207 /// * `ArrayIndexOutOfBoundsException` - if `start` is larget than `env.GetArrayLength(array)`.
22208 /// * `ArrayIndexOutOfBoundsException` - if `start` equals env.GetArrayLength(array) and `len` is larger than 0.
22209 ///
22210 /// # Panics
22211 /// if asserts feature is enabled and UB was detected
22212 ///
22213 /// # Safety
22214 /// Current thread must not be detached from JNI.
22215 ///
22216 /// Current thread must not be currently throwing an exception.
22217 ///
22218 /// Current thread does not hold a critical reference.
22219 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22220 ///
22221 /// `array` must be a valid non-null reference to a jshortArray.
22222 ///
22223 /// # Example
22224 /// ```rust
22225 /// use jni_simple::{*};
22226 ///
22227 /// unsafe fn copy_entire_java_array_to_rust(env: JNIEnv, array: jshortArray) -> Vec<jshort> {
22228 /// if array.is_null() {
22229 /// panic!("Java Array is null")
22230 /// }
22231 /// env.GetShortArrayRegion_as_vec(array, 0, None)
22232 /// }
22233 /// ```
22234 ///
22235 pub unsafe fn GetShortArrayRegion_as_vec(&self, array: jshortArray, start: jsize, len: Option<jsize>) -> Vec<jshort> {
22236 unsafe {
22237 let len = len.unwrap_or_else(|| self.GetArrayLength(array).saturating_sub(start.max(0)).max(0));
22238 if let Ok(len) = usize::try_from(len) {
22239 let mut data = vec![0i16; len]; //We could un-init this, but better play it safe...
22240 self.GetShortArrayRegion_into_slice(array, start, data.as_mut_slice());
22241 if self.ExceptionCheck() {
22242 return Vec::new();
22243 }
22244 return data;
22245 }
22246
22247 //Negative len
22248 let mut sentinel_buffer = [0];
22249 self.GetShortArrayRegion(array, start, len.min(-1), sentinel_buffer.as_mut_ptr());
22250 Vec::new()
22251 }
22252 }
22253
22254 ///
22255 /// Copies data from the jintArray `array` starting from the given `start` index into the memory pointed to by `buf`.
22256 ///
22257 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_PrimitiveType_ArrayRegion_routines>
22258 ///
22259 /// # Arguments
22260 /// * `array` - handle to a Java jintArray
22261 /// * `start` - the index of the first element to copy in the Java jintArray
22262 /// * `len` - amount of data to be copied
22263 /// * `buf` - pointer to memory where the data should be copied to
22264 ///
22265 /// # Throws Java Exception:
22266 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the `array`.
22267 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22268 ///
22269 /// It is JVM implementation specific what is written into `buf` if this function throws an exception.
22270 /// * Data partially written
22271 /// * No data written
22272 ///
22273 /// # Panics
22274 /// if asserts feature is enabled and UB was detected
22275 ///
22276 /// # Safety
22277 /// Current thread must not be detached from JNI.
22278 ///
22279 /// Current thread must not be currently throwing an exception.
22280 ///
22281 /// Current thread does not hold a critical reference.
22282 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22283 ///
22284 /// `array` must be a valid non-null reference to a jintArray.
22285 /// `buf` must be valid non-null pointer to memory with enough capacity and proper alignment to store `len` jint's.
22286 ///
22287 /// # Example
22288 /// ```rust
22289 /// use jni_simple::{*};
22290 ///
22291 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
22292 /// array: jintArray, chunk_buffer: &mut [jint], chunk_offset: usize) -> bool {
22293 /// if array.is_null() {
22294 /// panic!("Java Array is null")
22295 /// }
22296 ///
22297 /// env.GetIntArrayRegion(array, chunk_offset as jsize, chunk_buffer.len() as jsize, chunk_buffer.as_mut_ptr());
22298 /// if env.ExceptionCheck() {
22299 /// //ArrayIndexOutOfBoundsException
22300 /// env.ExceptionClear();
22301 /// return false;
22302 /// }
22303 /// true
22304 /// }
22305 /// ```
22306 ///
22307 pub unsafe fn GetIntArrayRegion(&self, array: jintArray, start: jsize, len: jsize, buf: *mut jint) {
22308 unsafe {
22309 #[cfg(feature = "asserts")]
22310 {
22311 self.check_not_critical("GetIntArrayRegion");
22312 self.check_no_exception("GetIntArrayRegion");
22313 assert!(!array.is_null(), "GetIntArrayRegion jarray must not be null");
22314 assert!(!buf.is_null(), "GetIntArrayRegion buf must not be null");
22315 assert_eq!(0, buf.align_offset(align_of::<jint>()), "GetIntArrayRegion buf pointer is not aligned");
22316 }
22317
22318 self.jni::<extern "system" fn(JNIEnvVTable, jbooleanArray, jsize, jsize, *mut jint)>(203)(self.vtable, array, start, len, buf);
22319 }
22320 }
22321
22322 ///
22323 /// Copies data from the jintArray `array` starting from the given `start` index into the slice `buf`.
22324 ///
22325 /// # Arguments
22326 /// * `array` - handle to a Java jintArray.
22327 /// * `start` - the index of the first element to copy in the Java jintArray
22328 /// * `buf` - the slice to copy data into
22329 ///
22330 /// # Throws Java Exception:
22331 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
22332 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22333 ///
22334 /// It is JVM implementation specific what is stored inside buf if this function throws an exception.
22335 /// * Data partially written
22336 /// * No data written
22337 ///
22338 /// # Panics
22339 /// if asserts feature is enabled and UB was detected
22340 /// if the `buf.len()` is larger than `jsize::MAX`
22341 ///
22342 /// # Safety
22343 /// Current thread must not be detached from JNI.
22344 ///
22345 /// Current thread must not be currently throwing an exception.
22346 ///
22347 /// Current thread does not hold a critical reference.
22348 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22349 ///
22350 /// `array` must be a valid non-null reference to a jintArray.
22351 ///
22352 /// # Example
22353 /// ```rust
22354 /// use jni_simple::{*};
22355 ///
22356 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
22357 /// array: jintArray, chunk_buffer: &mut [jint], chunk_offset: usize) -> bool {
22358 /// if array.is_null() {
22359 /// panic!("Java Array is null")
22360 /// }
22361 ///
22362 /// env.GetIntArrayRegion_into_slice(array, chunk_offset as jsize, chunk_buffer);
22363 /// if env.ExceptionCheck() {
22364 /// //ArrayIndexOutOfBoundsException
22365 /// env.ExceptionClear();
22366 /// return false;
22367 /// }
22368 /// true
22369 /// }
22370 /// ```
22371 ///
22372 pub unsafe fn GetIntArrayRegion_into_slice(&self, array: jshortArray, start: jsize, buf: &mut [jint]) {
22373 unsafe {
22374 self.GetIntArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_mut_ptr());
22375 }
22376 }
22377
22378 ///
22379 /// Copies data from the slice `buf` into the jintArray `array` starting at the given `start` index.
22380 ///
22381 /// # Arguments
22382 /// * `array` - handle to a Java jintArray.
22383 /// * `start` - the index where the first element should be coped into in the Java jintArray
22384 /// * `buf` - the slice where data is copied from
22385 ///
22386 /// # Throws Java Exception:
22387 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
22388 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22389 ///
22390 /// It is JVM implementation specific what is stored inside `array` if this function throws an exception.
22391 /// * Data partially written
22392 /// * No data written
22393 ///
22394 /// # Panics
22395 /// if asserts feature is enabled and UB was detected
22396 ///
22397 /// # Safety
22398 /// Current thread must not be detached from JNI.
22399 ///
22400 /// Current thread must not be currently throwing an exception.
22401 ///
22402 /// Current thread does not hold a critical reference.
22403 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22404 ///
22405 /// `array` must be a valid non-null reference to a jintArray.
22406 ///
22407 /// # Example
22408 /// ```rust
22409 /// use jni_simple::{*};
22410 ///
22411 /// unsafe fn copy_chunk_from_rust_to_java(env: JNIEnv,
22412 /// array: jintArray, chunk_buffer: &[jint], chunk_offset: usize) -> bool {
22413 /// if array.is_null() {
22414 /// panic!("Java Array is null")
22415 /// }
22416 ///
22417 /// env.SetIntArrayRegion_from_slice(array, chunk_offset as jsize, chunk_buffer);
22418 /// if env.ExceptionCheck() {
22419 /// //ArrayIndexOutOfBoundsException
22420 /// env.ExceptionClear();
22421 /// return false;
22422 /// }
22423 /// true
22424 /// }
22425 /// ```
22426 ///
22427 pub unsafe fn SetIntArrayRegion_from_slice(&self, array: jintArray, start: jsize, buf: &[jint]) {
22428 unsafe {
22429 self.SetIntArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_ptr());
22430 }
22431 }
22432
22433 ///
22434 /// Copies data from a Java jintArray `array` into a new `Vec<jint>`
22435 ///
22436 /// # Arguments
22437 /// * `array` - handle to a Java jintArray.
22438 /// * `start` - the index of the first element to copy in the Java jintArray
22439 /// * `len` - the amount of data that should be copied. If `None` then all remaining elements in the array are copied.
22440 ///
22441 /// # Returns:
22442 /// a new `Vec<jint>` that contains the copied data.
22443 ///
22444 /// # Returns empty Vec:
22445 /// * When the array in fact was empty or len was zero.
22446 /// * When this function throws a Java Exception.
22447 ///
22448 /// # Throws Java Exception:
22449 /// * `ArrayIndexOutOfBoundsException` - if `len` is negative.
22450 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the array.
22451 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative.
22452 /// * `ArrayIndexOutOfBoundsException` - if `start` is larget than `env.GetArrayLength(array)`.
22453 /// * `ArrayIndexOutOfBoundsException` - if `start` equals env.GetArrayLength(array) and `len` is larger than 0.
22454 ///
22455 /// # Panics
22456 /// if asserts feature is enabled and UB was detected
22457 ///
22458 /// # Safety
22459 /// Current thread must not be detached from JNI.
22460 ///
22461 /// Current thread must not be currently throwing an exception.
22462 ///
22463 /// Current thread does not hold a critical reference.
22464 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22465 ///
22466 /// `array` must be a valid non-null reference to a jintArray.
22467 ///
22468 /// # Example
22469 /// ```rust
22470 /// use jni_simple::{*};
22471 ///
22472 /// unsafe fn copy_entire_java_array_to_rust(env: JNIEnv, array: jintArray) -> Vec<jint> {
22473 /// if array.is_null() {
22474 /// panic!("Java Array is null")
22475 /// }
22476 /// env.GetIntArrayRegion_as_vec(array, 0, None)
22477 /// }
22478 /// ```
22479 ///
22480 pub unsafe fn GetIntArrayRegion_as_vec(&self, array: jintArray, start: jsize, len: Option<jsize>) -> Vec<jint> {
22481 unsafe {
22482 let len = len.unwrap_or_else(|| self.GetArrayLength(array).saturating_sub(start.max(0)).max(0));
22483 if let Ok(len) = usize::try_from(len) {
22484 let mut data = vec![0i32; len]; //We could un-init this, but better play it safe...
22485 self.GetIntArrayRegion_into_slice(array, start, data.as_mut_slice());
22486 if self.ExceptionCheck() {
22487 return Vec::new();
22488 }
22489 return data;
22490 }
22491
22492 //Negative len
22493 let mut sentinel_buffer = [0];
22494 self.GetIntArrayRegion(array, start, len.min(-1), sentinel_buffer.as_mut_ptr());
22495 Vec::new()
22496 }
22497 }
22498
22499 ///
22500 /// Copies data from the jlongArray `array` starting from the given `start` index into the memory pointed to by `buf`.
22501 ///
22502 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_PrimitiveType_ArrayRegion_routines>
22503 ///
22504 /// # Arguments
22505 /// * `array` - handle to a Java jlongArray
22506 /// * `start` - the index of the first element to copy in the Java jlongArray
22507 /// * `len` - amount of data to be copied
22508 /// * `buf` - pointer to memory where the data should be copied to
22509 ///
22510 /// # Throws Java Exception:
22511 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the `array`.
22512 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22513 ///
22514 /// It is JVM implementation specific what is written into `buf` if this function throws an exception.
22515 /// * Data partially written
22516 /// * No data written
22517 ///
22518 /// # Panics
22519 /// if asserts feature is enabled and UB was detected
22520 ///
22521 /// # Safety
22522 /// Current thread must not be detached from JNI.
22523 ///
22524 /// Current thread must not be currently throwing an exception.
22525 ///
22526 /// Current thread does not hold a critical reference.
22527 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22528 ///
22529 /// `array` must be a valid non-null reference to a jlongArray.
22530 /// `buf` must be valid non-null pointer to memory with enough capacity and proper alignment to store `len` jlong's.
22531 ///
22532 /// # Example
22533 /// ```rust
22534 /// use jni_simple::{*};
22535 ///
22536 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
22537 /// array: jlongArray, chunk_buffer: &mut [jlong], chunk_offset: usize) -> bool {
22538 /// if array.is_null() {
22539 /// panic!("Java Array is null")
22540 /// }
22541 ///
22542 /// env.GetLongArrayRegion(array, chunk_offset as jsize, chunk_buffer.len() as jsize, chunk_buffer.as_mut_ptr());
22543 /// if env.ExceptionCheck() {
22544 /// //ArrayIndexOutOfBoundsException
22545 /// env.ExceptionClear();
22546 /// return false;
22547 /// }
22548 /// true
22549 /// }
22550 /// ```
22551 ///
22552 pub unsafe fn GetLongArrayRegion(&self, array: jlongArray, start: jsize, len: jsize, buf: *mut jlong) {
22553 unsafe {
22554 #[cfg(feature = "asserts")]
22555 {
22556 self.check_not_critical("GetLongArrayRegion");
22557 self.check_no_exception("GetLongArrayRegion");
22558 assert!(!array.is_null(), "GetLongArrayRegion jarray must not be null");
22559 assert!(!buf.is_null(), "GetLongArrayRegion buf must not be null");
22560 assert_eq!(0, buf.align_offset(align_of::<jlong>()), "GetLongArrayRegion buf pointer is not aligned");
22561 }
22562
22563 self.jni::<extern "system" fn(JNIEnvVTable, jbooleanArray, jsize, jsize, *mut jlong)>(204)(self.vtable, array, start, len, buf);
22564 }
22565 }
22566
22567 ///
22568 /// Copies data from the jlongArray `array` starting from the given `start` index into the slice `buf`.
22569 ///
22570 /// # Arguments
22571 /// * `array` - handle to a Java jlongArray.
22572 /// * `start` - the index of the first element to copy in the Java jlongArray
22573 /// * `buf` - the slice to copy data into
22574 ///
22575 /// # Throws Java Exception:
22576 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
22577 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22578 ///
22579 /// It is JVM implementation specific what is stored inside buf if this function throws an exception.
22580 /// * Data partially written
22581 /// * No data written
22582 ///
22583 /// # Panics
22584 /// if asserts feature is enabled and UB was detected
22585 /// if the `buf.len()` is larger than `jsize::MAX`
22586 ///
22587 /// # Safety
22588 /// Current thread must not be detached from JNI.
22589 ///
22590 /// Current thread must not be currently throwing an exception.
22591 ///
22592 /// Current thread does not hold a critical reference.
22593 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22594 ///
22595 /// `array` must be a valid non-null reference to a jlongArray.
22596 ///
22597 /// # Example
22598 /// ```rust
22599 /// use jni_simple::{*};
22600 ///
22601 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
22602 /// array: jlongArray, chunk_buffer: &mut [jlong], chunk_offset: usize) -> bool {
22603 /// if array.is_null() {
22604 /// panic!("Java Array is null")
22605 /// }
22606 ///
22607 /// env.GetLongArrayRegion_into_slice(array, chunk_offset as jsize, chunk_buffer);
22608 /// if env.ExceptionCheck() {
22609 /// //ArrayIndexOutOfBoundsException
22610 /// env.ExceptionClear();
22611 /// return false;
22612 /// }
22613 /// true
22614 /// }
22615 /// ```
22616 ///
22617 pub unsafe fn GetLongArrayRegion_into_slice(&self, array: jlongArray, start: jsize, buf: &mut [i64]) {
22618 unsafe {
22619 self.GetLongArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_mut_ptr());
22620 }
22621 }
22622
22623 ///
22624 /// Copies data from the slice `buf` into the jlongArray `array` starting at the given `start` index.
22625 ///
22626 /// # Arguments
22627 /// * `array` - handle to a Java jlongArray.
22628 /// * `start` - the index where the first element should be coped into in the Java jlongArray
22629 /// * `buf` - the slice where data is copied from
22630 ///
22631 /// # Throws Java Exception:
22632 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
22633 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22634 ///
22635 /// It is JVM implementation specific what is stored inside `array` if this function throws an exception.
22636 /// * Data partially written
22637 /// * No data written
22638 ///
22639 /// # Panics
22640 /// if asserts feature is enabled and UB was detected
22641 ///
22642 /// # Safety
22643 /// Current thread must not be detached from JNI.
22644 ///
22645 /// Current thread must not be currently throwing an exception.
22646 ///
22647 /// Current thread does not hold a critical reference.
22648 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22649 ///
22650 /// `array` must be a valid non-null reference to a jlongArray.
22651 ///
22652 /// # Example
22653 /// ```rust
22654 /// use jni_simple::{*};
22655 ///
22656 /// unsafe fn copy_chunk_from_rust_to_java(env: JNIEnv,
22657 /// array: jlongArray, chunk_buffer: &[jlong], chunk_offset: usize) -> bool {
22658 /// if array.is_null() {
22659 /// panic!("Java Array is null")
22660 /// }
22661 ///
22662 /// env.SetLongArrayRegion_from_slice(array, chunk_offset as jsize, chunk_buffer);
22663 /// if env.ExceptionCheck() {
22664 /// //ArrayIndexOutOfBoundsException
22665 /// env.ExceptionClear();
22666 /// return false;
22667 /// }
22668 /// true
22669 /// }
22670 /// ```
22671 ///
22672 pub unsafe fn SetLongArrayRegion_from_slice(&self, array: jlongArray, start: jsize, buf: &[jlong]) {
22673 unsafe {
22674 self.SetLongArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_ptr());
22675 }
22676 }
22677
22678 ///
22679 /// Copies data from a Java jlongArray `array` into a new `Vec<jlong>`
22680 ///
22681 /// # Arguments
22682 /// * `array` - handle to a Java jlongArray.
22683 /// * `start` - the index of the first element to copy in the Java jlongArray
22684 /// * `len` - the amount of data that should be copied. If `None` then all remaining elements in the array are copied.
22685 ///
22686 /// # Returns:
22687 /// a new `Vec<jlong>` that contains the copied data.
22688 ///
22689 /// # Returns empty Vec:
22690 /// * When the array in fact was empty or len was zero.
22691 /// * When this function throws a Java Exception.
22692 ///
22693 /// # Throws Java Exception:
22694 /// * `ArrayIndexOutOfBoundsException` - if `len` is negative.
22695 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the array.
22696 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative.
22697 /// * `ArrayIndexOutOfBoundsException` - if `start` is larget than `env.GetArrayLength(array)`.
22698 /// * `ArrayIndexOutOfBoundsException` - if `start` equals env.GetArrayLength(array) and `len` is larger than 0.
22699 ///
22700 /// # Panics
22701 /// if asserts feature is enabled and UB was detected
22702 ///
22703 /// # Safety
22704 /// Current thread must not be detached from JNI.
22705 ///
22706 /// Current thread must not be currently throwing an exception.
22707 ///
22708 /// Current thread does not hold a critical reference.
22709 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22710 ///
22711 /// `array` must be a valid non-null reference to a jlongArray.
22712 ///
22713 /// # Example
22714 /// ```rust
22715 /// use jni_simple::{*};
22716 ///
22717 /// unsafe fn copy_entire_java_array_to_rust(env: JNIEnv, array: jlongArray) -> Vec<jlong> {
22718 /// if array.is_null() {
22719 /// panic!("Java Array is null")
22720 /// }
22721 /// env.GetLongArrayRegion_as_vec(array, 0, None)
22722 /// }
22723 /// ```
22724 ///
22725 pub unsafe fn GetLongArrayRegion_as_vec(&self, array: jlongArray, start: jsize, len: Option<jsize>) -> Vec<jlong> {
22726 unsafe {
22727 let len = len.unwrap_or_else(|| self.GetArrayLength(array).saturating_sub(start.max(0)).max(0));
22728 if let Ok(len) = usize::try_from(len) {
22729 let mut data = vec![0i64; len]; //We could un-init this, but better play it safe...
22730 self.GetLongArrayRegion_into_slice(array, start, data.as_mut_slice());
22731 if self.ExceptionCheck() {
22732 return Vec::new();
22733 }
22734 return data;
22735 }
22736
22737 //Negative len
22738 let mut sentinel_buffer = [0];
22739 self.GetLongArrayRegion(array, start, len.min(-1), sentinel_buffer.as_mut_ptr());
22740 Vec::new()
22741 }
22742 }
22743
22744 ///
22745 /// Copies data from the jfloatArray `array` starting from the given `start` index into the memory pointed to by `buf`.
22746 ///
22747 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_PrimitiveType_ArrayRegion_routines>
22748 ///
22749 /// # Arguments
22750 /// * `array` - handle to a Java jfloatArray
22751 /// * `start` - the index of the first element to copy in the Java jfloatArray
22752 /// * `len` - amount of data to be copied
22753 /// * `buf` - pointer to memory where the data should be copied to
22754 ///
22755 /// # Throws Java Exception:
22756 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the `array`.
22757 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22758 ///
22759 /// It is JVM implementation specific what is written into `buf` if this function throws an exception.
22760 /// * Data partially written
22761 /// * No data written
22762 ///
22763 /// # Panics
22764 /// if asserts feature is enabled and UB was detected
22765 ///
22766 /// # Safety
22767 /// Current thread must not be detached from JNI.
22768 ///
22769 /// Current thread must not be currently throwing an exception.
22770 ///
22771 /// Current thread does not hold a critical reference.
22772 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22773 ///
22774 /// `array` must be a valid non-null reference to a jfloatArray.
22775 /// `buf` must be valid non-null pointer to memory with enough capacity and proper alignment to store `len` jfloat's.
22776 ///
22777 /// # Example
22778 /// ```rust
22779 /// use jni_simple::{*};
22780 ///
22781 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
22782 /// array: jfloatArray, chunk_buffer: &mut [jfloat], chunk_offset: usize) -> bool {
22783 /// if array.is_null() {
22784 /// panic!("Java Array is null")
22785 /// }
22786 ///
22787 /// env.GetFloatArrayRegion(array, chunk_offset as jsize, chunk_buffer.len() as jsize, chunk_buffer.as_mut_ptr());
22788 /// if env.ExceptionCheck() {
22789 /// //ArrayIndexOutOfBoundsException
22790 /// env.ExceptionClear();
22791 /// return false;
22792 /// }
22793 /// true
22794 /// }
22795 /// ```
22796 ///
22797 pub unsafe fn GetFloatArrayRegion(&self, array: jfloatArray, start: jsize, len: jsize, buf: *mut jfloat) {
22798 unsafe {
22799 #[cfg(feature = "asserts")]
22800 {
22801 self.check_not_critical("GetFloatArrayRegion");
22802 self.check_no_exception("GetFloatArrayRegion");
22803 assert!(!array.is_null(), "GetFloatArrayRegion jarray must not be null");
22804 assert!(!buf.is_null(), "GetFloatArrayRegion buf must not be null");
22805 assert_eq!(0, buf.align_offset(align_of::<jfloat>()), "GetFloatArrayRegion buf pointer is not aligned");
22806 }
22807
22808 self.jni::<extern "system" fn(JNIEnvVTable, jbooleanArray, jsize, jsize, *mut jfloat)>(205)(self.vtable, array, start, len, buf);
22809 }
22810 }
22811
22812 ///
22813 /// Copies data from the jfloatArray `array` starting from the given `start` index into the slice `buf`.
22814 ///
22815 /// # Arguments
22816 /// * `array` - handle to a Java jfloatArray.
22817 /// * `start` - the index of the first element to copy in the Java jfloatArray
22818 /// * `buf` - the slice to copy data into
22819 ///
22820 /// # Throws Java Exception:
22821 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
22822 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22823 ///
22824 /// It is JVM implementation specific what is stored inside buf if this function throws an exception.
22825 /// * Data partially written
22826 /// * No data written
22827 ///
22828 /// # Panics
22829 /// if asserts feature is enabled and UB was detected
22830 /// if the `buf.len()` is larger than `jsize::MAX`
22831 ///
22832 /// # Safety
22833 /// Current thread must not be detached from JNI.
22834 ///
22835 /// Current thread must not be currently throwing an exception.
22836 ///
22837 /// Current thread does not hold a critical reference.
22838 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22839 ///
22840 /// `array` must be a valid non-null reference to a jfloatArray.
22841 ///
22842 /// # Example
22843 /// ```rust
22844 /// use jni_simple::{*};
22845 ///
22846 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
22847 /// array: jfloatArray, chunk_buffer: &mut [jfloat], chunk_offset: usize) -> bool {
22848 /// if array.is_null() {
22849 /// panic!("Java Array is null")
22850 /// }
22851 ///
22852 /// env.GetFloatArrayRegion_into_slice(array, chunk_offset as jsize, chunk_buffer);
22853 /// if env.ExceptionCheck() {
22854 /// //ArrayIndexOutOfBoundsException
22855 /// env.ExceptionClear();
22856 /// return false;
22857 /// }
22858 /// true
22859 /// }
22860 /// ```
22861 ///
22862 pub unsafe fn GetFloatArrayRegion_into_slice(&self, array: jfloatArray, start: jsize, buf: &mut [jfloat]) {
22863 unsafe {
22864 self.GetFloatArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_mut_ptr());
22865 }
22866 }
22867
22868 ///
22869 /// Copies data from the slice `buf` into the jfloatArray `array` starting at the given `start` index.
22870 ///
22871 /// # Arguments
22872 /// * `array` - handle to a Java jfloatArray.
22873 /// * `start` - the index where the first element should be coped into in the Java jfloatArray
22874 /// * `buf` - the slice where data is copied from
22875 ///
22876 /// # Throws Java Exception:
22877 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
22878 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
22879 ///
22880 /// It is JVM implementation specific what is stored inside `array` if this function throws an exception.
22881 /// * Data partially written
22882 /// * No data written
22883 ///
22884 /// # Panics
22885 /// if asserts feature is enabled and UB was detected
22886 ///
22887 /// # Safety
22888 /// Current thread must not be detached from JNI.
22889 ///
22890 /// Current thread must not be currently throwing an exception.
22891 ///
22892 /// Current thread does not hold a critical reference.
22893 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22894 ///
22895 /// `array` must be a valid non-null reference to a jfloatArray.
22896 ///
22897 /// # Example
22898 /// ```rust
22899 /// use jni_simple::{*};
22900 ///
22901 /// unsafe fn copy_chunk_from_rust_to_java(env: JNIEnv,
22902 /// array: jfloatArray, chunk_buffer: &[jfloat], chunk_offset: usize) -> bool {
22903 /// if array.is_null() {
22904 /// panic!("Java Array is null")
22905 /// }
22906 ///
22907 /// env.SetFloatArrayRegion_from_slice(array, chunk_offset as jsize, chunk_buffer);
22908 /// if env.ExceptionCheck() {
22909 /// //ArrayIndexOutOfBoundsException
22910 /// env.ExceptionClear();
22911 /// return false;
22912 /// }
22913 /// true
22914 /// }
22915 /// ```
22916 ///
22917 pub unsafe fn SetFloatArrayRegion_from_slice(&self, array: jfloatArray, start: jsize, buf: &[jfloat]) {
22918 unsafe {
22919 self.SetFloatArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_ptr());
22920 }
22921 }
22922
22923 ///
22924 /// Copies data from a Java jfloatArray `array` into a new `Vec<jfloat>`
22925 ///
22926 /// # Arguments
22927 /// * `array` - handle to a Java jfloatArray.
22928 /// * `start` - the index of the first element to copy in the Java jfloatArray
22929 /// * `len` - the amount of data that should be copied. If `None` then all remaining elements in the array are copied.
22930 ///
22931 /// # Returns:
22932 /// a new `Vec<jfloat>` that contains the copied data.
22933 ///
22934 /// # Returns empty Vec:
22935 /// * When the array in fact was empty or len was zero.
22936 /// * When this function throws a Java Exception.
22937 ///
22938 /// # Throws Java Exception:
22939 /// * `ArrayIndexOutOfBoundsException` - if `len` is negative.
22940 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the array.
22941 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative.
22942 /// * `ArrayIndexOutOfBoundsException` - if `start` is larget than `env.GetArrayLength(array)`.
22943 /// * `ArrayIndexOutOfBoundsException` - if `start` equals env.GetArrayLength(array) and `len` is larger than 0.
22944 ///
22945 /// # Panics
22946 /// if asserts feature is enabled and UB was detected
22947 ///
22948 /// # Safety
22949 /// Current thread must not be detached from JNI.
22950 ///
22951 /// Current thread must not be currently throwing an exception.
22952 ///
22953 /// Current thread does not hold a critical reference.
22954 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
22955 ///
22956 /// `array` must be a valid non-null reference to a jfloatArray.
22957 ///
22958 /// # Example
22959 /// ```rust
22960 /// use jni_simple::{*};
22961 ///
22962 /// unsafe fn copy_entire_java_array_to_rust(env: JNIEnv, array: jfloatArray) -> Vec<jfloat> {
22963 /// if array.is_null() {
22964 /// panic!("Java Array is null")
22965 /// }
22966 /// env.GetFloatArrayRegion_as_vec(array, 0, None)
22967 /// }
22968 /// ```
22969 ///
22970 pub unsafe fn GetFloatArrayRegion_as_vec(&self, array: jfloatArray, start: jsize, len: Option<jsize>) -> Vec<jfloat> {
22971 unsafe {
22972 let len = len.unwrap_or_else(|| self.GetArrayLength(array).saturating_sub(start.max(0)).max(0));
22973 if let Ok(len) = usize::try_from(len) {
22974 let mut data = vec![jfloat::default(); len]; //We could un-init this, but better play it safe...
22975 self.GetFloatArrayRegion_into_slice(array, start, data.as_mut_slice());
22976 if self.ExceptionCheck() {
22977 return Vec::new();
22978 }
22979 return data;
22980 }
22981
22982 //Negative len
22983 let mut sentinel_buffer = [jfloat::default()];
22984 self.GetFloatArrayRegion(array, start, len.min(-1), sentinel_buffer.as_mut_ptr());
22985 Vec::new()
22986 }
22987 }
22988
22989 ///
22990 /// Copies data from the jdoubleArray `array` starting from the given `start` index into the memory pointed to by `buf`.
22991 ///
22992 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Get_PrimitiveType_ArrayRegion_routines>
22993 ///
22994 /// # Arguments
22995 /// * `array` - handle to a Java jdoubleArray
22996 /// * `start` - the index of the first element to copy in the Java jdoubleArray
22997 /// * `len` - amount of data to be copied
22998 /// * `buf` - pointer to memory where the data should be copied to
22999 ///
23000 /// # Throws Java Exception:
23001 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the `array`.
23002 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
23003 ///
23004 /// It is JVM implementation specific what is written into `buf` if this function throws an exception.
23005 /// * Data partially written
23006 /// * No data written
23007 ///
23008 /// # Panics
23009 /// if asserts feature is enabled and UB was detected
23010 ///
23011 /// # Safety
23012 /// Current thread must not be detached from JNI.
23013 ///
23014 /// Current thread must not be currently throwing an exception.
23015 ///
23016 /// Current thread does not hold a critical reference.
23017 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23018 ///
23019 /// `array` must be a valid non-null reference to a jdoubleArray.
23020 /// `buf` must be valid non-null pointer to memory with enough capacity and proper alignment to store `len` jdouble's.
23021 ///
23022 /// # Example
23023 /// ```rust
23024 /// use jni_simple::{*};
23025 ///
23026 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
23027 /// array: jdoubleArray, chunk_buffer: &mut [jdouble], chunk_offset: usize) -> bool {
23028 /// if array.is_null() {
23029 /// panic!("Java Array is null")
23030 /// }
23031 ///
23032 /// env.GetDoubleArrayRegion(array, chunk_offset as jsize, chunk_buffer.len() as jsize, chunk_buffer.as_mut_ptr());
23033 /// if env.ExceptionCheck() {
23034 /// //ArrayIndexOutOfBoundsException
23035 /// env.ExceptionClear();
23036 /// return false;
23037 /// }
23038 /// true
23039 /// }
23040 /// ```
23041 ///
23042 pub unsafe fn GetDoubleArrayRegion(&self, array: jdoubleArray, start: jsize, len: jsize, buf: *mut jdouble) {
23043 unsafe {
23044 #[cfg(feature = "asserts")]
23045 {
23046 self.check_not_critical("GetDoubleArrayRegion");
23047 self.check_no_exception("GetDoubleArrayRegion");
23048 assert!(!array.is_null(), "GetDoubleArrayRegion jarray must not be null");
23049 assert!(!buf.is_null(), "GetDoubleArrayRegion buf must not be null");
23050 assert_eq!(0, buf.align_offset(align_of::<jdouble>()), "GetDoubleArrayRegion buf pointer is not aligned");
23051 }
23052
23053 self.jni::<extern "system" fn(JNIEnvVTable, jbooleanArray, jsize, jsize, *mut jdouble)>(206)(self.vtable, array, start, len, buf);
23054 }
23055 }
23056
23057 ///
23058 /// Copies data from the jdoubleArray `array` starting from the given `start` index into the slice `buf`.
23059 ///
23060 /// # Arguments
23061 /// * `array` - handle to a Java jdoubleArray.
23062 /// * `start` - the index of the first element to copy in the Java jdoubleArray
23063 /// * `buf` - the slice to copy data into
23064 ///
23065 /// # Throws Java Exception:
23066 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
23067 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
23068 ///
23069 /// It is JVM implementation specific what is stored inside buf if this function throws an exception.
23070 /// * Data partially written
23071 /// * No data written
23072 ///
23073 /// # Panics
23074 /// if asserts feature is enabled and UB was detected
23075 /// if the `buf.len()` is larger than `jsize::MAX`
23076 ///
23077 /// # Safety
23078 /// Current thread must not be detached from JNI.
23079 ///
23080 /// Current thread must not be currently throwing an exception.
23081 ///
23082 /// Current thread does not hold a critical reference.
23083 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23084 ///
23085 /// `array` must be a valid non-null reference to a jdoubleArray.
23086 ///
23087 /// # Example
23088 /// ```rust
23089 /// use jni_simple::{*};
23090 ///
23091 /// unsafe fn copy_chunk_from_java_to_rust(env: JNIEnv,
23092 /// array: jdoubleArray, chunk_buffer: &mut [jdouble], chunk_offset: usize) -> bool {
23093 /// if array.is_null() {
23094 /// panic!("Java Array is null")
23095 /// }
23096 ///
23097 /// env.GetDoubleArrayRegion_into_slice(array, chunk_offset as jsize, chunk_buffer);
23098 /// if env.ExceptionCheck() {
23099 /// //ArrayIndexOutOfBoundsException
23100 /// env.ExceptionClear();
23101 /// return false;
23102 /// }
23103 /// true
23104 /// }
23105 /// ```
23106 ///
23107 pub unsafe fn GetDoubleArrayRegion_into_slice(&self, array: jdoubleArray, start: jsize, buf: &mut [jdouble]) {
23108 unsafe {
23109 self.GetDoubleArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_mut_ptr());
23110 }
23111 }
23112
23113 ///
23114 /// Copies data from the slice `buf` into the jfloatArray `array` starting at the given `start` index.
23115 ///
23116 /// # Arguments
23117 /// * `array` - handle to a Java jfloatArray.
23118 /// * `start` - the index where the first element should be coped into in the Java jfloatArray
23119 /// * `buf` - the slice where data is copied from
23120 ///
23121 /// # Throws Java Exception:
23122 /// * `ArrayIndexOutOfBoundsException` - if the slice `buf` is larger than the amount of remaining elements in the `array`.
23123 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or >= env.GetArrayLength(array)
23124 ///
23125 /// It is JVM implementation specific what is stored inside `array` if this function throws an exception.
23126 /// * Data partially written
23127 /// * No data written
23128 ///
23129 /// # Panics
23130 /// if asserts feature is enabled and UB was detected
23131 ///
23132 /// # Safety
23133 /// Current thread must not be detached from JNI.
23134 ///
23135 /// Current thread must not be currently throwing an exception.
23136 ///
23137 /// Current thread does not hold a critical reference.
23138 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23139 ///
23140 /// `array` must be a valid non-null reference to a jfloatArray.
23141 ///
23142 /// # Example
23143 /// ```rust
23144 /// use jni_simple::{*};
23145 ///
23146 /// unsafe fn copy_chunk_from_rust_to_java(env: JNIEnv,
23147 /// array: jfloatArray, chunk_buffer: &[jdouble], chunk_offset: usize) -> bool {
23148 /// if array.is_null() {
23149 /// panic!("Java Array is null")
23150 /// }
23151 ///
23152 /// env.SetDoubleArrayRegion_from_slice(array, chunk_offset as jsize, chunk_buffer);
23153 /// if env.ExceptionCheck() {
23154 /// //ArrayIndexOutOfBoundsException
23155 /// env.ExceptionClear();
23156 /// return false;
23157 /// }
23158 /// true
23159 /// }
23160 /// ```
23161 ///
23162 pub unsafe fn SetDoubleArrayRegion_from_slice(&self, array: jdoubleArray, start: jsize, buf: &[jdouble]) {
23163 unsafe {
23164 self.SetDoubleArrayRegion(array, start, jsize::try_from(buf.len()).expect("buf.len() > jsize::MAX"), buf.as_ptr());
23165 }
23166 }
23167
23168 ///
23169 /// Copies data from a Java jdoubleArray `array` into a new `Vec<jdouble>`
23170 ///
23171 /// # Arguments
23172 /// * `array` - handle to a Java jdoubleArray.
23173 /// * `start` - the index of the first element to copy in the Java jdoubleArray
23174 /// * `len` - the amount of data that should be copied. If `None` then all remaining elements in the array are copied.
23175 ///
23176 /// # Returns:
23177 /// a new `Vec<jdouble>` that contains the copied data.
23178 ///
23179 /// # Returns empty Vec:
23180 /// * When the array in fact was empty or len was zero.
23181 /// * When this function throws a Java Exception.
23182 ///
23183 /// # Throws Java Exception:
23184 /// * `ArrayIndexOutOfBoundsException` - if `len` is negative.
23185 /// * `ArrayIndexOutOfBoundsException` - if `len` is larger than the amount of remaining elements in the array.
23186 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative.
23187 /// * `ArrayIndexOutOfBoundsException` - if `start` is larget than `env.GetArrayLength(array)`.
23188 /// * `ArrayIndexOutOfBoundsException` - if `start` equals env.GetArrayLength(array) and `len` is larger than 0.
23189 ///
23190 /// # Panics
23191 /// if asserts feature is enabled and UB was detected
23192 ///
23193 /// # Safety
23194 /// Current thread must not be detached from JNI.
23195 ///
23196 /// Current thread must not be currently throwing an exception.
23197 ///
23198 /// Current thread does not hold a critical reference.
23199 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23200 ///
23201 /// `array` must be a valid non-null reference to a jdoubleArray.
23202 ///
23203 /// # Example
23204 /// ```rust
23205 /// use jni_simple::{*};
23206 ///
23207 /// unsafe fn copy_entire_java_array_to_rust(env: JNIEnv, array: jdoubleArray) -> Vec<jdouble> {
23208 /// if array.is_null() {
23209 /// panic!("Java Array is null")
23210 /// }
23211 /// env.GetDoubleArrayRegion_as_vec(array, 0, None)
23212 /// }
23213 /// ```
23214 ///
23215 pub unsafe fn GetDoubleArrayRegion_as_vec(&self, array: jdoubleArray, start: jsize, len: Option<jsize>) -> Vec<jdouble> {
23216 unsafe {
23217 let len = len.unwrap_or_else(|| self.GetArrayLength(array).saturating_sub(start.max(0)).max(0));
23218 if let Ok(len) = usize::try_from(len) {
23219 let mut data = vec![jdouble::default(); len]; //We could un-init this, but better play it safe...
23220 self.GetDoubleArrayRegion_into_slice(array, start, data.as_mut_slice());
23221 if self.ExceptionCheck() {
23222 return Vec::new();
23223 }
23224 return data;
23225 }
23226
23227 //Negative len
23228 let mut sentinel_buffer = [jdouble::default()];
23229 self.GetDoubleArrayRegion(array, start, len.min(-1), sentinel_buffer.as_mut_ptr());
23230 Vec::new()
23231 }
23232 }
23233
23234 ///
23235 /// Sets a boolean array region from a buffer
23236 ///
23237 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_PrimitiveType_ArrayRegion_routines>
23238 ///
23239 /// # Arguments
23240 /// * `array` - handle to a Java array.
23241 /// * must not be null
23242 /// * `start` - index in the `array` where the fist element should be copied to
23243 /// * `len` - amount of elements to copy
23244 /// * `buf` - buffer where the elements are copied from.
23245 /// * must not be null
23246 ///
23247 /// # Throws Java Exception:
23248 /// * `ArrayIndexOutOfBoundsException` - if `len` was Some and is larger than the amount of remaining elements in the array.
23249 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or `start` is >= env.GetArrayLength(array)
23250 ///
23251 /// The state of the array is implementation specific if the fn throws an exception.
23252 /// It may have partially copied some data or copied no data.
23253 ///
23254 /// # Panics
23255 /// if asserts feature is enabled and UB was detected
23256 ///
23257 /// # Safety
23258 /// Current thread must not be detached from JNI.
23259 ///
23260 /// Current thread must not be currently throwing an exception.
23261 ///
23262 /// Current thread does not hold a critical reference.
23263 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23264 ///
23265 /// `array` must be a valid non-null reference to a jbooleanArray.
23266 /// `buf` must be at least `len` elements in size
23267 ///
23268 pub unsafe fn SetBooleanArrayRegion(&self, array: jbooleanArray, start: jsize, len: jsize, buf: *const impl JBooleanInputLayout) {
23269 let ptr: *const jboolean = buf.cast();
23270 unsafe {
23271 #[cfg(feature = "asserts")]
23272 {
23273 self.check_not_critical("SetBooleanArrayRegion");
23274 self.check_no_exception("SetBooleanArrayRegion");
23275 assert!(!array.is_null(), "SetBooleanArrayRegion jarray must not be null");
23276 assert!(!buf.is_null(), "SetBooleanArrayRegion buf must not be null");
23277 Self::check_bool_array_is_narrow("SetBooleanArrayRegion", ptr, len);
23278 }
23279 self.jni::<extern "system" fn(JNIEnvVTable, jbooleanArray, jsize, jsize, *const jboolean)>(207)(self.vtable, array, start, len, ptr);
23280 }
23281 }
23282
23283 ///
23284 /// Sets a byte array region from a buffer
23285 ///
23286 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_PrimitiveType_ArrayRegion_routines>
23287 ///
23288 /// # Arguments
23289 /// * `array` - handle to a Java array.
23290 /// * must not be null
23291 /// * `start` - index in the `array` where the fist element should be copied to
23292 /// * `len` - amount of elements to copy
23293 /// * `buf` - buffer where the elements are copied from.
23294 /// * must not be null
23295 ///
23296 /// # Throws Java Exception:
23297 /// * `ArrayIndexOutOfBoundsException` - if `len` was Some and is larger than the amount of remaining elements in the array.
23298 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or `start` is >= env.GetArrayLength(array)
23299 ///
23300 /// The state of the array is implementation specific if the fn throws an exception.
23301 /// It may have partially copied some data or copied no data.
23302 ///
23303 /// # Panics
23304 /// if asserts feature is enabled and UB was detected
23305 ///
23306 /// # Safety
23307 /// Current thread must not be detached from JNI.
23308 ///
23309 /// Current thread must not be currently throwing an exception.
23310 ///
23311 /// Current thread does not hold a critical reference.
23312 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23313 ///
23314 /// `array` must be a valid non-null reference to a jbyteArray.
23315 /// `buf` must be at least `len` elements in size
23316 ///
23317 pub unsafe fn SetByteArrayRegion(&self, array: jbyteArray, start: jsize, len: jsize, buf: *const jbyte) {
23318 unsafe {
23319 #[cfg(feature = "asserts")]
23320 {
23321 self.check_not_critical("SetByteArrayRegion");
23322 self.check_no_exception("SetByteArrayRegion");
23323 assert!(!array.is_null(), "SetByteArrayRegion jarray must not be null");
23324 assert!(!buf.is_null(), "SetByteArrayRegion buf must not be null");
23325 }
23326
23327 self.jni::<extern "system" fn(JNIEnvVTable, jbyteArray, jsize, jsize, *const jbyte)>(208)(self.vtable, array, start, len, buf);
23328 }
23329 }
23330
23331 ///
23332 /// Sets a char array region from a buffer
23333 ///
23334 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_PrimitiveType_ArrayRegion_routines>
23335 ///
23336 /// # Arguments
23337 /// * `array` - handle to a Java array.
23338 /// * must not be null
23339 /// * `start` - index in the `array` where the fist element should be copied to
23340 /// * `len` - amount of elements to copy
23341 /// * `buf` - buffer where the elements are copied from.
23342 /// * must not be null
23343 ///
23344 /// # Throws Java Exception:
23345 /// * `ArrayIndexOutOfBoundsException` - if `len` was Some and is larger than the amount of remaining elements in the array.
23346 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or `start` is >= env.GetArrayLength(array)
23347 ///
23348 /// The state of the array is implementation specific if the fn throws an exception.
23349 /// It may have partially copied some data or copied no data.
23350 ///
23351 /// # Panics
23352 /// if asserts feature is enabled and UB was detected
23353 ///
23354 /// # Safety
23355 /// Current thread must not be detached from JNI.
23356 ///
23357 /// Current thread must not be currently throwing an exception.
23358 ///
23359 /// Current thread does not hold a critical reference.
23360 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23361 ///
23362 /// `array` must be a valid non-null reference to a jcharArray.
23363 /// `buf` must be at least `len` elements in size
23364 ///
23365 pub unsafe fn SetCharArrayRegion(&self, array: jcharArray, start: jsize, len: jsize, buf: *const jchar) {
23366 unsafe {
23367 #[cfg(feature = "asserts")]
23368 {
23369 self.check_not_critical("SetCharArrayRegion");
23370 self.check_no_exception("SetCharArrayRegion");
23371 assert!(!array.is_null(), "SetCharArrayRegion jarray must not be null");
23372 assert!(!buf.is_null(), "SetCharArrayRegion buf must not be null");
23373 assert_eq!(0, buf.align_offset(align_of::<jchar>()), "SetCharArrayRegion buf pointer is not aligned");
23374 }
23375
23376 self.jni::<extern "system" fn(JNIEnvVTable, jcharArray, jsize, jsize, *const jchar)>(209)(self.vtable, array, start, len, buf);
23377 }
23378 }
23379
23380 ///
23381 /// Sets a short array region from a buffer
23382 ///
23383 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_PrimitiveType_ArrayRegion_routines>
23384 ///
23385 /// # Arguments
23386 /// * `array` - handle to a Java array.
23387 /// * must not be null
23388 /// * `start` - index in the `array` where the fist element should be copied to
23389 /// * `len` - amount of elements to copy
23390 /// * `buf` - buffer where the elements are copied from.
23391 /// * must not be null
23392 ///
23393 /// # Throws Java Exception:
23394 /// * `ArrayIndexOutOfBoundsException` - if `len` was Some and is larger than the amount of remaining elements in the array.
23395 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or `start` is >= env.GetArrayLength(array)
23396 ///
23397 /// The state of the array is implementation specific if the fn throws an exception.
23398 /// It may have partially copied some data or copied no data.
23399 ///
23400 /// # Panics
23401 /// if asserts feature is enabled and UB was detected
23402 ///
23403 /// # Safety
23404 /// Current thread must not be detached from JNI.
23405 ///
23406 /// Current thread must not be currently throwing an exception.
23407 ///
23408 /// Current thread does not hold a critical reference.
23409 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23410 ///
23411 /// `array` must be a valid non-null reference to a jshortArray.
23412 /// `buf` must be at least `len` elements in size
23413 ///
23414 pub unsafe fn SetShortArrayRegion(&self, array: jshortArray, start: jsize, len: jsize, buf: *const jshort) {
23415 unsafe {
23416 #[cfg(feature = "asserts")]
23417 {
23418 self.check_not_critical("SetShortArrayRegion");
23419 self.check_no_exception("SetShortArrayRegion");
23420 assert!(!array.is_null(), "SetShortArrayRegion jarray must not be null");
23421 assert!(!buf.is_null(), "SetShortArrayRegion buf must not be null");
23422 assert_eq!(0, buf.align_offset(align_of::<jshort>()), "SetShortArrayRegion buf pointer is not aligned");
23423 }
23424
23425 self.jni::<extern "system" fn(JNIEnvVTable, jshortArray, jsize, jsize, *const jshort)>(210)(self.vtable, array, start, len, buf);
23426 }
23427 }
23428
23429 ///
23430 /// Sets a int array region from a buffer
23431 ///
23432 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_PrimitiveType_ArrayRegion_routines>
23433 ///
23434 /// # Arguments
23435 /// * `array` - handle to a Java array.
23436 /// * must not be null
23437 /// * `start` - index in the `array` where the fist element should be copied to
23438 /// * `len` - amount of elements to copy
23439 /// * `buf` - buffer where the elements are copied from.
23440 /// * must not be null
23441 ///
23442 /// # Throws Java Exception:
23443 /// * `ArrayIndexOutOfBoundsException` - if `len` was Some and is larger than the amount of remaining elements in the array.
23444 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or `start` is >= env.GetArrayLength(array)
23445 ///
23446 /// The state of the array is implementation specific if the fn throws an exception.
23447 /// It may have partially copied some data or copied no data.
23448 ///
23449 /// # Panics
23450 /// if asserts feature is enabled and UB was detected
23451 ///
23452 /// # Safety
23453 /// Current thread must not be detached from JNI.
23454 ///
23455 /// Current thread must not be currently throwing an exception.
23456 ///
23457 /// Current thread does not hold a critical reference.
23458 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23459 ///
23460 /// `array` must be a valid non-null reference to a jintArray.
23461 /// `buf` must be at least `len` elements in size
23462 ///
23463 pub unsafe fn SetIntArrayRegion(&self, array: jintArray, start: jsize, len: jsize, buf: *const jint) {
23464 unsafe {
23465 #[cfg(feature = "asserts")]
23466 {
23467 self.check_not_critical("SetIntArrayRegion");
23468 self.check_no_exception("SetIntArrayRegion");
23469 assert!(!array.is_null(), "SetIntArrayRegion jarray must not be null");
23470 assert!(!buf.is_null(), "SetIntArrayRegion buf must not be null");
23471 assert_eq!(0, buf.align_offset(align_of::<jint>()), "SetIntArrayRegion buf pointer is not aligned");
23472 }
23473
23474 self.jni::<extern "system" fn(JNIEnvVTable, jintArray, jsize, jsize, *const jint)>(211)(self.vtable, array, start, len, buf);
23475 }
23476 }
23477
23478 ///
23479 /// Sets a long array region from a buffer
23480 ///
23481 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_PrimitiveType_ArrayRegion_routines>
23482 ///
23483 /// # Arguments
23484 /// * `array` - handle to a Java array.
23485 /// * must not be null
23486 /// * `start` - index in the `array` where the fist element should be copied to
23487 /// * `len` - amount of elements to copy
23488 /// * `buf` - buffer where the elements are copied from.
23489 /// * must not be null
23490 ///
23491 /// # Throws Java Exception:
23492 /// * `ArrayIndexOutOfBoundsException` - if `len` was Some and is larger than the amount of remaining elements in the array.
23493 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or `start` is >= env.GetArrayLength(array)
23494 ///
23495 /// The state of the array is implementation specific if the fn throws an exception.
23496 /// It may have partially copied some data or copied no data.
23497 ///
23498 /// # Panics
23499 /// if asserts feature is enabled and UB was detected
23500 ///
23501 /// # Safety
23502 /// Current thread must not be detached from JNI.
23503 ///
23504 /// Current thread must not be currently throwing an exception.
23505 ///
23506 /// Current thread does not hold a critical reference.
23507 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23508 ///
23509 /// `array` must be a valid non-null reference to a jlongArray.
23510 /// `buf` must be at least `len` elements in size
23511 ///
23512 pub unsafe fn SetLongArrayRegion(&self, array: jlongArray, start: jsize, len: jsize, buf: *const jlong) {
23513 unsafe {
23514 #[cfg(feature = "asserts")]
23515 {
23516 self.check_not_critical("SetLongArrayRegion");
23517 self.check_no_exception("SetLongArrayRegion");
23518 assert!(!array.is_null(), "SetLongArrayRegion jarray must not be null");
23519 assert!(!buf.is_null(), "SetLongArrayRegion buf must not be null");
23520 assert_eq!(0, buf.align_offset(align_of::<jlong>()), "SetLongArrayRegion buf pointer is not aligned");
23521 }
23522
23523 self.jni::<extern "system" fn(JNIEnvVTable, jlongArray, jsize, jsize, *const jlong)>(212)(self.vtable, array, start, len, buf);
23524 }
23525 }
23526
23527 ///
23528 /// Sets a float array region from a buffer
23529 ///
23530 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_PrimitiveType_ArrayRegion_routines>
23531 ///
23532 /// # Arguments
23533 /// * `array` - handle to a Java array.
23534 /// * must not be null
23535 /// * `start` - index in the `array` where the fist element should be copied to
23536 /// * `len` - amount of elements to copy
23537 /// * `buf` - buffer where the elements are copied from.
23538 /// * must not be null
23539 ///
23540 /// # Throws Java Exception:
23541 /// * `ArrayIndexOutOfBoundsException` - if `len` was Some and is larger than the amount of remaining elements in the array.
23542 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or `start` is >= env.GetArrayLength(array)
23543 ///
23544 /// The state of the array is implementation specific if the fn throws an exception.
23545 /// It may have partially copied some data or copied no data.
23546 ///
23547 /// # Panics
23548 /// if asserts feature is enabled and UB was detected
23549 ///
23550 /// # Safety
23551 /// Current thread must not be detached from JNI.
23552 ///
23553 /// Current thread must not be currently throwing an exception.
23554 ///
23555 /// Current thread does not hold a critical reference.
23556 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23557 ///
23558 /// `array` must be a valid non-null reference to a jfloatArray.
23559 /// `buf` must be at least `len` elements in size
23560 ///
23561 pub unsafe fn SetFloatArrayRegion(&self, array: jfloatArray, start: jsize, len: jsize, buf: *const jfloat) {
23562 unsafe {
23563 #[cfg(feature = "asserts")]
23564 {
23565 self.check_not_critical("SetFloatArrayRegion");
23566 self.check_no_exception("SetFloatArrayRegion");
23567 assert!(!array.is_null(), "SetFloatArrayRegion jarray must not be null");
23568 assert!(!buf.is_null(), "SetFloatArrayRegion buf must not be null");
23569 assert_eq!(0, buf.align_offset(align_of::<jfloat>()), "SetFloatArrayRegion buf pointer is not aligned");
23570 }
23571
23572 self.jni::<extern "system" fn(JNIEnvVTable, jfloatArray, jsize, jsize, *const jfloat)>(213)(self.vtable, array, start, len, buf);
23573 }
23574 }
23575
23576 ///
23577 /// Sets a double array region from a buffer
23578 ///
23579 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#Set_PrimitiveType_ArrayRegion_routines>
23580 ///
23581 /// # Arguments
23582 /// * `array` - handle to a Java array.
23583 /// * must not be null
23584 /// * `start` - index in the `array` where the fist element should be copied to
23585 /// * `len` - amount of elements to copy
23586 /// * `buf` - buffer where the elements are copied from.
23587 /// * must not be null
23588 ///
23589 /// # Throws Java Exception:
23590 /// * `ArrayIndexOutOfBoundsException` - if `len` was Some and is larger than the amount of remaining elements in the array.
23591 /// * `ArrayIndexOutOfBoundsException` - if `start` is negative or `start` is >= env.GetArrayLength(array)
23592 ///
23593 /// The state of the array is implementation specific if the fn throws an exception.
23594 /// It may have partially copied some data or copied no data.
23595 ///
23596 /// # Panics
23597 /// if asserts feature is enabled and UB was detected
23598 ///
23599 /// # Safety
23600 /// Current thread must not be detached from JNI.
23601 ///
23602 /// Current thread must not be currently throwing an exception.
23603 ///
23604 /// Current thread does not hold a critical reference.
23605 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23606 ///
23607 /// `array` must be a valid non-null reference to a jdoubleArray.
23608 /// `buf` must be at least `len` elements in size
23609 ///
23610 pub unsafe fn SetDoubleArrayRegion(&self, array: jdoubleArray, start: jsize, len: jsize, buf: *const jdouble) {
23611 unsafe {
23612 #[cfg(feature = "asserts")]
23613 {
23614 self.check_not_critical("SetDoubleArrayRegion");
23615 self.check_no_exception("SetDoubleArrayRegion");
23616 assert!(!array.is_null(), "SetDoubleArrayRegion jarray must not be null");
23617 assert!(!buf.is_null(), "SetDoubleArrayRegion buf must not be null");
23618 assert_eq!(0, buf.align_offset(align_of::<jdouble>()), "SetDoubleArrayRegion buf pointer is not aligned");
23619 }
23620
23621 self.jni::<extern "system" fn(JNIEnvVTable, jdoubleArray, jsize, jsize, *const jdouble)>(214)(self.vtable, array, start, len, buf);
23622 }
23623 }
23624
23625 #[cfg(all(feature = "asserts", feature = "std"))]
23626 std::thread_local! {
23627 //The "Critical Section" created by GetPrimitiveArrayCritical has a lot of restrictions placed upon it.
23628 //This attempts to track "some" of them on a best effort basis.
23629 static CRITICAL_POINTERS: std::cell::RefCell<std::collections::HashMap<*mut c_void, usize>> = std::cell::RefCell::new(std::collections::HashMap::new());
23630 }
23631
23632 ///
23633 /// Obtains a critical pointer into a primitive java array.
23634 /// This pointer must be released by calling `ReleasePrimitiveArrayCritical`.
23635 /// No other JNI functions can be called in the current thread.
23636 /// The only exception being multiple consecutive calls to `GetPrimitiveArrayCritical` & `GetStringCritical` to obtain multiple critical
23637 /// pointers at the same time.
23638 ///
23639 /// This method will return NULL to indicate error.
23640 /// The JVM will most likely throw an Exception, probably an `OOMError`.
23641 /// If you obtain multiple critical pointers, you MUST release all successfully obtained critical pointers
23642 /// before being able to check for the exception.
23643 ///
23644 /// Special care must be taken to avoid blocking the current thread with a dependency on another JVM thread.
23645 /// I.e. Do not read from a pipe that is filled by another JVM thread for example.
23646 ///
23647 /// It is also ill-advised to hold onto critical pointers for long periods of time even if no dependency on another JVM Thread is made.
23648 /// The JVM may decide among other things to suspend garbage collection while a critical pointer is held.
23649 /// So reading from a Socket with a long timeout while holding a critical pointer is unlikely to be a good idea.
23650 /// As it may cause unintended side effects in the rest of the JVM (like running out of memory because the GC doesn't run)
23651 ///
23652 /// Failure to release critical pointers before returning execution back to Java Code should be treated as UB
23653 /// even tho the JVM spec fails to mention this detail.
23654 ///
23655 /// Releasing critical pointers in another thread other than the thread that created it should be treated as UB
23656 /// even tho the JVM spec only mentions this detail indirectly.
23657 ///
23658 /// I recommend against using this method for almost every use case as using either Set/Get array region or direct NIO buffers
23659 /// is a better choice. One use case I can think of where this method is a valid choice
23660 /// is performing pixel manipulations on the int[]/byte[] inside a large existing `BufferedImage`.
23661 ///
23662 /// # Returns
23663 /// returns null on error otherwise returns a pointer into the data and begins a critical section.
23664 ///
23665 /// # Panics
23666 /// if asserts feature is enabled and UB was detected
23667 ///
23668 /// # Safety
23669 /// `array` must be valid non null reference to a array that is not already garbage collected
23670 ///
23671 pub unsafe fn GetPrimitiveArrayCritical(&self, array: jarray, isCopy: impl JBooleanMutPtr) -> *mut c_void {
23672 unsafe {
23673 #[cfg(all(feature = "asserts", feature = "std"))]
23674 {
23675 Self::CRITICAL_POINTERS.with(|set| {
23676 if set.borrow().is_empty() {
23677 Self::CRITICAL_STRINGS.with(|strings| {
23678 if strings.borrow().is_empty() {
23679 //We can only do this check if we have not yet obtained a unreleased critical on the current thread.
23680 //For subsequent calls we cannot do this check.
23681 self.check_no_exception("GetPrimitiveArrayCritical");
23682 }
23683 });
23684 }
23685 });
23686 assert!(!array.is_null(), "GetPrimitiveArrayCritical jarray must not be null");
23687 }
23688
23689 let crit = isCopy.use_jboolean_mut(|isCopy| self.jni::<extern "system" fn(JNIEnvVTable, jarray, *mut jboolean) -> *mut c_void>(222)(self.vtable, array, isCopy));
23690
23691 #[cfg(all(feature = "asserts", feature = "std"))]
23692 {
23693 if !crit.is_null() {
23694 Self::CRITICAL_POINTERS.with(|set| {
23695 let mut rm = set.borrow_mut();
23696 let n = rm.remove(&crit).unwrap_or(0) + 1;
23697 rm.insert(crit, n);
23698 });
23699 }
23700 }
23701
23702 crit
23703 }
23704 }
23705
23706 ///
23707 /// Releases a critical array obtains in `GetPrimitiveArrayCritical`
23708 ///
23709 /// # Panics
23710 /// if asserts feature is enabled and UB was detected
23711 ///
23712 /// # Safety
23713 /// `array` must be valid non null reference to a array that is not already garbage collected
23714 /// `carray` must be the result of a `GetPrimitiveArrayCritical` call with the same `array`
23715 /// `mode` must be one of `JNI_OK`, `JNI_COMMIT` or `JNI_ABORT` constant values.
23716 ///
23717 pub unsafe fn ReleasePrimitiveArrayCritical(&self, array: jarray, carray: *mut c_void, mode: jint) {
23718 unsafe {
23719 #[cfg(feature = "asserts")]
23720 {
23721 assert!(!array.is_null(), "ReleasePrimitiveArrayCritical jarray must not be null");
23722 assert!(!carray.is_null(), "ReleasePrimitiveArrayCritical carray must not be null");
23723 assert!(
23724 mode == JNI_OK || mode == JNI_COMMIT || mode == JNI_ABORT,
23725 "ReleasePrimitiveArrayCritical mode is invalid {mode}"
23726 );
23727
23728 #[cfg(feature = "std")]
23729 {
23730 Self::CRITICAL_POINTERS.with(|set| {
23731 let mut rm = set.borrow_mut();
23732 let mut n = rm.remove(&carray).expect("ReleasePrimitiveArrayCritical carray is not valid");
23733 if n == 0 {
23734 unreachable!();
23735 }
23736
23737 if mode != JNI_COMMIT {
23738 //JNI_COMMIT does not release the pointer. It's a noop for non-copied pointers.
23739 n -= 1;
23740 }
23741
23742 if n >= 1 {
23743 rm.insert(carray, n);
23744 }
23745 });
23746 }
23747 }
23748
23749 self.jni::<extern "system" fn(JNIEnvVTable, jarray, *mut c_void, jint)>(223)(self.vtable, array, carray, mode);
23750 }
23751 }
23752
23753 ///
23754 /// Registers native methods to a java class with native methods
23755 ///
23756 /// # Arguments
23757 /// * `clazz` - handle to a Java array.
23758 /// * must not be null
23759 /// * `methods` - the native method function pointers
23760 ///
23761 /// # Panics
23762 /// if more than `jsize::MAX` native methods are supposed to be registered.
23763 /// if asserts feature is enabled and UB was detected
23764 ///
23765 /// # Safety
23766 /// Current thread must not be detached from JNI.
23767 ///
23768 /// Current thread must not be currently throwing an exception.
23769 ///
23770 /// Current thread does not hold a critical reference.
23771 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23772 ///
23773 /// `clazz` must be a valid non-null reference to a class.
23774 /// `methods` all elements and their function pointers must be non null and valid.
23775 ///
23776 pub unsafe fn RegisterNatives_from_slice(&self, clazz: jclass, methods: &[JNINativeMethod]) -> jint {
23777 unsafe { self.RegisterNatives(clazz, methods.as_ptr(), jint::try_from(methods.len()).expect("More than jsize::MAX methods")) }
23778 }
23779
23780 ///
23781 /// Registers native methods to a java class with native methods
23782 ///
23783 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#RegisterNatives>
23784 ///
23785 /// # Arguments
23786 /// * `clazz`
23787 /// * must not be null
23788 /// * must not be already garbage collected
23789 /// * `methods` - the native method function pointers
23790 /// * must not be null
23791 /// * `size` - amount of `JNINativeMethod`'s in `methods`
23792 /// * must not be negative
23793 ///
23794 /// # Panics
23795 /// if asserts feature is enabled and UB was detected
23796 ///
23797 /// # Safety
23798 /// Current thread must not be detached from JNI.
23799 ///
23800 /// Current thread must not be currently throwing an exception.
23801 ///
23802 /// Current thread does not hold a critical reference.
23803 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23804 ///
23805 /// `clazz` must be a valid non-null reference to a class.
23806 /// `methods` all elements and their function pointers must be non null and valid.
23807 /// `methods` must be at least `size` elements large
23808 ///
23809 pub unsafe fn RegisterNatives(&self, clazz: jclass, methods: *const JNINativeMethod, size: jint) -> jint {
23810 unsafe {
23811 #[cfg(feature = "asserts")]
23812 {
23813 self.check_not_critical("RegisterNatives");
23814 self.check_no_exception("RegisterNatives");
23815 assert!(!clazz.is_null(), "RegisterNatives class must not be null");
23816 assert!(size > 0, "RegisterNatives size must be greater than 0");
23817 if let Ok(size) = usize::try_from(size) {
23818 for (idx, cur) in core::slice::from_raw_parts(methods, size).iter().enumerate() {
23819 assert!(!cur.name.is_null(), "RegisterNatives JNINativeMethod[{idx}],name is null");
23820 assert!(!cur.signature.is_null(), "RegisterNatives JNINativeMethod[{idx}].signature is null");
23821 assert!(!cur.fnPtr.is_null(), "RegisterNatives JNINativeMethod[{idx}].fnPtr is null");
23822 }
23823 }
23824 }
23825
23826 self.jni::<extern "system" fn(JNIEnvVTable, jclass, *const JNINativeMethod, jint) -> jint>(215)(self.vtable, clazz, methods, size)
23827 }
23828 }
23829
23830 ///
23831 /// Unregisters all native bindings from a java class.
23832 ///
23833 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#UnregisterNatives>
23834 ///
23835 /// # Arguments
23836 /// * `clazz`
23837 /// * must not be null
23838 /// * must not be already garbage collected
23839 ///
23840 /// # Panics
23841 /// if asserts feature is enabled and UB was detected
23842 ///
23843 /// # Safety
23844 /// Current thread must not be detached from JNI.
23845 ///
23846 /// Current thread must not be currently throwing an exception.
23847 ///
23848 /// Current thread does not hold a critical reference.
23849 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23850 ///
23851 /// `clazz` must be a valid non-null reference to a class.
23852 /// `methods` all elements and their function pointers must be non null and valid.
23853 /// `methods` must be at least `size` elements large
23854 ///
23855 pub unsafe fn UnregisterNatives(&self, clazz: jclass) -> jint {
23856 unsafe {
23857 #[cfg(feature = "asserts")]
23858 {
23859 self.check_not_critical("UnregisterNatives");
23860 self.check_no_exception("UnregisterNatives");
23861 assert!(!clazz.is_null(), "UnregisterNatives class must not be null");
23862 }
23863
23864 self.jni::<extern "system" fn(JNIEnvVTable, jclass) -> jint>(216)(self.vtable, clazz)
23865 }
23866 }
23867
23868 ///
23869 /// Enters a monitor on a java object.
23870 /// A will cause all other java threads to block when trying to enter a synchronized block
23871 /// on the object or other native threads to block when trying to enter a monitor.
23872 /// This fn will block until all other threads have either left their synchronized block or monitor sections.
23873 ///
23874 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#MonitorEnter>
23875 ///
23876 /// # Returns
23877 /// `JNI_OK` on success
23878 ///
23879 /// # Arguments
23880 /// * `obj`
23881 /// * must not be null
23882 /// * must not be already garbage collected
23883 ///
23884 /// # Panics
23885 /// if asserts feature is enabled and UB was detected
23886 ///
23887 /// # Safety
23888 /// Current thread must not be detached from JNI.
23889 ///
23890 /// Current thread must not be currently throwing an exception.
23891 ///
23892 /// Current thread does not hold a critical reference.
23893 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23894 ///
23895 /// `jobject` must be a valid non-null reference that is not yet garbage collected.
23896 ///
23897 pub unsafe fn MonitorEnter(&self, obj: jobject) -> jint {
23898 unsafe {
23899 #[cfg(feature = "asserts")]
23900 {
23901 self.check_not_critical("MonitorEnter");
23902 self.check_no_exception("MonitorEnter");
23903 assert!(!obj.is_null(), "MonitorEnter object must not be null");
23904 }
23905
23906 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jint>(217)(self.vtable, obj)
23907 }
23908 }
23909
23910 ///
23911 /// Leaves a monitor entered by `MonitorEnter`
23912 /// This fn cannot be used to "leave" synchronized blocks entered into by java code.
23913 ///
23914 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#MonitorExit>
23915 ///
23916 /// # Arguments
23917 /// * `obj`
23918 /// * must not be null
23919 /// * must not be already garbage collected
23920 ///
23921 /// # Returns
23922 /// `JNI_OK` on success
23923 ///
23924 /// # Throws Java Exception
23925 /// * `IllegalMonitorStateException` - if the current thread does not own the monitor
23926 ///
23927 /// # Panics
23928 /// if asserts feature is enabled and UB was detected
23929 ///
23930 /// # Safety
23931 /// Current thread must not be detached from JNI.
23932 ///
23933 /// Current thread must not be currently throwing an exception.
23934 ///
23935 /// Current thread does not hold a critical reference.
23936 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23937 ///
23938 /// `jobject` must be a valid non-null reference that is not yet garbage collected.
23939 ///
23940 pub unsafe fn MonitorExit(&self, obj: jobject) -> jint {
23941 unsafe {
23942 #[cfg(feature = "asserts")]
23943 {
23944 self.check_not_critical("MonitorExit");
23945 assert!(!obj.is_null(), "MonitorExit object must not be null");
23946 }
23947
23948 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jint>(218)(self.vtable, obj)
23949 }
23950 }
23951
23952 ///
23953 /// Creates a new nio direct `ByteBuffer` that is backed by some native memory provided to by the pointer.
23954 /// When garbage collection collects that `ByteBuffer` it will not perform any operation on the backed memory.
23955 /// The caller has to ensure that the pointer remains valid for the entire existance of the `ByteBuffer`
23956 ///
23957 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#NewDirectByteBuffer>
23958 ///
23959 /// # Arguments
23960 /// * `address`
23961 /// * must not be null
23962 /// * `capacity`
23963 /// * size of the memory pointed to by address
23964 /// * must be positive
23965 ///
23966 /// # Returns
23967 /// A local reference to the newly created `ByteBuffer`
23968 ///
23969 /// # Panics
23970 /// if asserts feature is enabled and UB was detected
23971 ///
23972 /// # Safety
23973 /// Current thread must not be detached from JNI.
23974 ///
23975 /// Current thread must not be currently throwing an exception.
23976 ///
23977 /// Current thread does not hold a critical reference.
23978 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
23979 ///
23980 /// `address` must be a valid non-null.
23981 /// `capacity` must be positive, the memory pointed to by `address` must have at least this amount of bytes in space.
23982 ///
23983 pub unsafe fn NewDirectByteBuffer(&self, address: *mut c_void, capacity: jlong) -> jobject {
23984 unsafe {
23985 #[cfg(feature = "asserts")]
23986 {
23987 self.check_not_critical("NewDirectByteBuffer");
23988 self.check_no_exception("NewDirectByteBuffer");
23989 assert!(!address.is_null(), "NewDirectByteBuffer address must not be null");
23990 assert!(capacity >= 0, "NewDirectByteBuffer capacity must not be negative {capacity}");
23991 assert!(
23992 capacity <= jlong::from(jint::MAX),
23993 "NewDirectByteBuffer capacity is too big, its larger than Integer.MAX_VALUE {capacity}"
23994 );
23995 }
23996
23997 self.jni::<extern "system" fn(JNIEnvVTable, *mut c_void, jlong) -> jobject>(229)(self.vtable, address, capacity)
23998 }
23999 }
24000
24001 ///
24002 /// Gets the memory address that backs a direct nio buffer.
24003 ///
24004 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetDirectBufferAddress>
24005 ///
24006 /// # Arguments
24007 /// * `buf`
24008 /// * must not be null
24009 /// * must not be garbage collected
24010 ///
24011 /// If `buf` does not refer to a Buffer object or is not direct then this fn returns -1.
24012 /// If the jvm does not support accessing direct buffers then this fn returns -1.
24013 ///
24014 /// # Returns
24015 /// The backing pointer or -1 on error
24016 ///
24017 /// # Panics
24018 /// if asserts feature is enabled and UB was detected
24019 ///
24020 /// # Safety
24021 /// Current thread must not be detached from JNI.
24022 ///
24023 /// Current thread must not be currently throwing an exception.
24024 ///
24025 /// Current thread does not hold a critical reference.
24026 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
24027 ///
24028 /// `buf` must be a valid non-null reference to a object and not be garbage collected.
24029 ///
24030 pub unsafe fn GetDirectBufferAddress(&self, buf: jobject) -> *mut c_void {
24031 unsafe {
24032 #[cfg(feature = "asserts")]
24033 {
24034 self.check_not_critical("GetDirectBufferAddress");
24035 self.check_no_exception("GetDirectBufferAddress");
24036 assert!(!buf.is_null(), "GetDirectBufferAddress buffer must not be null");
24037 }
24038 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> *mut c_void>(230)(self.vtable, buf)
24039 }
24040 }
24041
24042 ///
24043 /// Gets the capacity of a direct nio buffer.
24044 ///
24045 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetDirectBufferCapacity>
24046 ///
24047 /// # Arguments
24048 /// * `buf`
24049 /// * must not be null
24050 /// * must not be garbage collected
24051 ///
24052 /// If `buf` does not refer to a Buffer object or is not direct then this fn returns -1.
24053 /// If the jvm does not support accessing direct buffers then this fn returns -1.
24054 ///
24055 /// # Returns
24056 /// The capacity or -1 on error
24057 ///
24058 /// # Panics
24059 /// if asserts feature is enabled and UB was detected
24060 ///
24061 /// # Safety
24062 /// Current thread must not be detached from JNI.
24063 ///
24064 /// Current thread must not be currently throwing an exception.
24065 ///
24066 /// Current thread does not hold a critical reference.
24067 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
24068 ///
24069 /// `buf` must be a valid non-null reference to a object and not be garbage collected.
24070 ///
24071 pub unsafe fn GetDirectBufferCapacity(&self, buf: jobject) -> jlong {
24072 unsafe {
24073 #[cfg(feature = "asserts")]
24074 {
24075 self.check_not_critical("GetDirectBufferCapacity");
24076 self.check_no_exception("GetDirectBufferCapacity");
24077 assert!(!buf.is_null(), "GetDirectBufferCapacity buffer must not be null");
24078 }
24079 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jlong>(231)(self.vtable, buf)
24080 }
24081 }
24082
24083 ///
24084 /// Converts a reflection Method to a jmethodID
24085 ///
24086 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#FromReflectedMethod>
24087 ///
24088 /// # Arguments
24089 /// * `method`
24090 /// * must not be null
24091 /// * must not be garbage collected
24092 /// * must be instanceof a java.lang.reflect.Method or java.lang.reflect.Constructor
24093 ///
24094 ///
24095 /// # Returns
24096 /// the jmethodID that refers to the same method.
24097 ///
24098 /// # Panics
24099 /// if asserts feature is enabled and UB was detected
24100 ///
24101 /// # Safety
24102 /// Current thread must not be detached from JNI.
24103 ///
24104 /// Current thread must not be currently throwing an exception.
24105 ///
24106 /// Current thread does not hold a critical reference.
24107 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
24108 ///
24109 /// `method` must be a valid non-null reference to a java.lang.reflect.Method or java.lang.reflect.Constructor and not be garbage collected.
24110 ///
24111 pub unsafe fn FromReflectedMethod(&self, method: jobject) -> jmethodID {
24112 unsafe {
24113 #[cfg(feature = "asserts")]
24114 {
24115 self.check_not_critical("FromReflectedMethod");
24116 self.check_no_exception("FromReflectedMethod");
24117 assert!(!method.is_null(), "FromReflectedMethod method must not be null");
24118 }
24119 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jmethodID>(7)(self.vtable, method)
24120 }
24121 }
24122
24123 ///
24124 /// Converts a jmethodID into a reflection Method
24125 ///
24126 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#FromReflectedField>
24127 ///
24128 /// # Arguments
24129 /// * `cls` - the class the method is in
24130 /// * must not be null
24131 /// * must not be garbage collected
24132 /// * `jmethodID`
24133 /// * must not be null
24134 /// * must refer to a method that is in `cls`
24135 /// * `isStatic` - is the method static or not?
24136 ///
24137 ///
24138 /// # Returns
24139 /// a local reference that refers to the same method as the jmethodID or null on erro
24140 ///
24141 /// # Throws Java Exception
24142 /// * `OutOfMemoryError` - if the jvm runs out of memory.
24143 ///
24144 /// # Panics
24145 /// if asserts feature is enabled and UB was detected
24146 ///
24147 /// # Safety
24148 /// Current thread must not be detached from JNI.
24149 ///
24150 /// Current thread must not be currently throwing an exception.
24151 ///
24152 /// Current thread does not hold a critical reference.
24153 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
24154 ///
24155 /// `cls` must be a valid non-null reference to a Class and not be garbage collected.
24156 /// `jmethodID` must refer to a method in `cls` and must be either static or not static depending on the `isStatic` flag.
24157 ///
24158 pub unsafe fn ToReflectedMethod(&self, cls: jclass, jmethodID: jmethodID, isStatic: impl Into<jboolean>) -> jobject {
24159 let isStatic = isStatic.into();
24160 unsafe {
24161 #[cfg(feature = "asserts")]
24162 {
24163 self.check_not_critical("ToReflectedMethod");
24164 self.check_no_exception("ToReflectedMethod");
24165 assert!(!cls.is_null(), "ToReflectedMethod class must not be null");
24166 assert!(!jmethodID.is_null(), "ToReflectedMethod method must not be null");
24167 assert!(!isStatic.is_wide(), "ToReflectedMethod isStatic is wide value");
24168 }
24169 self.jni::<extern "system" fn(JNIEnvVTable, jclass, jmethodID, jboolean) -> jobject>(9)(self.vtable, cls, jmethodID, isStatic)
24170 }
24171 }
24172
24173 ///
24174 /// Converts a reflection Field to a jfieldID
24175 ///
24176 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#FromReflectedField>
24177 ///
24178 /// # Arguments
24179 /// * `field`
24180 /// * must not be null
24181 /// * must not be garbage collected
24182 /// * must be instanceof a java.lang.reflect.Field
24183 ///
24184 ///
24185 /// # Returns
24186 /// the jfieldID that refers to the same field.
24187 ///
24188 /// # Panics
24189 /// if asserts feature is enabled and UB was detected
24190 ///
24191 /// # Safety
24192 /// Current thread must not be detached from JNI.
24193 ///
24194 /// Current thread must not be currently throwing an exception.
24195 ///
24196 /// Current thread does not hold a critical reference.
24197 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
24198 ///
24199 /// `field` must be a valid non-null reference to a java.lang.reflect.Field and not be garbage collected.
24200 ///
24201 pub unsafe fn FromReflectedField(&self, field: jobject) -> jfieldID {
24202 unsafe {
24203 #[cfg(feature = "asserts")]
24204 {
24205 self.check_not_critical("FromReflectedField");
24206 self.check_no_exception("FromReflectedField");
24207 assert!(!field.is_null(), "FromReflectedField field must not be null");
24208 }
24209 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jfieldID>(8)(self.vtable, field)
24210 }
24211 }
24212
24213 ///
24214 /// Converts a jfieldID into a reflection Field
24215 ///
24216 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#FromReflectedField>
24217 ///
24218 /// # Arguments
24219 /// * `cls` - the class the method is in
24220 /// * must not be null
24221 /// * must not be garbage collected
24222 /// * `jfieldID`
24223 /// * must not be null
24224 /// * must refer to a field that is in `cls`
24225 /// * `isStatic` - is the method static or not?
24226 ///
24227 ///
24228 /// # Returns
24229 /// a local reference that refers to the same field as the jfieldID or null on erro
24230 ///
24231 /// # Throws Java Exception
24232 /// * `OutOfMemoryError` - if the jvm runs out of memory.
24233 ///
24234 /// # Panics
24235 /// if asserts feature is enabled and UB was detected
24236 ///
24237 /// # Safety
24238 /// Current thread must not be detached from JNI.
24239 ///
24240 /// Current thread must not be currently throwing an exception.
24241 ///
24242 /// Current thread does not hold a critical reference.
24243 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
24244 ///
24245 /// `cls` must be a valid non-null reference to a Class and not be garbage collected.
24246 /// `jfieldID` must refer to a field in `cls` and must be either static or not static depending on the `isStatic` flag.
24247 ///
24248 pub unsafe fn ToReflectedField(&self, cls: jclass, jfieldID: jfieldID, isStatic: impl Into<jboolean>) -> jobject {
24249 let isStatic = isStatic.into();
24250 unsafe {
24251 #[cfg(feature = "asserts")]
24252 {
24253 self.check_not_critical("ToReflectedField");
24254 self.check_no_exception("ToReflectedField");
24255 assert!(!cls.is_null(), "ToReflectedField class must not be null");
24256 assert!(!jfieldID.is_null(), "ToReflectedField field must not be null");
24257 assert!(!isStatic.is_wide(), "ToReflectedMethod isStatic is wide value");
24258 }
24259 self.jni::<extern "system" fn(JNIEnvVTable, jclass, jfieldID, jboolean) -> jobject>(12)(self.vtable, cls, jfieldID, isStatic)
24260 }
24261 }
24262
24263 ///
24264 /// Returns the `JavaVM` assosicated with this `JNIEnv`
24265 ///
24266 /// <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetJavaVM>
24267 ///
24268 /// # Panics
24269 /// if the JVM does not return an error but refuses to set the `JavaVM` pointer.
24270 ///
24271 /// # Returns
24272 /// the `JavaVM` "object" or an error code.
24273 ///
24274 /// # Errors
24275 /// JNI implementation specific error constants like `JNI_EINVAL`
24276 ///
24277 /// # Panics
24278 /// if asserts feature is enabled and UB was detected
24279 ///
24280 /// # Safety
24281 /// Current thread must not be detached from JNI.
24282 ///
24283 /// Current thread must not be currently throwing an exception.
24284 ///
24285 /// Current thread does not hold a critical reference.
24286 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
24287 ///
24288 pub unsafe fn GetJavaVM(&self) -> Result<JavaVM, jint> {
24289 unsafe {
24290 #[cfg(feature = "asserts")]
24291 {
24292 self.check_not_critical("GetJavaVM");
24293 self.check_no_exception("GetJavaVM");
24294 }
24295 let mut r: JNIInvPtr = SyncMutPtr::null();
24296 let res = self.jni::<extern "system" fn(JNIEnvVTable, *mut JNIInvPtr) -> jint>(219)(self.vtable, &raw mut r);
24297 if res != 0 {
24298 return Err(res);
24299 }
24300 assert!(!r.is_null(), "GetJavaVM returned 0 but did not set JVM pointer");
24301 Ok(JavaVM { vtable: r })
24302 }
24303 }
24304
24305 ///
24306 /// Returns the module of the given class.
24307 ///
24308 /// <https://docs.oracle.com/en/java/javase/21/docs/specs/jni/functions.html#getmodule>
24309 ///
24310 /// # Arguments
24311 /// * `cls`
24312 /// * must not be null
24313 /// * must not be garbage collected
24314 /// * must refer to a class
24315 ///
24316 /// # Returns
24317 /// a local reference to the module object.
24318 ///
24319 /// # Panics
24320 /// if asserts feature is enabled and UB was detected
24321 ///
24322 /// # Safety
24323 /// Current thread must not be detached from JNI.
24324 ///
24325 /// Current thread must not be currently throwing an exception.
24326 ///
24327 /// Current thread does not hold a critical reference.
24328 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
24329 ///
24330 /// The JVM must be at least Java 9
24331 ///
24332 /// `cls` must refer to a non-null class that is not yet garbage collected.
24333 ///
24334 pub unsafe fn GetModule(&self, cls: jclass) -> jobject {
24335 unsafe {
24336 #[cfg(feature = "asserts")]
24337 {
24338 self.check_not_critical("GetModule");
24339 self.check_no_exception("GetModule");
24340 assert!(self.GetVersion() >= JNI_VERSION_9);
24341 }
24342
24343 self.jni::<extern "system" fn(JNIEnvVTable, jclass) -> jobject>(233)(self.vtable, cls)
24344 }
24345 }
24346
24347 ///
24348 /// Returns the module of the given class.
24349 ///
24350 /// <https://docs.oracle.com/en/java/javase/21/docs/specs/jni/functions.html#isvirtualthread>
24351 ///
24352 /// # Arguments
24353 /// * `thread`
24354 /// * must not be null
24355 /// * must not be garbage collected
24356 /// * must refer to a java.lang.Thread
24357 ///
24358 /// # Returns
24359 /// true if the thread is virtual, false if not.
24360 ///
24361 /// # Panics
24362 /// if asserts feature is enabled and UB was detected
24363 ///
24364 /// # Safety
24365 /// Current thread must not be detached from JNI.
24366 ///
24367 /// Current thread must not be currently throwing an exception.
24368 ///
24369 /// Current thread does not hold a critical reference.
24370 /// * <https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/functions.html#GetPrimitiveArrayCritical_ReleasePrimitiveArrayCritical>
24371 ///
24372 /// The JVM must be at least Java 21
24373 ///
24374 /// `thread` must refer to a non-null java.lang.Thread that is not yet garbage collected.
24375 ///
24376 pub unsafe fn IsVirtualThread(&self, thread: jobject) -> bool {
24377 unsafe {
24378 #[cfg(feature = "asserts")]
24379 {
24380 self.check_not_critical("IsVirtualThread");
24381 self.check_no_exception("IsVirtualThread");
24382 assert!(self.GetVersion() >= JNI_VERSION_21);
24383 }
24384 self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jboolean>(234)(self.vtable, thread).as_bool()
24385 }
24386 }
24387
24388 /// Checks that we are not in a critical section currently.
24389 #[cfg(feature = "asserts")]
24390 unsafe fn check_not_critical(self, context: &str) {
24391 #[cfg(feature = "std")]
24392 {
24393 Self::CRITICAL_POINTERS.with(|set| {
24394 let sz = set.borrow_mut().len();
24395 assert_eq!(
24396 sz, 0,
24397 "{context} cannot be called now, because there are {sz} critical pointers into primitive arrays that have not been released by the current thread."
24398 );
24399 });
24400 Self::CRITICAL_STRINGS.with(|set| {
24401 let sz = set.borrow_mut().len();
24402 assert_eq!(
24403 sz, 0,
24404 "{context} cannot be called now, because there are {sz} critical pointers into strings that have not been released by the current thread."
24405 );
24406 });
24407 }
24408
24409 _ = context;
24410 _ = self;
24411 }
24412
24413 /// Checks that obj is an array of any type
24414 #[cfg(feature = "asserts")]
24415 unsafe fn check_is_array(self, obj: jobject, context: &str) {
24416 unsafe {
24417 assert!(!obj.is_null(), "{context} cannot check if arg is array because arg is null");
24418 let cl = self.GetObjectClass(obj);
24419 assert!(!cl.is_null(), "{context} arg.getClass() is null?");
24420 let clazz = self.GetObjectClass(cl);
24421 assert!(!clazz.is_null(), "{context} Class#getClass() is null?");
24422
24423 let is_array = self.GetMethodID(clazz, "isArray", "()Z");
24424 let r = self.CallBooleanMethod0(cl, is_array);
24425 if self.ExceptionCheck() {
24426 self.ExceptionDescribe();
24427 panic!("{context} Class#isArray() is throws?");
24428 }
24429
24430 assert!(r, "{context} arg is not an array");
24431
24432 self.DeleteLocalRef(cl);
24433 self.DeleteLocalRef(clazz);
24434 }
24435 }
24436
24437 /// Checks that all boolean values in the array determined by len are 0 or 1 in memory (aka not wide booleans)
24438 #[cfg(feature = "asserts")]
24439 unsafe fn check_bool_array_is_narrow(context: &str, ptr: *const jboolean, len: jsize) {
24440 unsafe {
24441 if ptr.is_null() {
24442 return;
24443 }
24444
24445 let Ok(len) = usize::try_from(len) else {
24446 return;
24447 };
24448
24449 let sl = core::slice::from_raw_parts(ptr, len);
24450 for (idx, b) in sl.iter().enumerate() {
24451 assert!(
24452 !b.is_wide(),
24453 "{context} boolean array contains a wide value {} in index {idx}. This would likely be UB in the JVM.",
24454 b.as_wide()
24455 );
24456 }
24457 }
24458 }
24459
24460 /// Checks that no exception is currently thrown
24461 #[cfg(feature = "asserts")]
24462 unsafe fn check_no_exception(self, context: &str) {
24463 unsafe {
24464 if !self.ExceptionCheck() {
24465 return;
24466 }
24467
24468 self.ExceptionDescribe();
24469 panic!("{context} exception is thrown and not handled");
24470 }
24471 }
24472
24473 /// Checks if the object is a valid reference or null
24474 #[cfg(feature = "asserts")]
24475 unsafe fn check_ref_obj_permit_null(self, context: &str, obj: jobject) {
24476 unsafe {
24477 if obj.is_null() {
24478 return;
24479 }
24480
24481 if self.ExceptionCheck() {
24482 //We cannot do this check currently...
24483 return;
24484 }
24485
24486 assert_ne!(self.GetObjectRefType(obj), jobjectRefType::JNIInvalidRefType, "{context} ref is invalid");
24487 }
24488 }
24489
24490 /// Checks if the object is a valid non-null reference
24491 #[cfg(feature = "asserts")]
24492 unsafe fn check_ref_obj(self, context: &str, obj: jobject) {
24493 unsafe {
24494 assert!(!obj.is_null(), "{context} ref is null");
24495
24496 if self.ExceptionCheck() {
24497 //We cannot do this check currently...
24498 return;
24499 }
24500
24501 let cl = self.FindClass("java/lang/System");
24502 assert!(!cl.is_null(), "java/lang/System not found?");
24503
24504 let cname = CString::new("gc").unwrap_unchecked();
24505 let csig = CString::new("()V").unwrap_unchecked();
24506 //GetStaticMethodID
24507 let gc_method = self.jni::<extern "system" fn(JNIEnvVTable, jobject, *const c_char, *const c_char) -> jmethodID>(113)(self.vtable, cl, cname.as_ptr(), csig.as_ptr());
24508
24509 assert!(!gc_method.is_null(), "java/lang/System#gc() not found?");
24510
24511 match self.GetObjectRefType(obj) {
24512 jobjectRefType::JNIInvalidRefType => panic!("{context} ref is invalid"),
24513 jobjectRefType::JNIWeakGlobalRefType => {
24514 //This bad practice, but sadly sometimes valid.
24515 //I.e. caller holds a strong reference and "knows" the weak ref cannot be GC'ed during the call.
24516 //Good practice would be to use the strong ref to make the call but sadly JVM doesn't enforce this.
24517 //This is just best effort really since we have absolutely NO clue when the GC will run.
24518 //CallStaticVoidMethod
24519 self.jni::<extern "C" fn(JNIEnvVTable, jobject, jmethodID)>(141)(self.vtable, obj, gc_method);
24520 assert!(!self.IsSameObject(obj, null_mut()), "{context} weak reference that has already been garbage collected");
24521 }
24522 _ => {}
24523 }
24524
24525 self.DeleteLocalRef(cl);
24526 }
24527 }
24528
24529 /// Checks if the class is a throwable
24530 #[cfg(feature = "asserts")]
24531 unsafe fn check_is_exception_class(self, context: &str, obj: jclass) {
24532 unsafe {
24533 self.check_is_class(context, obj);
24534 let throwable_cl = self.FindClass("java/lang/Throwable");
24535 assert!(!throwable_cl.is_null(), "{context} java/lang/Throwable not found???");
24536 assert!(self.IsAssignableFrom(obj, throwable_cl), "{context} class is not throwable");
24537 self.DeleteLocalRef(throwable_cl);
24538 }
24539 }
24540
24541 /// Checks if the class is not abstract
24542 #[cfg(feature = "asserts")]
24543 unsafe fn check_is_not_abstract(self, context: &str, obj: jclass) {
24544 unsafe {
24545 self.check_is_class(context, obj);
24546 let class_cl = self.FindClass("java/lang/Class");
24547 assert!(!class_cl.is_null(), "{context} java/lang/Class not found???");
24548 let meth = self.GetMethodID(class_cl, "getModifiers", "()I");
24549 assert!(!meth.is_null(), "{context} java/lang/Class#getModifiers not found???");
24550 let mods = self.CallIntMethod0(obj, meth);
24551 self.DeleteLocalRef(class_cl);
24552 if self.ExceptionCheck() {
24553 self.ExceptionDescribe();
24554 panic!("{context} java/lang/Class#getModifiers throws?");
24555 }
24556
24557 let mod_cl = self.FindClass("java/lang/reflect/Modifier");
24558 assert!(!mod_cl.is_null(), "{context} java/lang/reflect/Modifier not found???");
24559 let mod_field = self.GetStaticFieldID(mod_cl, "ABSTRACT", "I");
24560 assert!(!mod_field.is_null(), "{context} java/lang/reflect/Modifier.ABSTRACT not found???");
24561 let amod = self.GetStaticIntField(mod_cl, mod_field);
24562 self.DeleteLocalRef(mod_cl);
24563
24564 assert_eq!(mods & amod, 0, "{context} class is abstract");
24565 }
24566 }
24567
24568 /// Checks if obj is a class.
24569 #[cfg(feature = "asserts")]
24570 unsafe fn check_is_class(self, context: &str, obj: jclass) {
24571 unsafe {
24572 assert!(!obj.is_null(), "{context} class is null");
24573 self.check_ref_obj(context, obj);
24574
24575 let class_cl = self.FindClass("java/lang/Class");
24576 assert!(!class_cl.is_null(), "{context} java/lang/Class not found???");
24577 //GET OBJECT CLASS
24578 let tcl = self.jni::<extern "system" fn(JNIEnvVTable, jobject) -> jobject>(31)(self.vtable, obj);
24579 assert!(self.IsSameObject(tcl, class_cl), "{context} not a class!");
24580 self.DeleteLocalRef(tcl);
24581 self.DeleteLocalRef(class_cl);
24582 }
24583 }
24584
24585 /// Checks if the `obj` is a classloader or null
24586 #[cfg(feature = "asserts")]
24587 unsafe fn check_is_classloader_or_null(self, context: &str, obj: jobject) {
24588 unsafe {
24589 if obj.is_null() {
24590 return;
24591 }
24592 self.check_ref_obj(context, obj);
24593 let classloader_cl = self.FindClass("java/lang/ClassLoader");
24594 assert!(!classloader_cl.is_null(), "{context} java/lang/ClassLoader not found");
24595 assert!(self.IsInstanceOf(obj, classloader_cl), "{context} argument is not a valid instanceof ClassLoader");
24596
24597 self.DeleteLocalRef(classloader_cl);
24598 }
24599 }
24600
24601 /// Checks if the argument refers toa string
24602 #[cfg(feature = "asserts")]
24603 unsafe fn check_if_arg_is_string(self, src: &str, jobject: jobject) {
24604 unsafe {
24605 if jobject.is_null() {
24606 return;
24607 }
24608
24609 let clazz = self.GetObjectClass(jobject);
24610 assert!(!clazz.is_null(), "{src} string.class is null?");
24611 let str_class = self.FindClass("java/lang/String");
24612 assert!(!str_class.is_null(), "{src} java/lang/String not found?");
24613 assert!(self.IsSameObject(clazz, str_class), "{src} Non string passed to GetStringCritical");
24614 self.DeleteLocalRef(clazz);
24615 self.DeleteLocalRef(str_class);
24616 }
24617 }
24618
24619 /// Checks if the field type of a static field matches
24620 #[cfg(feature = "asserts")]
24621 unsafe fn check_field_type_static(self, context: &str, obj: jclass, fieldID: jfieldID, ty: &str) {
24622 unsafe {
24623 self.check_is_class(context, obj);
24624 assert!(!fieldID.is_null(), "{context} fieldID is null");
24625 let f = self.ToReflectedField(obj, fieldID, true);
24626 assert!(!f.is_null(), "{context} -> ToReflectedField returned null");
24627 let field_cl = self.FindClass("java/lang/reflect/Field");
24628 assert!(!f.is_null(), "{context} java/lang/reflect/Method not found???");
24629 let field_rtyp = self.GetMethodID(field_cl, "getType", "()Ljava/lang/Class;");
24630 assert!(!field_rtyp.is_null(), "{context} java/lang/reflect/Field#getType not found???");
24631 //CallObjectMethodA
24632 let rtc = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, f, field_rtyp, null());
24633 assert!(!rtc.is_null(), "{context} java/lang/reflect/Field#getType returned null???");
24634 self.DeleteLocalRef(field_cl);
24635 self.DeleteLocalRef(f);
24636 let class_cl = self.FindClass("java/lang/Class");
24637 assert!(!class_cl.is_null(), "{context} java/lang/Class not found???");
24638 let class_name = self.GetMethodID(class_cl, "getName", "()Ljava/lang/String;");
24639 assert!(!class_name.is_null(), "{context} java/lang/Class#getName not found???");
24640 //CallObjectMethodA
24641 let name_str = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, rtc, class_name, null());
24642 assert!(!name_str.is_null(), "{context} java/lang/Class#getName returned null??? Class has no name???");
24643 self.DeleteLocalRef(rtc);
24644 let the_name = self
24645 .GetStringUTFChars_as_string(name_str)
24646 .unwrap_or_else(|| panic!("{context} failed to get/parse classname???"));
24647 self.DeleteLocalRef(class_cl);
24648 self.DeleteLocalRef(name_str);
24649 if the_name.as_str().eq(ty) {
24650 return;
24651 }
24652
24653 if ty.eq("object") {
24654 match the_name.as_str() {
24655 "long" | "int" | "short" | "byte" | "char" | "float" | "double" | "boolean" => {
24656 panic!("{context} type of field is {the_name} but expected object");
24657 }
24658 _ => {
24659 return;
24660 }
24661 }
24662 }
24663
24664 panic!("{context} type of field is {the_name} but expected {ty}");
24665 }
24666 }
24667
24668 /// Checks if the return type of a static method matches
24669 #[cfg(feature = "asserts")]
24670 unsafe fn check_return_type_static(self, context: &str, obj: jclass, methodID: jmethodID, ty: &str) {
24671 unsafe {
24672 self.check_is_class(context, obj);
24673 assert!(!methodID.is_null(), "{context} methodID is null");
24674 let m = self.ToReflectedMethod(obj, methodID, true);
24675 assert!(!m.is_null(), "{context} -> ToReflectedMethod returned null");
24676 let meth_cl = self.FindClass("java/lang/reflect/Method");
24677 assert!(!m.is_null(), "{context} java/lang/reflect/Method not found???");
24678 let meth_rtyp = self.GetMethodID(meth_cl, "getReturnType", "()Ljava/lang/Class;");
24679 assert!(!meth_rtyp.is_null(), "{context} java/lang/reflect/Method#getReturnType not found???");
24680 //CallObjectMethodA
24681 let rtc = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, m, meth_rtyp, null());
24682 self.DeleteLocalRef(meth_cl);
24683 self.DeleteLocalRef(m);
24684 if rtc.is_null() {
24685 if ty.eq("void") {
24686 return;
24687 }
24688
24689 panic!("{context} return type of method is void but expected {ty}");
24690 }
24691 let class_cl = self.FindClass("java/lang/Class");
24692 assert!(!class_cl.is_null(), "{context} java/lang/Class not found???");
24693 let class_name = self.GetMethodID(class_cl, "getName", "()Ljava/lang/String;");
24694 assert!(!class_name.is_null(), "{context} java/lang/Class#getName not found???");
24695 //CallObjectMethodA
24696 let name_str = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, rtc, class_name, null());
24697 assert!(!name_str.is_null(), "{context} java/lang/Class#getName returned null??? Class has no name???");
24698 self.DeleteLocalRef(rtc);
24699 let the_name = self
24700 .GetStringUTFChars_as_string(name_str)
24701 .unwrap_or_else(|| panic!("{context} failed to get/parse classname???"));
24702 self.DeleteLocalRef(class_cl);
24703 self.DeleteLocalRef(name_str);
24704 if the_name.as_str().eq(ty) {
24705 return;
24706 }
24707
24708 if ty.eq("object") {
24709 match the_name.as_str() {
24710 "void" | "long" | "int" | "short" | "byte" | "char" | "float" | "double" | "boolean" => {
24711 panic!("{context} return type of method is {the_name} but expected object");
24712 }
24713 _ => {
24714 return;
24715 }
24716 }
24717 }
24718
24719 panic!("{context} return type of method is {the_name} but expected {ty}");
24720 }
24721 }
24722
24723 /// Checks if the parameter types for a static fn match
24724 #[cfg(feature = "asserts")]
24725 unsafe fn check_parameter_types_static<T: JType>(self, context: &str, clazz: jclass, methodID: jmethodID, param1: T, idx: jsize, count: jsize) {
24726 unsafe {
24727 self.check_is_class(context, clazz);
24728 assert!(!methodID.is_null(), "{context} methodID is null");
24729 let java_method = self.ToReflectedMethod(clazz, methodID, true);
24730 assert!(!java_method.is_null(), "{context} -> ToReflectedMethod returned null");
24731 let meth_cl = self.FindClass("java/lang/reflect/Method");
24732 assert!(!java_method.is_null(), "{context} java/lang/reflect/Method not found???");
24733 let meth_params = self.GetMethodID(meth_cl, "getParameterTypes", "()[Ljava/lang/Class;");
24734 assert!(!meth_params.is_null(), "{context} java/lang/reflect/Method#getParameterTypes not found???");
24735
24736 //CallObjectMethodA
24737 let parameter_array = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, java_method, meth_params, null());
24738 self.DeleteLocalRef(meth_cl);
24739 self.DeleteLocalRef(java_method);
24740 assert!(!parameter_array.is_null(), "{context} java/lang/reflect/Method#getParameterTypes return null???");
24741 let parameter_count = self.GetArrayLength(parameter_array);
24742 assert_eq!(parameter_count, count, "{context} wrong number of method parameters");
24743 let param1_class = self.GetObjectArrayElement(parameter_array, idx);
24744 assert!(!param1_class.is_null(), "{context} java/lang/reflect/Method#getParameterTypes[{idx}] is null???");
24745 self.DeleteLocalRef(parameter_array);
24746
24747 let class_cl = self.FindClass("java/lang/Class");
24748 assert!(!class_cl.is_null(), "{context} java/lang/Class not found???");
24749 let class_name = self.GetMethodID(class_cl, "getName", "()Ljava/lang/String;");
24750 assert!(!class_name.is_null(), "{context} java/lang/Class#getName not found???");
24751 let class_is_primitive = self.GetMethodID(class_cl, "isPrimitive", "()Z");
24752 assert!(!class_is_primitive.is_null(), "{context} java/lang/Class#isPrimitive not found???");
24753
24754 //CallObjectMethodA
24755 let name_str = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, param1_class, class_name, null());
24756 assert!(!name_str.is_null(), "{context} java/lang/Class#getName returned null??? Class has no name???");
24757 //CallBooleanMethodA
24758 let param1_is_primitive =
24759 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jboolean>(39)(self.vtable, param1_class, class_is_primitive, null());
24760
24761 let the_name = self
24762 .GetStringUTFChars_as_string(name_str)
24763 .unwrap_or_else(|| panic!("{context} failed to get/parse classname???"));
24764 self.DeleteLocalRef(class_cl);
24765 self.DeleteLocalRef(name_str);
24766
24767 match T::jtype_id() {
24768 'Z' => assert_eq!("boolean", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed boolean"),
24769 'B' => assert_eq!("byte", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed byte"),
24770 'S' => assert_eq!("short", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed short"),
24771 'C' => assert_eq!("char", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed char"),
24772 'I' => assert_eq!("int", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed int"),
24773 'J' => assert_eq!("long", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed long"),
24774 'F' => assert_eq!("float", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed float"),
24775 'D' => assert_eq!("double", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed double"),
24776 'L' => {
24777 assert!(!param1_is_primitive, "{context} param{idx} wrong type. Method has {the_name} but passed an object or null");
24778 let jt: jtype = param1.into();
24779 let obj = jt.object;
24780 if !obj.is_null() {
24781 assert!(
24782 self.IsInstanceOf(obj, param1_class),
24783 "{context} param{idx} wrong type. Method has {the_name} but passed an object that is not null and not instanceof"
24784 );
24785 }
24786 }
24787 _ => unreachable!("{}", T::jtype_id()),
24788 }
24789
24790 self.DeleteLocalRef(param1_class);
24791 }
24792 }
24793
24794 /// Checks if the parameter type matches the constructor
24795 #[cfg(feature = "asserts")]
24796 unsafe fn check_parameter_types_constructor<T: JType>(self, context: &str, clazz: jclass, methodID: jmethodID, param1: T, idx: jsize, count: jsize) {
24797 unsafe {
24798 self.check_ref_obj(context, clazz);
24799 assert!(!clazz.is_null(), "{context} obj.class is null??");
24800 assert!(!methodID.is_null(), "{context} methodID is null");
24801 let java_method = self.ToReflectedMethod(clazz, methodID, false);
24802 assert!(!java_method.is_null(), "{context} -> ToReflectedMethod returned null");
24803 let meth_cl = self.FindClass("java/lang/reflect/Method");
24804 assert!(!java_method.is_null(), "{context} java/lang/reflect/Method not found???");
24805 let meth_params = self.GetMethodID(meth_cl, "getParameterTypes", "()[Ljava/lang/Class;");
24806 assert!(!meth_params.is_null(), "{context} java/lang/reflect/Method#getParameterTypes not found???");
24807
24808 //CallObjectMethodA
24809 let parameter_array = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, java_method, meth_params, null());
24810 self.DeleteLocalRef(meth_cl);
24811 self.DeleteLocalRef(java_method);
24812 assert!(!parameter_array.is_null(), "{context} java/lang/reflect/Method#getParameterTypes return null???");
24813 let parameter_count = self.GetArrayLength(parameter_array);
24814 assert_eq!(parameter_count, count, "{context} wrong number of method parameters");
24815 let param1_class = self.GetObjectArrayElement(parameter_array, idx);
24816 assert!(!param1_class.is_null(), "{context} java/lang/reflect/Method#getParameterTypes[{idx}] is null???");
24817 self.DeleteLocalRef(parameter_array);
24818
24819 let class_cl = self.FindClass("java/lang/Class");
24820 assert!(!class_cl.is_null(), "{context} java/lang/Class not found???");
24821 let class_name = self.GetMethodID(class_cl, "getName", "()Ljava/lang/String;");
24822 assert!(!class_name.is_null(), "{context} java/lang/Class#getName not found???");
24823 let class_is_primitive = self.GetMethodID(class_cl, "isPrimitive", "()Z");
24824 assert!(!class_is_primitive.is_null(), "{context} java/lang/Class#isPrimitive not found???");
24825
24826 //CallObjectMethodA
24827 let name_str = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, param1_class, class_name, null());
24828 assert!(!name_str.is_null(), "{context} java/lang/Class#getName returned null??? Class has no name???");
24829 //CallBooleanMethodA
24830 let param1_is_primitive =
24831 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jboolean>(39)(self.vtable, param1_class, class_is_primitive, null());
24832
24833 let the_name = self
24834 .GetStringUTFChars_as_string(name_str)
24835 .unwrap_or_else(|| panic!("{context} failed to get/parse classname???"));
24836 self.DeleteLocalRef(class_cl);
24837 self.DeleteLocalRef(name_str);
24838
24839 match T::jtype_id() {
24840 'Z' => assert_eq!("boolean", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed boolean"),
24841 'B' => assert_eq!("byte", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed byte"),
24842 'S' => assert_eq!("short", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed short"),
24843 'C' => assert_eq!("char", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed char"),
24844 'I' => assert_eq!("int", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed int"),
24845 'J' => assert_eq!("long", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed long"),
24846 'F' => assert_eq!("float", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed float"),
24847 'D' => assert_eq!("double", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed double"),
24848 'L' => {
24849 assert!(!param1_is_primitive, "{context} param{idx} wrong type. Method has {the_name} but passed an object or null");
24850 let jt: jtype = param1.into();
24851 let obj = jt.object;
24852 if !obj.is_null() {
24853 assert!(
24854 self.IsInstanceOf(obj, param1_class),
24855 "{context} param{idx} wrong type. Method has {the_name} but passed an object that is not null and not instanceof"
24856 );
24857 }
24858 }
24859 _ => unreachable!("{}", T::jtype_id()),
24860 }
24861
24862 self.DeleteLocalRef(param1_class);
24863 }
24864 }
24865
24866 /// checks if the method parameter matches the provided argument
24867 #[cfg(feature = "asserts")]
24868 unsafe fn check_parameter_types_object<T: JType>(self, context: &str, obj: jobject, methodID: jmethodID, param1: T, idx: jsize, count: jsize) {
24869 unsafe {
24870 assert!(!obj.is_null(), "{context} obj is null");
24871 self.check_ref_obj(context, obj);
24872 let clazz = self.GetObjectClass(obj);
24873 assert!(!clazz.is_null(), "{context} obj.class is null??");
24874 assert!(!methodID.is_null(), "{context} methodID is null");
24875 let java_method = self.ToReflectedMethod(clazz, methodID, false);
24876 assert!(!java_method.is_null(), "{context} -> ToReflectedMethod returned null");
24877 self.DeleteLocalRef(clazz);
24878 let meth_cl = self.FindClass("java/lang/reflect/Method");
24879 assert!(!java_method.is_null(), "{context} java/lang/reflect/Method not found???");
24880 let meth_params = self.GetMethodID(meth_cl, "getParameterTypes", "()[Ljava/lang/Class;");
24881 assert!(!meth_params.is_null(), "{context} java/lang/reflect/Method#getParameterTypes not found???");
24882
24883 //CallObjectMethodA
24884 let parameter_array = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, java_method, meth_params, null());
24885 self.DeleteLocalRef(meth_cl);
24886 self.DeleteLocalRef(java_method);
24887 assert!(!parameter_array.is_null(), "{context} java/lang/reflect/Method#getParameterTypes return null???");
24888 let parameter_count = self.GetArrayLength(parameter_array);
24889 assert_eq!(parameter_count, count, "{context} wrong number of method parameters");
24890 let param1_class = self.GetObjectArrayElement(parameter_array, idx);
24891 assert!(!param1_class.is_null(), "{context} java/lang/reflect/Method#getParameterTypes[{idx}] is null???");
24892 self.DeleteLocalRef(parameter_array);
24893
24894 let class_cl = self.FindClass("java/lang/Class");
24895 assert!(!class_cl.is_null(), "{context} java/lang/Class not found???");
24896 let class_name = self.GetMethodID(class_cl, "getName", "()Ljava/lang/String;");
24897 assert!(!class_name.is_null(), "{context} java/lang/Class#getName not found???");
24898 let class_is_primitive = self.GetMethodID(class_cl, "isPrimitive", "()Z");
24899 assert!(!class_is_primitive.is_null(), "{context} java/lang/Class#isPrimitive not found???");
24900
24901 //CallObjectMethodA
24902 let name_str = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, param1_class, class_name, null());
24903 assert!(!name_str.is_null(), "{context} java/lang/Class#getName returned null??? Class has no name???");
24904 //CallBooleanMethodA
24905 let param1_is_primitive =
24906 self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jboolean>(39)(self.vtable, param1_class, class_is_primitive, null());
24907
24908 let the_name = self
24909 .GetStringUTFChars_as_string(name_str)
24910 .unwrap_or_else(|| panic!("{context} failed to get/parse classname???"));
24911
24912 self.DeleteLocalRef(class_cl);
24913 self.DeleteLocalRef(name_str);
24914
24915 match T::jtype_id() {
24916 'Z' => assert_eq!("boolean", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed boolean"),
24917 'B' => assert_eq!("byte", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed byte"),
24918 'S' => assert_eq!("short", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed short"),
24919 'C' => assert_eq!("char", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed char"),
24920 'I' => assert_eq!("int", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed int"),
24921 'J' => assert_eq!("long", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed long"),
24922 'F' => assert_eq!("float", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed float"),
24923 'D' => assert_eq!("double", the_name, "{context} param{idx} wrong type. Method has {the_name} but passed double"),
24924 'L' => {
24925 assert!(!param1_is_primitive, "{context} param{idx} wrong type. Method has {the_name} but passed an object or null");
24926 let jt: jtype = param1.into();
24927 let obj = jt.object;
24928 if !obj.is_null() {
24929 assert!(
24930 self.IsInstanceOf(obj, param1_class),
24931 "{context} param{idx} wrong type. Method has {the_name} but passed an object that is not null and not instanceof"
24932 );
24933 }
24934 }
24935 _ => unreachable!("{}", T::jtype_id()),
24936 }
24937
24938 self.DeleteLocalRef(param1_class);
24939 }
24940 }
24941
24942 /// Checks if the function returns an object
24943 #[cfg(feature = "asserts")]
24944 unsafe fn check_return_type_object(self, context: &str, obj: jobject, methodID: jmethodID, ty: &str) {
24945 unsafe {
24946 assert!(!obj.is_null(), "{context} obj is null");
24947 self.check_ref_obj(context, obj);
24948 let clazz = self.GetObjectClass(obj);
24949 assert!(!clazz.is_null(), "{context} obj.class is null??");
24950 assert!(!methodID.is_null(), "{context} methodID is null");
24951 let m = self.ToReflectedMethod(clazz, methodID, false);
24952 self.DeleteLocalRef(clazz);
24953 assert!(!m.is_null(), "{context} -> ToReflectedMethod returned null");
24954 let meth_cl = self.FindClass("java/lang/reflect/Method");
24955 assert!(!m.is_null(), "{context} java/lang/reflect/Method not found???");
24956 let meth_rtyp = self.GetMethodID(meth_cl, "getReturnType", "()Ljava/lang/Class;");
24957 assert!(!meth_rtyp.is_null(), "{context} java/lang/reflect/Method#getReturnType not found???");
24958 //CallObjectMethodA
24959 let rtc = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, m, meth_rtyp, null());
24960 self.DeleteLocalRef(meth_cl);
24961 self.DeleteLocalRef(m);
24962 if rtc.is_null() {
24963 if ty.eq("void") {
24964 return;
24965 }
24966
24967 panic!("{context} return type of method is void but expected {ty}");
24968 }
24969 let class_cl = self.FindClass("java/lang/Class");
24970 assert!(!class_cl.is_null(), "{context} java/lang/Class not found???");
24971 let class_name = self.GetMethodID(class_cl, "getName", "()Ljava/lang/String;");
24972 assert!(!class_name.is_null(), "{context} java/lang/Class#getName not found???");
24973 //CallObjectMethodA
24974 let name_str = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, rtc, class_name, null());
24975 assert!(!name_str.is_null(), "{context} java/lang/Class#getName returned null??? Class has no name???");
24976 self.DeleteLocalRef(rtc);
24977 let the_name = self
24978 .GetStringUTFChars_as_string(name_str)
24979 .unwrap_or_else(|| panic!("{context} failed to get/parse classname???"));
24980 self.DeleteLocalRef(class_cl);
24981 self.DeleteLocalRef(name_str);
24982 if the_name.as_str().eq(ty) {
24983 return;
24984 }
24985
24986 if ty.eq("object") {
24987 match the_name.as_str() {
24988 "void" | "long" | "int" | "short" | "byte" | "char" | "float" | "double" | "boolean" => {
24989 panic!("{context} return type of method is {the_name} but expected object");
24990 }
24991 _ => {
24992 return;
24993 }
24994 }
24995 }
24996
24997 panic!("{context} return type of method is {the_name} but expected {ty}");
24998 }
24999 }
25000
25001 /// checks if the field type is any object.
25002 #[cfg(feature = "asserts")]
25003 unsafe fn check_field_type_object(self, context: &str, obj: jclass, fieldID: jfieldID, ty: &str) {
25004 unsafe {
25005 assert!(!obj.is_null(), "{context} obj is null");
25006 let clazz = self.GetObjectClass(obj);
25007 assert!(!clazz.is_null(), "{context} obj.class is null??");
25008 assert!(!fieldID.is_null(), "{context} fieldID is null");
25009 let f = self.ToReflectedField(clazz, fieldID, false);
25010 assert!(!f.is_null(), "{context} -> ToReflectedField returned null");
25011 let field_cl = self.FindClass("java/lang/reflect/Field");
25012 assert!(!f.is_null(), "{context} java/lang/reflect/Method not found???");
25013 let field_rtyp = self.GetMethodID(field_cl, "getType", "()Ljava/lang/Class;");
25014 assert!(!field_rtyp.is_null(), "{context} java/lang/reflect/Field#getType not found???");
25015 //CallObjectMethodA
25016 let rtc = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, f, field_rtyp, null());
25017 assert!(!rtc.is_null(), "{context} java/lang/reflect/Field#getType returned null???");
25018 self.DeleteLocalRef(field_cl);
25019 self.DeleteLocalRef(f);
25020 let class_cl = self.FindClass("java/lang/Class");
25021 assert!(!class_cl.is_null(), "{context} java/lang/Class not found???");
25022 let class_name = self.GetMethodID(class_cl, "getName", "()Ljava/lang/String;");
25023 assert!(!class_name.is_null(), "{context} java/lang/Class#getName not found???");
25024 //CallObjectMethodA
25025 let name_str = self.jni::<extern "system" fn(JNIEnvVTable, jobject, jmethodID, *const jtype) -> jobject>(36)(self.vtable, rtc, class_name, null());
25026 assert!(!name_str.is_null(), "{context} java/lang/Class#getName returned null??? Class has no name???");
25027 self.DeleteLocalRef(rtc);
25028 let the_name = self
25029 .GetStringUTFChars_as_string(name_str)
25030 .unwrap_or_else(|| panic!("{context} failed to get/parse classname???"));
25031 self.DeleteLocalRef(class_cl);
25032 self.DeleteLocalRef(name_str);
25033 if the_name.as_str().eq(ty) {
25034 return;
25035 }
25036
25037 if ty.eq("object") {
25038 match the_name.as_str() {
25039 "long" | "int" | "short" | "byte" | "char" | "float" | "double" | "boolean" => {
25040 panic!("{context} type of field is {the_name} but expected object");
25041 }
25042 _ => {
25043 return;
25044 }
25045 }
25046 }
25047
25048 panic!("{context} type of field is {the_name} but expected {ty}");
25049 }
25050 }
25051}
25052
25053impl JavaVM {
25054 /// Helper fn to assist with casting of the internal vtable
25055 /// # Safety
25056 /// This fn is only safe if X matches whats in the vtable of index.
25057 #[inline]
25058 unsafe fn ivk<X>(&self, index: usize) -> X {
25059 unsafe { core::mem::transmute_copy(&(self.vtable.inner().read_volatile().add(index).read_volatile())) }
25060 }
25061
25062 ///
25063 /// Attaches the current thread to the JVM as a normal thread.
25064 /// If a thread name is provided then it will be used as the java name of the current thread.
25065 ///
25066 /// # Errors
25067 /// JNI implementation specific error constants like `JNI_EINVAL`
25068 ///
25069 /// # Safety
25070 /// This fn must not be called on a `JavaVM` object that has been destroyed or is in the process of being destroyed.
25071 ///
25072 pub unsafe fn AttachCurrentThread_str(&self, version: jint, thread_name: impl UseCString, thread_group: jobject) -> Result<JNIEnv, jint> {
25073 unsafe {
25074 thread_name.use_as_const_c_char(|thread_name| {
25075 let mut args = JavaVMAttachArgs::new(version, thread_name, thread_group);
25076 self.AttachCurrentThread(&raw mut args)
25077 })
25078 }
25079 }
25080
25081 ///
25082 /// Attaches the current thread to the JVM as a normal thread.
25083 /// If a thread name is provided then it will be used as the java name of the current thread.
25084 ///
25085 /// # Errors
25086 /// JNI implementation specific error constants like `JNI_EINVAL`
25087 ///
25088 /// # Panics
25089 /// If the JVM does not return an error but also does not set the `JNIEnv` ptr.
25090 ///
25091 /// # Safety
25092 /// This fn must not be called on a `JavaVM` object that has been destroyed or is in the process of being destroyed.
25093 ///
25094 pub unsafe fn AttachCurrentThread(&self, args: *mut JavaVMAttachArgs) -> Result<JNIEnv, jint> {
25095 unsafe {
25096 #[cfg(feature = "asserts")]
25097 {
25098 assert!(!args.is_null(), "AttachCurrentThread args must not be null");
25099 }
25100
25101 let mut envptr: JNIEnvVTable = null_mut();
25102
25103 let result = self.ivk::<extern "system" fn(JNIInvPtr, *mut JNIEnvVTable, *mut JavaVMAttachArgs) -> jint>(4)(self.vtable, &raw mut envptr, args);
25104 if result != JNI_OK {
25105 return Err(result);
25106 }
25107
25108 #[cfg(feature = "asserts")]
25109 {
25110 let jni_version = (*args).version;
25111 assert!(
25112 jni_version & 0x3000_0000 != 0x3000_0000,
25113 "AttachCurrentThread called with jni version 0x{jni_version:X} which should cause an error in the JVM but it did not. Using the resulting vtable is likely ub."
25114 );
25115 }
25116
25117 assert!(!envptr.is_null(), "AttachCurrentThread returned JNI_OK but did not set the JNIEnv pointer!");
25118
25119 Ok(JNIEnv { vtable: envptr })
25120 }
25121 }
25122
25123 ///
25124 /// Attaches the current thread to the JVM as a daemon thread.
25125 /// If a thread name is provided then it will be used as the java name of the current thread.
25126 ///
25127 /// # Errors
25128 /// JNI implementation specific error constants like `JNI_EINVAL`
25129 ///
25130 /// # Safety
25131 /// This fn must not be called on a `JavaVM` object that has been destroyed or is in the process of being destroyed.
25132 ///
25133 pub unsafe fn AttachCurrentThreadAsDaemon_str(&self, version: jint, thread_name: impl UseCString, thread_group: jobject) -> Result<JNIEnv, jint> {
25134 unsafe {
25135 thread_name.use_as_const_c_char(|thread_name| {
25136 let mut args = JavaVMAttachArgs::new(version, thread_name, thread_group);
25137 self.AttachCurrentThreadAsDaemon(&raw mut args)
25138 })
25139 }
25140 }
25141
25142 ///
25143 /// Attaches the current thread to the JVM as a daemon thread.
25144 /// If a thread name is provided then it will be used as the java name of the current thread.
25145 ///
25146 /// # Errors
25147 /// JNI implementation specific error constants like `JNI_EINVAL`
25148 ///
25149 /// # Panics
25150 /// If the JVM does not return an error but also does not set the `JNIEnv` ptr.
25151 ///
25152 /// # Safety
25153 /// This fn must not be called on a `JavaVM` object that has been destroyed or is in the process of being destroyed.
25154 ///
25155 pub unsafe fn AttachCurrentThreadAsDaemon(&self, args: *mut JavaVMAttachArgs) -> Result<JNIEnv, jint> {
25156 unsafe {
25157 #[cfg(feature = "asserts")]
25158 {
25159 assert!(!args.is_null(), "AttachCurrentThreadAsDaemon args must not be null");
25160 }
25161 let mut envptr: JNIEnvVTable = null_mut();
25162
25163 let result = self.ivk::<extern "system" fn(JNIInvPtr, *mut JNIEnvVTable, *mut JavaVMAttachArgs) -> jint>(7)(self.vtable, &raw mut envptr, args);
25164
25165 if result != JNI_OK {
25166 return Err(result);
25167 }
25168
25169 assert!(!envptr.is_null(), "AttachCurrentThreadAsDaemon returned JNI_OK but did not set the JNIEnv pointer!");
25170
25171 Ok(JNIEnv { vtable: envptr })
25172 }
25173 }
25174
25175 ///
25176 /// Gets the `JNIEnv` for the current thread.
25177 ///
25178 /// Concerning the generic type `T`. This type must refer to the correct function table for the given `jni_version`:
25179 /// - For ordinary `jni_version` values `T` must be `JNIEnv`.
25180 /// - For jvmti `jni_version` values `T` must be `JVMTIEnv`.
25181 /// - `*mut c_void` is also always a valid type for `T` regardless of the value of `jni_version`!
25182 /// - using `*mut c_void` will return the raw function table.
25183 ///
25184 /// Using the wrong type for `T` is undefined behavior!
25185 /// There is no way to check this as jvmti and jni function tables are completely different!
25186 ///
25187 ///
25188 /// # Safety
25189 /// This fn must not be called on a `JavaVM` object that has been destroyed or is in the process of being destroyed.
25190 /// # Panics
25191 /// If the JVM does not return an error but also does not set the `JNIEnv` ptr.
25192 ///
25193 /// If the asserts feature is enabled and the implementation can detect that `T` is not correct.
25194 /// This is only provided on a best effort basis.
25195 ///
25196 /// # Errors
25197 /// JNI implementation specific error constants like `JNI_EINVAL`
25198 /// # Undefined behavior
25199 /// Using the wrong type `T` for the given `jni_version`. I.e. using `JNIEnv` for `JVMTI` or `JVMTIEnv` for `JNI`.
25200 /// # Example
25201 /// ```rust
25202 /// use std::ffi::c_void;
25203 /// use jni_simple::{JNIEnv, JVMTIEnv, JavaVM, JNI_VERSION_1_8, JVMTI_VERSION_21};
25204 ///
25205 /// unsafe fn some_func(vm: &JavaVM) {
25206 /// //for 99% use cases this is what you want!
25207 /// let jni = vm.GetEnv::<JNIEnv>(JNI_VERSION_1_8).expect("Error");
25208 ///
25209 /// let jni_raw = vm.GetEnv::<*mut c_void>(JNI_VERSION_1_8).expect("Error");
25210 /// let jvmti = vm.GetEnv::<JVMTIEnv>(JVMTI_VERSION_21).expect("Error");
25211 /// let jni_raw = vm.GetEnv::<*mut c_void>(JVMTI_VERSION_21).expect("Error");
25212 /// }
25213 /// ```
25214 ///
25215 pub unsafe fn GetEnv<T: SealedEnvVTable>(&self, jni_version: jint) -> Result<T, jint> {
25216 unsafe {
25217 let mut envptr: *mut c_void = null_mut();
25218 #[cfg(feature = "asserts")]
25219 {
25220 assert!(
25221 jni_version & 0x3000_0000 != 0x3000_0000 || T::can_jvmti(),
25222 "type parameter T cannot receive a JVMTI function VTable but jni_version 0x{jni_version:X} would likely request one. Using the resulting VTable would be UB."
25223 );
25224
25225 assert!(
25226 jni_version & 0x3000_0000 != 0x0000_0000 || T::can_jni(),
25227 "type parameter T cannot receive a JNI function VTable but jni_version 0x{jni_version:X} would likely request one. Using the resulting VTable would be UB."
25228 );
25229 }
25230
25231 let result = self.ivk::<extern "system" fn(JNIInvPtr, *mut *mut c_void, jint) -> jint>(6)(self.vtable, &raw mut envptr, jni_version);
25232
25233 if result != JNI_OK {
25234 return Err(result);
25235 }
25236
25237 assert!(!envptr.is_null(), "GetEnv returned JNI_OK but did not set the JNIEnv pointer!");
25238
25239 Ok(T::from(envptr))
25240 }
25241 }
25242
25243 ///
25244 /// Detaches the current thread from the jvm.
25245 /// This should only be called on functions that were attached with `AttachCurrentThread` or `AttachCurrentThreadAsDaemon`.
25246 ///
25247 /// # Safety
25248 /// Detaches the current thread. The `JNIEnv` of the current thread is no longer valid after this call.
25249 /// Any further calls made using it will result in undefined behavior.
25250 ///
25251 #[must_use]
25252 pub unsafe fn DetachCurrentThread(&self) -> jint {
25253 unsafe { self.ivk::<extern "system" fn(JNIInvPtr) -> jint>(5)(self.vtable) }
25254 }
25255
25256 ///
25257 /// This function will block until all java threads have completed and then destroy the JVM.
25258 /// It should not be called from a method that is called from the JVM.
25259 ///
25260 /// # Safety
25261 /// Careful consideration should be taken when this fn is called. As mentioned calling it from
25262 /// a JVM Thread will probably just block the calling thread forever. However, this fn also
25263 /// does stuff internally with the jvm, after/during its return the JVM can no longer be used in
25264 /// any thread. Any existing `JavaVM` object will become invalid. Attempts to obtain a `JNIEnv` after
25265 /// this fn returns by way of calling `AttachThread` will likely lead to undefined behavior.
25266 /// Shutting down a JVM is a "terminal" operation for any Hotspot implementation of the JVM.
25267 /// The current process will never be able to relaunch a hotspot JVM.
25268 ///
25269 /// This fn should therefore only be used if a rust thread needs to "wait" until the JVM is dead to then perform
25270 /// some operations such a cleanup before eventually calling `exit()`
25271 ///
25272 /// Please note that this fn never returns if the `JavaVM` terminates abnormally (e.g. due to a crash),
25273 /// or someone calling Runtime.getRuntime().halt(...) in Java, because that just terminates the Process instantly.
25274 /// Its usefulness to run shutdown code is therefore limited.
25275 ///
25276 ///
25277 pub unsafe fn DestroyJavaVM(&self) {
25278 unsafe {
25279 self.ivk::<extern "system" fn(JNIInvPtr) -> ()>(3)(self.vtable);
25280 }
25281 }
25282}
25283
25284#[cfg(test)]
25285#[test]
25286const fn test_sync() {
25287 static_assertions::assert_impl_all!(JavaVM: Sync);
25288 static_assertions::assert_impl_all!(JavaVM: Send);
25289
25290 static_assertions::assert_impl_all!(jniNativeInterface: Sync);
25291 static_assertions::assert_impl_all!(jniNativeInterface: Send);
25292
25293 static_assertions::assert_not_impl_all!(JNIEnv: Sync);
25294 static_assertions::assert_not_impl_all!(JNIEnv: Send);
25295
25296 static_assertions::assert_impl_all!(JVMTIEnv: Sync);
25297 static_assertions::assert_impl_all!(JVMTIEnv: Send);
25298}
25299
25300#[cfg(doctest)]
25301#[doc = include_str!("../README.md")]
25302struct ReadmeDocTests;