Skip to main content

ri/java/classes/
device.rs

1//! Copyright © 2025-2026 Wenze Wei. All Rights Reserved.
2//!
3//! This file is part of Ri.
4//! The Ri project belongs to the Dunimd Team.
5//!
6//! Licensed under the Apache License, Version 2.0 (the "License");
7//! You may not use this file except in compliance with the License.
8//! You may obtain a copy of the License at
9//!
10//!     http://www.apache.org/licenses/LICENSE-2.0
11//!
12//! Unless required by applicable law or agreed to in writing, software
13//! distributed under the License is distributed on an "AS IS" BASIS,
14//! WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15//! See the License for the specific language governing permissions and
16//! limitations under the License.
17
18//! # Device Module JNI Bindings
19//!
20//! JNI bindings for Ri device classes.
21
22use jni::JNIEnv;
23use jni::objects::{JClass, JString, JObject};
24use jni::sys::{jlong, jboolean, jint, jdouble, jstring, jlongArray, jobjectArray};
25use crate::device::{
26    RiDeviceControlModule, RiDeviceControlConfig, RiDevice, RiDeviceType, RiDeviceStatus,
27    RiDeviceCapabilities, RiDeviceHealthMetrics, RiDeviceConfig, RiNetworkDeviceInfo,
28    RiDiscoveryResult, RiResourceRequest, RiResourceAllocation, RiDeviceSchedulingConfig,
29    RiDeviceController,
30};
31use crate::java::exception::{check_not_null, throw_ri_error};
32use crate::java::runtime::block_on_local;
33
34// =============================================================================
35// RiDeviceControlModule JNI Bindings
36// =============================================================================
37
38#[no_mangle]
39pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceControlModule_new0(
40    mut env: JNIEnv,
41    _class: JClass,
42    config_ptr: jlong,
43) -> jlong {
44    if config_ptr == 0 {
45        throw_ri_error(&mut env, "RiDeviceControlConfig pointer is null");
46        return 0;
47    }
48    let config = unsafe { (*(config_ptr as *const RiDeviceControlConfig)).clone() };
49    let module = Box::new(RiDeviceControlModule::new().with_config(config));
50    Box::into_raw(module) as jlong
51}
52
53#[no_mangle]
54pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceControlModule_free0(
55    _env: JNIEnv,
56    _class: JClass,
57    ptr: jlong,
58) {
59    if ptr != 0 {
60        unsafe {
61            let _ = Box::from_raw(ptr as *mut RiDeviceControlModule);
62        }
63    }
64}
65
66// =============================================================================
67// RiDeviceControlConfig JNI Bindings
68// =============================================================================
69
70#[no_mangle]
71pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceControlConfig_new0(
72    _env: JNIEnv,
73    _class: JClass,
74) -> jlong {
75    let config = Box::new(RiDeviceControlConfig::default());
76    Box::into_raw(config) as jlong
77}
78
79#[no_mangle]
80pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceControlConfig_free0(
81    _env: JNIEnv,
82    _class: JClass,
83    ptr: jlong,
84) {
85    if ptr != 0 {
86        unsafe {
87            let _ = Box::from_raw(ptr as *mut RiDeviceControlConfig);
88        }
89    }
90}
91
92// =============================================================================
93// RiDevice JNI Bindings
94// =============================================================================
95
96#[no_mangle]
97pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_new0(
98    mut env: JNIEnv,
99    _class: JClass,
100    name: JString,
101    device_type: jint,
102) -> jlong {
103    let name_str: String = match env.get_string(&name) {
104        Ok(s) => s.into(),
105        Err(_) => {
106            crate::java::exception::throw_ri_error(&mut env, "Invalid name string");
107            return 0;
108        }
109    };
110    
111    let dtype = match device_type {
112        0 => RiDeviceType::CPU,
113        1 => RiDeviceType::GPU,
114        2 => RiDeviceType::Memory,
115        3 => RiDeviceType::Storage,
116        4 => RiDeviceType::Network,
117        5 => RiDeviceType::Sensor,
118        6 => RiDeviceType::Actuator,
119        _ => RiDeviceType::Custom,
120    };
121    
122    let device = Box::new(RiDevice::new(name_str, dtype));
123    Box::into_raw(device) as jlong
124}
125
126#[no_mangle]
127pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_getId0<'local>(
128    mut env: JNIEnv<'local>,
129    _class: JClass<'local>,
130    ptr: jlong,
131) -> jstring {
132    if !check_not_null(&mut env, ptr, "RiDevice") {
133        return std::ptr::null_mut();
134    }
135    
136    let device = unsafe { &*(ptr as *const RiDevice) };
137    match env.new_string(device.id()) {
138            Ok(s) => s.into_raw(),
139            Err(_) => std::ptr::null_mut(),
140        }
141}
142
143#[no_mangle]
144pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_getName0<'local>(
145    mut env: JNIEnv<'local>,
146    _class: JClass<'local>,
147    ptr: jlong,
148) -> jstring {
149    if !check_not_null(&mut env, ptr, "RiDevice") {
150        return std::ptr::null_mut();
151    }
152    
153    let device = unsafe { &*(ptr as *const RiDevice) };
154    match env.new_string(device.name()) {
155            Ok(s) => s.into_raw(),
156            Err(_) => std::ptr::null_mut(),
157        }
158}
159
160#[no_mangle]
161pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_getDeviceType0(
162    mut env: JNIEnv,
163    _class: JClass,
164    ptr: jlong,
165) -> jint {
166    if !check_not_null(&mut env, ptr, "RiDevice") {
167        return 0;
168    }
169    
170    let device = unsafe { &*(ptr as *const RiDevice) };
171    device.device_type() as jint
172}
173
174#[no_mangle]
175pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_getStatus0(
176    mut env: JNIEnv,
177    _class: JClass,
178    ptr: jlong,
179) -> jint {
180    if !check_not_null(&mut env, ptr, "RiDevice") {
181        return 0;
182    }
183    
184    let device = unsafe { &*(ptr as *const RiDevice) };
185    device.status() as jint
186}
187
188#[no_mangle]
189pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_setStatus0(
190    mut env: JNIEnv,
191    _class: JClass,
192    ptr: jlong,
193    status: jint,
194) {
195    if !check_not_null(&mut env, ptr, "RiDevice") {
196        return;
197    }
198    
199    let device = unsafe { &mut *(ptr as *mut RiDevice) };
200    let status_val = match status {
201        0 => RiDeviceStatus::Unknown,
202        1 => RiDeviceStatus::Available,
203        2 => RiDeviceStatus::Busy,
204        3 => RiDeviceStatus::Error,
205        4 => RiDeviceStatus::Offline,
206        5 => RiDeviceStatus::Maintenance,
207        6 => RiDeviceStatus::Degraded,
208        _ => RiDeviceStatus::Allocated,
209    };
210    device.set_status(status_val);
211}
212
213#[no_mangle]
214pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_getCapabilities0(
215    mut env: JNIEnv,
216    _class: JClass,
217    ptr: jlong,
218) -> jlong {
219    if !check_not_null(&mut env, ptr, "RiDevice") {
220        return 0;
221    }
222    
223    let device = unsafe { &*(ptr as *const RiDevice) };
224    let capabilities = Box::new(device.capabilities().clone());
225    Box::into_raw(capabilities) as jlong
226}
227
228#[no_mangle]
229pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_setCapabilities0(
230    mut env: JNIEnv,
231    _class: JClass,
232    ptr: jlong,
233    capabilities_ptr: jlong,
234) {
235    if !check_not_null(&mut env, ptr, "RiDevice") || !check_not_null(&mut env, capabilities_ptr, "RiDeviceCapabilities") {
236        return;
237    }
238    
239    let device = unsafe { &mut *(ptr as *mut RiDevice) };
240    let capabilities = unsafe { &*(capabilities_ptr as *const RiDeviceCapabilities) };
241    let _ = device.clone().with_capabilities(capabilities.clone());
242}
243
244#[no_mangle]
245pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_getHealthMetrics0(
246    mut env: JNIEnv,
247    _class: JClass,
248    ptr: jlong,
249) -> jlong {
250    if !check_not_null(&mut env, ptr, "RiDevice") {
251        return 0;
252    }
253    
254    let device = unsafe { &*(ptr as *const RiDevice) };
255    let metrics = Box::new(device.health_metrics().clone());
256    Box::into_raw(metrics) as jlong
257}
258
259#[no_mangle]
260pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_isAvailable0(
261    mut env: JNIEnv,
262    _class: JClass,
263    ptr: jlong,
264) -> jboolean {
265    if !check_not_null(&mut env, ptr, "RiDevice") {
266        return 0;
267    }
268    
269    let device = unsafe { &*(ptr as *const RiDevice) };
270    device.is_available() as jboolean
271}
272
273#[no_mangle]
274pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_isAllocated0(
275    mut env: JNIEnv,
276    _class: JClass,
277    ptr: jlong,
278) -> jboolean {
279    if !check_not_null(&mut env, ptr, "RiDevice") {
280        return 0;
281    }
282    
283    let device = unsafe { &*(ptr as *const RiDevice) };
284    device.is_allocated() as jboolean
285}
286
287#[no_mangle]
288pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_getHealthScore0(
289    mut env: JNIEnv,
290    _class: JClass,
291    ptr: jlong,
292) -> jint {
293    if !check_not_null(&mut env, ptr, "RiDevice") {
294        return 0;
295    }
296    
297    let device = unsafe { &*(ptr as *const RiDevice) };
298    device.health_score() as jint
299}
300
301#[no_mangle]
302pub extern "system" fn Java_com_dunimd_ri_device_RiDevice_free0(
303    _env: JNIEnv,
304    _class: JClass,
305    ptr: jlong,
306) {
307    if ptr != 0 {
308        unsafe {
309            let _ = Box::from_raw(ptr as *mut RiDevice);
310        }
311    }
312}
313
314// =============================================================================
315// RiDeviceCapabilities JNI Bindings
316// =============================================================================
317
318#[no_mangle]
319pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceCapabilities_new0(
320    _env: JNIEnv,
321    _class: JClass,
322) -> jlong {
323    let capabilities = Box::new(RiDeviceCapabilities::new());
324    Box::into_raw(capabilities) as jlong
325}
326
327#[no_mangle]
328pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceCapabilities_getComputeUnits0(
329    mut env: JNIEnv,
330    _class: JClass,
331    ptr: jlong,
332) -> jint {
333    if !check_not_null(&mut env, ptr, "RiDeviceCapabilities") {
334        return -1;
335    }
336    
337    let capabilities = unsafe { &*(ptr as *const RiDeviceCapabilities) };
338    capabilities.compute_units.map(|v| v as jint).unwrap_or(-1)
339}
340
341#[no_mangle]
342pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceCapabilities_setComputeUnits0(
343    mut env: JNIEnv,
344    _class: JClass,
345    ptr: jlong,
346    units: jint,
347) {
348    if !check_not_null(&mut env, ptr, "RiDeviceCapabilities") {
349        return;
350    }
351    
352    let capabilities = unsafe { &mut *(ptr as *mut RiDeviceCapabilities) };
353    capabilities.compute_units = Some(units as usize);
354}
355
356#[no_mangle]
357pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceCapabilities_getMemoryGb0(
358    mut env: JNIEnv,
359    _class: JClass,
360    ptr: jlong,
361) -> jdouble {
362    if !check_not_null(&mut env, ptr, "RiDeviceCapabilities") {
363        return -1.0;
364    }
365    
366    let capabilities = unsafe { &*(ptr as *const RiDeviceCapabilities) };
367    capabilities.memory_gb.unwrap_or(-1.0)
368}
369
370#[no_mangle]
371pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceCapabilities_setMemoryGb0(
372    mut env: JNIEnv,
373    _class: JClass,
374    ptr: jlong,
375    memory_gb: jdouble,
376) {
377    if !check_not_null(&mut env, ptr, "RiDeviceCapabilities") {
378        return;
379    }
380    
381    let capabilities = unsafe { &mut *(ptr as *mut RiDeviceCapabilities) };
382    capabilities.memory_gb = Some(memory_gb);
383}
384
385#[no_mangle]
386pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceCapabilities_getStorageGb0(
387    mut env: JNIEnv,
388    _class: JClass,
389    ptr: jlong,
390) -> jdouble {
391    if !check_not_null(&mut env, ptr, "RiDeviceCapabilities") {
392        return -1.0;
393    }
394    
395    let capabilities = unsafe { &*(ptr as *const RiDeviceCapabilities) };
396    capabilities.storage_gb.unwrap_or(-1.0)
397}
398
399#[no_mangle]
400pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceCapabilities_setStorageGb0(
401    mut env: JNIEnv,
402    _class: JClass,
403    ptr: jlong,
404    storage_gb: jdouble,
405) {
406    if !check_not_null(&mut env, ptr, "RiDeviceCapabilities") {
407        return;
408    }
409    
410    let capabilities = unsafe { &mut *(ptr as *mut RiDeviceCapabilities) };
411    capabilities.storage_gb = Some(storage_gb);
412}
413
414#[no_mangle]
415pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceCapabilities_getBandwidthGbps0(
416    mut env: JNIEnv,
417    _class: JClass,
418    ptr: jlong,
419) -> jdouble {
420    if !check_not_null(&mut env, ptr, "RiDeviceCapabilities") {
421        return -1.0;
422    }
423    
424    let capabilities = unsafe { &*(ptr as *const RiDeviceCapabilities) };
425    capabilities.bandwidth_gbps.unwrap_or(-1.0)
426}
427
428#[no_mangle]
429pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceCapabilities_setBandwidthGbps0(
430    mut env: JNIEnv,
431    _class: JClass,
432    ptr: jlong,
433    bandwidth_gbps: jdouble,
434) {
435    if !check_not_null(&mut env, ptr, "RiDeviceCapabilities") {
436        return;
437    }
438    
439    let capabilities = unsafe { &mut *(ptr as *mut RiDeviceCapabilities) };
440    capabilities.bandwidth_gbps = Some(bandwidth_gbps);
441}
442
443#[no_mangle]
444pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceCapabilities_meetsRequirements0(
445    mut env: JNIEnv,
446    _class: JClass,
447    ptr: jlong,
448    requirements_ptr: jlong,
449) -> jboolean {
450    if !check_not_null(&mut env, ptr, "RiDeviceCapabilities") || !check_not_null(&mut env, requirements_ptr, "RiDeviceCapabilities") {
451        return 0;
452    }
453    
454    let capabilities = unsafe { &*(ptr as *const RiDeviceCapabilities) };
455    let requirements = unsafe { &*(requirements_ptr as *const RiDeviceCapabilities) };
456    capabilities.meets_requirements(requirements) as jboolean
457}
458
459#[no_mangle]
460pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceCapabilities_free0(
461    _env: JNIEnv,
462    _class: JClass,
463    ptr: jlong,
464) {
465    if ptr != 0 {
466        unsafe {
467            let _ = Box::from_raw(ptr as *mut RiDeviceCapabilities);
468        }
469    }
470}
471
472// =============================================================================
473// RiDeviceHealthMetrics JNI Bindings
474// =============================================================================
475
476#[no_mangle]
477pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_new0(
478    _env: JNIEnv,
479    _class: JClass,
480) -> jlong {
481    let metrics = Box::new(RiDeviceHealthMetrics::default());
482    Box::into_raw(metrics) as jlong
483}
484
485#[no_mangle]
486pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_getCpuUsagePercent0(
487    mut env: JNIEnv,
488    _class: JClass,
489    ptr: jlong,
490) -> jdouble {
491    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
492        return 0.0;
493    }
494    
495    let metrics = unsafe { &*(ptr as *const RiDeviceHealthMetrics) };
496    metrics.cpu_usage_percent
497}
498
499#[no_mangle]
500pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_setCpuUsagePercent0(
501    mut env: JNIEnv,
502    _class: JClass,
503    ptr: jlong,
504    percent: jdouble,
505) {
506    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
507        return;
508    }
509    
510    let metrics = unsafe { &mut *(ptr as *mut RiDeviceHealthMetrics) };
511    metrics.cpu_usage_percent = percent;
512}
513
514#[no_mangle]
515pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_getMemoryUsagePercent0(
516    mut env: JNIEnv,
517    _class: JClass,
518    ptr: jlong,
519) -> jdouble {
520    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
521        return 0.0;
522    }
523    
524    let metrics = unsafe { &*(ptr as *const RiDeviceHealthMetrics) };
525    metrics.memory_usage_percent
526}
527
528#[no_mangle]
529pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_setMemoryUsagePercent0(
530    mut env: JNIEnv,
531    _class: JClass,
532    ptr: jlong,
533    percent: jdouble,
534) {
535    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
536        return;
537    }
538    
539    let metrics = unsafe { &mut *(ptr as *mut RiDeviceHealthMetrics) };
540    metrics.memory_usage_percent = percent;
541}
542
543#[no_mangle]
544pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_getTemperatureCelsius0(
545    mut env: JNIEnv,
546    _class: JClass,
547    ptr: jlong,
548) -> jdouble {
549    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
550        return 0.0;
551    }
552    
553    let metrics = unsafe { &*(ptr as *const RiDeviceHealthMetrics) };
554    metrics.temperature_celsius
555}
556
557#[no_mangle]
558pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_setTemperatureCelsius0(
559    mut env: JNIEnv,
560    _class: JClass,
561    ptr: jlong,
562    temperature: jdouble,
563) {
564    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
565        return;
566    }
567    
568    let metrics = unsafe { &mut *(ptr as *mut RiDeviceHealthMetrics) };
569    metrics.temperature_celsius = temperature;
570}
571
572#[no_mangle]
573pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_getErrorCount0(
574    mut env: JNIEnv,
575    _class: JClass,
576    ptr: jlong,
577) -> jlong {
578    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
579        return 0;
580    }
581    
582    let metrics = unsafe { &*(ptr as *const RiDeviceHealthMetrics) };
583    metrics.error_count as jlong
584}
585
586#[no_mangle]
587pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_setErrorCount0(
588    mut env: JNIEnv,
589    _class: JClass,
590    ptr: jlong,
591    count: jlong,
592) {
593    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
594        return;
595    }
596    
597    let metrics = unsafe { &mut *(ptr as *mut RiDeviceHealthMetrics) };
598    metrics.error_count = count as u32;
599}
600
601#[no_mangle]
602pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_getThroughput0(
603    mut env: JNIEnv,
604    _class: JClass,
605    ptr: jlong,
606) -> jlong {
607    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
608        return 0;
609    }
610    
611    let metrics = unsafe { &*(ptr as *const RiDeviceHealthMetrics) };
612    metrics.throughput as jlong
613}
614
615#[no_mangle]
616pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_setThroughput0(
617    mut env: JNIEnv,
618    _class: JClass,
619    ptr: jlong,
620    throughput: jlong,
621) {
622    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
623        return;
624    }
625    
626    let metrics = unsafe { &mut *(ptr as *mut RiDeviceHealthMetrics) };
627    metrics.throughput = throughput as u64;
628}
629
630#[no_mangle]
631pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_getNetworkLatencyMs0(
632    mut env: JNIEnv,
633    _class: JClass,
634    ptr: jlong,
635) -> jdouble {
636    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
637        return 0.0;
638    }
639    
640    let metrics = unsafe { &*(ptr as *const RiDeviceHealthMetrics) };
641    metrics.network_latency_ms
642}
643
644#[no_mangle]
645pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_setNetworkLatencyMs0(
646    mut env: JNIEnv,
647    _class: JClass,
648    ptr: jlong,
649    latency_ms: jdouble,
650) {
651    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
652        return;
653    }
654    
655    let metrics = unsafe { &mut *(ptr as *mut RiDeviceHealthMetrics) };
656    metrics.network_latency_ms = latency_ms;
657}
658
659#[no_mangle]
660pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_getDiskIops0(
661    mut env: JNIEnv,
662    _class: JClass,
663    ptr: jlong,
664) -> jlong {
665    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
666        return 0;
667    }
668    
669    let metrics = unsafe { &*(ptr as *const RiDeviceHealthMetrics) };
670    metrics.disk_iops as jlong
671}
672
673#[no_mangle]
674pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_setDiskIops0(
675    mut env: JNIEnv,
676    _class: JClass,
677    ptr: jlong,
678    iops: jlong,
679) {
680    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
681        return;
682    }
683    
684    let metrics = unsafe { &mut *(ptr as *mut RiDeviceHealthMetrics) };
685    metrics.disk_iops = iops as u64;
686}
687
688#[no_mangle]
689pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_getResponseTimeMs0(
690    mut env: JNIEnv,
691    _class: JClass,
692    ptr: jlong,
693) -> jdouble {
694    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
695        return 0.0;
696    }
697    
698    let metrics = unsafe { &*(ptr as *const RiDeviceHealthMetrics) };
699    metrics.response_time_ms
700}
701
702#[no_mangle]
703pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_setResponseTimeMs0(
704    mut env: JNIEnv,
705    _class: JClass,
706    ptr: jlong,
707    response_time_ms: jdouble,
708) {
709    if !check_not_null(&mut env, ptr, "RiDeviceHealthMetrics") {
710        return;
711    }
712    
713    let metrics = unsafe { &mut *(ptr as *mut RiDeviceHealthMetrics) };
714    metrics.response_time_ms = response_time_ms;
715}
716
717#[no_mangle]
718pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceHealthMetrics_free0(
719    _env: JNIEnv,
720    _class: JClass,
721    ptr: jlong,
722) {
723    if ptr != 0 {
724        unsafe {
725            let _ = Box::from_raw(ptr as *mut RiDeviceHealthMetrics);
726        }
727    }
728}
729
730// =============================================================================
731// RiDeviceConfig JNI Bindings
732// =============================================================================
733
734#[no_mangle]
735pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceConfig_new0(
736    _env: JNIEnv,
737    _class: JClass,
738) -> jlong {
739    let config = Box::new(RiDeviceConfig::default());
740    Box::into_raw(config) as jlong
741}
742
743#[no_mangle]
744pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceConfig_isCpuDiscoveryEnabled0(
745    mut env: JNIEnv,
746    _class: JClass,
747    ptr: jlong,
748) -> jboolean {
749    if !check_not_null(&mut env, ptr, "RiDeviceConfig") {
750        return 0;
751    }
752    
753    let config = unsafe { &*(ptr as *const RiDeviceConfig) };
754    config.enable_cpu_discovery as jboolean
755}
756
757#[no_mangle]
758pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceConfig_setCpuDiscoveryEnabled0(
759    mut env: JNIEnv,
760    _class: JClass,
761    ptr: jlong,
762    enabled: jboolean,
763) {
764    if !check_not_null(&mut env, ptr, "RiDeviceConfig") {
765        return;
766    }
767    
768    let config = unsafe { &mut *(ptr as *mut RiDeviceConfig) };
769    config.enable_cpu_discovery = enabled != 0;
770}
771
772#[no_mangle]
773pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceConfig_isGpuDiscoveryEnabled0(
774    mut env: JNIEnv,
775    _class: JClass,
776    ptr: jlong,
777) -> jboolean {
778    if !check_not_null(&mut env, ptr, "RiDeviceConfig") {
779        return 0;
780    }
781    
782    let config = unsafe { &*(ptr as *const RiDeviceConfig) };
783    config.enable_gpu_discovery as jboolean
784}
785
786#[no_mangle]
787pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceConfig_setGpuDiscoveryEnabled0(
788    mut env: JNIEnv,
789    _class: JClass,
790    ptr: jlong,
791    enabled: jboolean,
792) {
793    if !check_not_null(&mut env, ptr, "RiDeviceConfig") {
794        return;
795    }
796    
797    let config = unsafe { &mut *(ptr as *mut RiDeviceConfig) };
798    config.enable_gpu_discovery = enabled != 0;
799}
800
801#[no_mangle]
802pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceConfig_getDiscoveryTimeoutSecs0(
803    mut env: JNIEnv,
804    _class: JClass,
805    ptr: jlong,
806) -> jlong {
807    if !check_not_null(&mut env, ptr, "RiDeviceConfig") {
808        return 0;
809    }
810    
811    let config = unsafe { &*(ptr as *const RiDeviceConfig) };
812    config.discovery_timeout_secs as jlong
813}
814
815#[no_mangle]
816pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceConfig_setDiscoveryTimeoutSecs0(
817    mut env: JNIEnv,
818    _class: JClass,
819    ptr: jlong,
820    timeout_secs: jlong,
821) {
822    if !check_not_null(&mut env, ptr, "RiDeviceConfig") {
823        return;
824    }
825    
826    let config = unsafe { &mut *(ptr as *mut RiDeviceConfig) };
827    config.discovery_timeout_secs = timeout_secs as u64;
828}
829
830#[no_mangle]
831pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceConfig_getMaxDevicesPerType0(
832    mut env: JNIEnv,
833    _class: JClass,
834    ptr: jlong,
835) -> jint {
836    if !check_not_null(&mut env, ptr, "RiDeviceConfig") {
837        return 0;
838    }
839    
840    let config = unsafe { &*(ptr as *const RiDeviceConfig) };
841    config.max_devices_per_type as jint
842}
843
844#[no_mangle]
845pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceConfig_setMaxDevicesPerType0(
846    mut env: JNIEnv,
847    _class: JClass,
848    ptr: jlong,
849    max: jint,
850) {
851    if !check_not_null(&mut env, ptr, "RiDeviceConfig") {
852        return;
853    }
854    
855    let config = unsafe { &mut *(ptr as *mut RiDeviceConfig) };
856    config.max_devices_per_type = max as usize;
857}
858
859#[no_mangle]
860pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceConfig_free0(
861    _env: JNIEnv,
862    _class: JClass,
863    ptr: jlong,
864) {
865    if ptr != 0 {
866        unsafe {
867            let _ = Box::from_raw(ptr as *mut RiDeviceConfig);
868        }
869    }
870}
871
872// =============================================================================
873// RiDeviceSchedulingConfig JNI Bindings
874// =============================================================================
875
876#[no_mangle]
877pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_new0(
878    _env: JNIEnv,
879    _class: JClass,
880) -> jlong {
881    let config = Box::new(RiDeviceSchedulingConfig::default());
882    Box::into_raw(config) as jlong
883}
884
885#[no_mangle]
886pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_isDiscoveryEnabled0(
887    mut env: JNIEnv,
888    _class: JClass,
889    ptr: jlong,
890) -> jboolean {
891    if !check_not_null(&mut env, ptr, "RiDeviceSchedulingConfig") {
892        return 0;
893    }
894    
895    let config = unsafe { &*(ptr as *const RiDeviceSchedulingConfig) };
896    config.discovery_enabled as jboolean
897}
898
899#[no_mangle]
900pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_setDiscoveryEnabled0(
901    mut env: JNIEnv,
902    _class: JClass,
903    ptr: jlong,
904    enabled: jboolean,
905) {
906    if !check_not_null(&mut env, ptr, "RiDeviceSchedulingConfig") {
907        return;
908    }
909    
910    let config = unsafe { &mut *(ptr as *mut RiDeviceSchedulingConfig) };
911    config.discovery_enabled = enabled != 0;
912}
913
914#[no_mangle]
915pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_getDiscoveryIntervalSecs0(
916    mut env: JNIEnv,
917    _class: JClass,
918    ptr: jlong,
919) -> jlong {
920    if !check_not_null(&mut env, ptr, "RiDeviceSchedulingConfig") {
921        return 0;
922    }
923    
924    let config = unsafe { &*(ptr as *const RiDeviceSchedulingConfig) };
925    config.discovery_interval_secs as jlong
926}
927
928#[no_mangle]
929pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_setDiscoveryIntervalSecs0(
930    mut env: JNIEnv,
931    _class: JClass,
932    ptr: jlong,
933    interval_secs: jlong,
934) {
935    if !check_not_null(&mut env, ptr, "RiDeviceSchedulingConfig") {
936        return;
937    }
938    
939    let config = unsafe { &mut *(ptr as *mut RiDeviceSchedulingConfig) };
940    config.discovery_interval_secs = interval_secs as u64;
941}
942
943#[no_mangle]
944pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_isAutoSchedulingEnabled0(
945    mut env: JNIEnv,
946    _class: JClass,
947    ptr: jlong,
948) -> jboolean {
949    if !check_not_null(&mut env, ptr, "RiDeviceSchedulingConfig") {
950        return 0;
951    }
952    
953    let config = unsafe { &*(ptr as *const RiDeviceSchedulingConfig) };
954    config.auto_scheduling_enabled as jboolean
955}
956
957#[no_mangle]
958pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_setAutoSchedulingEnabled0(
959    mut env: JNIEnv,
960    _class: JClass,
961    ptr: jlong,
962    enabled: jboolean,
963) {
964    if !check_not_null(&mut env, ptr, "RiDeviceSchedulingConfig") {
965        return;
966    }
967    
968    let config = unsafe { &mut *(ptr as *mut RiDeviceSchedulingConfig) };
969    config.auto_scheduling_enabled = enabled != 0;
970}
971
972#[no_mangle]
973pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_getMaxConcurrentTasks0(
974    mut env: JNIEnv,
975    _class: JClass,
976    ptr: jlong,
977) -> jint {
978    if !check_not_null(&mut env, ptr, "RiDeviceSchedulingConfig") {
979        return 0;
980    }
981    
982    let config = unsafe { &*(ptr as *const RiDeviceSchedulingConfig) };
983    config.max_concurrent_tasks as jint
984}
985
986#[no_mangle]
987pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_setMaxConcurrentTasks0(
988    mut env: JNIEnv,
989    _class: JClass,
990    ptr: jlong,
991    max: jint,
992) {
993    if !check_not_null(&mut env, ptr, "RiDeviceSchedulingConfig") {
994        return;
995    }
996    
997    let config = unsafe { &mut *(ptr as *mut RiDeviceSchedulingConfig) };
998    config.max_concurrent_tasks = max as usize;
999}
1000
1001#[no_mangle]
1002pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_getResourceAllocationTimeoutSecs0(
1003    mut env: JNIEnv,
1004    _class: JClass,
1005    ptr: jlong,
1006) -> jlong {
1007    if !check_not_null(&mut env, ptr, "RiDeviceSchedulingConfig") {
1008        return 0;
1009    }
1010    
1011    let config = unsafe { &*(ptr as *const RiDeviceSchedulingConfig) };
1012    config.resource_allocation_timeout_secs as jlong
1013}
1014
1015#[no_mangle]
1016pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_setResourceAllocationTimeoutSecs0(
1017    mut env: JNIEnv,
1018    _class: JClass,
1019    ptr: jlong,
1020    timeout_secs: jlong,
1021) {
1022    if !check_not_null(&mut env, ptr, "RiDeviceSchedulingConfig") {
1023        return;
1024    }
1025    
1026    let config = unsafe { &mut *(ptr as *mut RiDeviceSchedulingConfig) };
1027    config.resource_allocation_timeout_secs = timeout_secs as u64;
1028}
1029
1030#[no_mangle]
1031pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceSchedulingConfig_free0(
1032    _env: JNIEnv,
1033    _class: JClass,
1034    ptr: jlong,
1035) {
1036    if ptr != 0 {
1037        unsafe {
1038            let _ = Box::from_raw(ptr as *mut RiDeviceSchedulingConfig);
1039        }
1040    }
1041}
1042
1043// =============================================================================
1044// RiNetworkDeviceInfo JNI Bindings
1045// =============================================================================
1046
1047#[no_mangle]
1048pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_new0(
1049    mut env: JNIEnv,
1050    _class: JClass,
1051    id: JString,
1052    device_type: JString,
1053    source: JString,
1054) -> jlong {
1055    let id_str: String = match env.get_string(&id) {
1056        Ok(s) => s.into(),
1057        Err(_) => {
1058            crate::java::exception::throw_ri_error(&mut env, "Invalid id string");
1059            return 0;
1060        }
1061    };
1062    let device_type_str: String = match env.get_string(&device_type) {
1063        Ok(s) => s.into(),
1064        Err(_) => {
1065            crate::java::exception::throw_ri_error(&mut env, "Invalid device_type string");
1066            return 0;
1067        }
1068    };
1069    let source_str: String = match env.get_string(&source) {
1070        Ok(s) => s.into(),
1071        Err(_) => {
1072            crate::java::exception::throw_ri_error(&mut env, "Invalid source string");
1073            return 0;
1074        }
1075    };
1076    
1077    let info = Box::new(RiNetworkDeviceInfo {
1078        id: id_str,
1079        device_type: device_type_str,
1080        source: source_str,
1081        compute_units: None,
1082        memory_gb: None,
1083        storage_gb: None,
1084        bandwidth_gbps: None,
1085    });
1086    Box::into_raw(info) as jlong
1087}
1088
1089#[no_mangle]
1090pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_getId0<'local>(
1091    mut env: JNIEnv<'local>,
1092    _class: JClass<'local>,
1093    ptr: jlong,
1094) -> jstring {
1095    if !check_not_null(&mut env, ptr, "RiNetworkDeviceInfo") {
1096        return std::ptr::null_mut();
1097    }
1098    
1099    let info = unsafe { &*(ptr as *const RiNetworkDeviceInfo) };
1100    match env.new_string(&info.id) {
1101            Ok(s) => s.into_raw(),
1102            Err(_) => std::ptr::null_mut(),
1103        }
1104}
1105
1106#[no_mangle]
1107pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_getDeviceType0<'local>(
1108    mut env: JNIEnv<'local>,
1109    _class: JClass<'local>,
1110    ptr: jlong,
1111) -> jstring {
1112    if !check_not_null(&mut env, ptr, "RiNetworkDeviceInfo") {
1113        return std::ptr::null_mut();
1114    }
1115    
1116    let info = unsafe { &*(ptr as *const RiNetworkDeviceInfo) };
1117    match env.new_string(&info.device_type) {
1118            Ok(s) => s.into_raw(),
1119            Err(_) => std::ptr::null_mut(),
1120        }
1121}
1122
1123#[no_mangle]
1124pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_getSource0<'local>(
1125    mut env: JNIEnv<'local>,
1126    _class: JClass<'local>,
1127    ptr: jlong,
1128) -> jstring {
1129    if !check_not_null(&mut env, ptr, "RiNetworkDeviceInfo") {
1130        return std::ptr::null_mut();
1131    }
1132    
1133    let info = unsafe { &*(ptr as *const RiNetworkDeviceInfo) };
1134    match env.new_string(&info.source) {
1135            Ok(s) => s.into_raw(),
1136            Err(_) => std::ptr::null_mut(),
1137        }
1138}
1139
1140#[no_mangle]
1141pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_getComputeUnits0(
1142    mut env: JNIEnv,
1143    _class: JClass,
1144    ptr: jlong,
1145) -> jint {
1146    if !check_not_null(&mut env, ptr, "RiNetworkDeviceInfo") {
1147        return -1;
1148    }
1149    
1150    let info = unsafe { &*(ptr as *const RiNetworkDeviceInfo) };
1151    info.compute_units.map(|v| v as jint).unwrap_or(-1)
1152}
1153
1154#[no_mangle]
1155pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_setComputeUnits0(
1156    mut env: JNIEnv,
1157    _class: JClass,
1158    ptr: jlong,
1159    units: jint,
1160) {
1161    if !check_not_null(&mut env, ptr, "RiNetworkDeviceInfo") {
1162        return;
1163    }
1164    
1165    let info = unsafe { &mut *(ptr as *mut RiNetworkDeviceInfo) };
1166    info.compute_units = Some(units as usize);
1167}
1168
1169#[no_mangle]
1170pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_getMemoryGb0(
1171    mut env: JNIEnv,
1172    _class: JClass,
1173    ptr: jlong,
1174) -> jdouble {
1175    if !check_not_null(&mut env, ptr, "RiNetworkDeviceInfo") {
1176        return -1.0;
1177    }
1178    
1179    let info = unsafe { &*(ptr as *const RiNetworkDeviceInfo) };
1180    info.memory_gb.unwrap_or(-1.0)
1181}
1182
1183#[no_mangle]
1184pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_setMemoryGb0(
1185    mut env: JNIEnv,
1186    _class: JClass,
1187    ptr: jlong,
1188    memory_gb: jdouble,
1189) {
1190    if !check_not_null(&mut env, ptr, "RiNetworkDeviceInfo") {
1191        return;
1192    }
1193    
1194    let info = unsafe { &mut *(ptr as *mut RiNetworkDeviceInfo) };
1195    info.memory_gb = Some(memory_gb);
1196}
1197
1198#[no_mangle]
1199pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_getStorageGb0(
1200    mut env: JNIEnv,
1201    _class: JClass,
1202    ptr: jlong,
1203) -> jdouble {
1204    if !check_not_null(&mut env, ptr, "RiNetworkDeviceInfo") {
1205        return -1.0;
1206    }
1207    
1208    let info = unsafe { &*(ptr as *const RiNetworkDeviceInfo) };
1209    info.storage_gb.unwrap_or(-1.0)
1210}
1211
1212#[no_mangle]
1213pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_setStorageGb0(
1214    mut env: JNIEnv,
1215    _class: JClass,
1216    ptr: jlong,
1217    storage_gb: jdouble,
1218) {
1219    if !check_not_null(&mut env, ptr, "RiNetworkDeviceInfo") {
1220        return;
1221    }
1222    
1223    let info = unsafe { &mut *(ptr as *mut RiNetworkDeviceInfo) };
1224    info.storage_gb = Some(storage_gb);
1225}
1226
1227#[no_mangle]
1228pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_getBandwidthGbps0(
1229    mut env: JNIEnv,
1230    _class: JClass,
1231    ptr: jlong,
1232) -> jdouble {
1233    if !check_not_null(&mut env, ptr, "RiNetworkDeviceInfo") {
1234        return -1.0;
1235    }
1236    
1237    let info = unsafe { &*(ptr as *const RiNetworkDeviceInfo) };
1238    info.bandwidth_gbps.unwrap_or(-1.0)
1239}
1240
1241#[no_mangle]
1242pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_setBandwidthGbps0(
1243    mut env: JNIEnv,
1244    _class: JClass,
1245    ptr: jlong,
1246    bandwidth_gbps: jdouble,
1247) {
1248    if !check_not_null(&mut env, ptr, "RiNetworkDeviceInfo") {
1249        return;
1250    }
1251    
1252    let info = unsafe { &mut *(ptr as *mut RiNetworkDeviceInfo) };
1253    info.bandwidth_gbps = Some(bandwidth_gbps);
1254}
1255
1256#[no_mangle]
1257pub extern "system" fn Java_com_dunimd_ri_device_RiNetworkDeviceInfo_free0(
1258    _env: JNIEnv,
1259    _class: JClass,
1260    ptr: jlong,
1261) {
1262    if ptr != 0 {
1263        unsafe {
1264            let _ = Box::from_raw(ptr as *mut RiNetworkDeviceInfo);
1265        }
1266    }
1267}
1268
1269// =============================================================================
1270// RiDiscoveryResult JNI Bindings
1271// =============================================================================
1272
1273#[no_mangle]
1274pub extern "system" fn Java_com_dunimd_ri_device_RiDiscoveryResult_getDiscoveredDevices0(
1275    mut env: JNIEnv,
1276    _class: JClass,
1277    ptr: jlong,
1278) -> jlongArray {
1279    if !check_not_null(&mut env, ptr, "RiDiscoveryResult") {
1280        return std::ptr::null_mut();
1281    }
1282    
1283    let result = unsafe { &*(ptr as *const RiDiscoveryResult) };
1284    let devices: Vec<jlong> = result.discovered_devices.iter().map(|_| 0 as jlong).collect();
1285    
1286    let array = match env.new_long_array(devices.len() as i32) {
1287        Ok(a) => a,
1288        Err(_) => return std::ptr::null_mut(),
1289    };
1290    let _ = env.set_long_array_region(&array, 0, &devices);
1291    array.into_raw()
1292}
1293
1294#[no_mangle]
1295pub extern "system" fn Java_com_dunimd_ri_device_RiDiscoveryResult_getUpdatedDevices0(
1296    mut env: JNIEnv,
1297    _class: JClass,
1298    ptr: jlong,
1299) -> jlongArray {
1300    if !check_not_null(&mut env, ptr, "RiDiscoveryResult") {
1301        return std::ptr::null_mut();
1302    }
1303    
1304    let result = unsafe { &*(ptr as *const RiDiscoveryResult) };
1305    let devices: Vec<jlong> = result.updated_devices.iter().map(|_| 0 as jlong).collect();
1306    
1307    let array = match env.new_long_array(devices.len() as i32) {
1308        Ok(a) => a,
1309        Err(_) => return std::ptr::null_mut(),
1310    };
1311    let _ = env.set_long_array_region(&array, 0, &devices);
1312    array.into_raw()
1313}
1314
1315#[no_mangle]
1316pub extern "system" fn Java_com_dunimd_ri_device_RiDiscoveryResult_getRemovedDevices0(
1317    mut env: JNIEnv,
1318    _class: JClass,
1319    ptr: jlong,
1320) -> jobjectArray {
1321    if !check_not_null(&mut env, ptr, "RiDiscoveryResult") {
1322        return std::ptr::null_mut();
1323    }
1324    
1325    let result = unsafe { &*(ptr as *const RiDiscoveryResult) };
1326    let string_class = match env.find_class("java/lang/String") {
1327        Ok(c) => c,
1328        Err(_) => return std::ptr::null_mut(),
1329    };
1330    let array = match env.new_object_array(result.removed_devices.len() as i32, string_class, JObject::null()) {
1331        Ok(a) => a,
1332        Err(_) => return std::ptr::null_mut(),
1333    };
1334    
1335    for (i, id) in result.removed_devices.iter().enumerate() {
1336        let jstr = match env.new_string(id) {
1337            Ok(s) => s,
1338            Err(_) => continue,
1339        };
1340        let _ = env.set_object_array_element(&array, i as i32, jstr);
1341    }
1342    
1343    array.into_raw()
1344}
1345
1346#[no_mangle]
1347pub extern "system" fn Java_com_dunimd_ri_device_RiDiscoveryResult_getTotalDevices0(
1348    mut env: JNIEnv,
1349    _class: JClass,
1350    ptr: jlong,
1351) -> jint {
1352    if !check_not_null(&mut env, ptr, "RiDiscoveryResult") {
1353        return 0;
1354    }
1355    
1356    let result = unsafe { &*(ptr as *const RiDiscoveryResult) };
1357    result.total_devices as jint
1358}
1359
1360#[no_mangle]
1361pub extern "system" fn Java_com_dunimd_ri_device_RiDiscoveryResult_free0(
1362    _env: JNIEnv,
1363    _class: JClass,
1364    ptr: jlong,
1365) {
1366    if ptr != 0 {
1367        unsafe {
1368            let _ = Box::from_raw(ptr as *mut RiDiscoveryResult);
1369        }
1370    }
1371}
1372
1373// =============================================================================
1374// RiResourceRequest JNI Bindings
1375// =============================================================================
1376
1377#[no_mangle]
1378pub extern "system" fn Java_com_dunimd_ri_device_RiResourceRequest_new0(
1379    mut env: JNIEnv,
1380    _class: JClass,
1381    request_id: JString,
1382    device_type: jint,
1383    capabilities_ptr: jlong,
1384) -> jlong {
1385    let request_id_str: String = match env.get_string(&request_id) {
1386        Ok(s) => s.into(),
1387        Err(_) => {
1388            crate::java::exception::throw_ri_error(&mut env, "Invalid request_id string");
1389            return 0;
1390        }
1391    };
1392    
1393    let dtype = match device_type {
1394        0 => RiDeviceType::CPU,
1395        1 => RiDeviceType::GPU,
1396        2 => RiDeviceType::Memory,
1397        3 => RiDeviceType::Storage,
1398        4 => RiDeviceType::Network,
1399        5 => RiDeviceType::Sensor,
1400        6 => RiDeviceType::Actuator,
1401        _ => RiDeviceType::Custom,
1402    };
1403    
1404    let capabilities = if capabilities_ptr != 0 {
1405        unsafe { &*(capabilities_ptr as *const RiDeviceCapabilities) }.clone()
1406    } else {
1407        RiDeviceCapabilities::new()
1408    };
1409    
1410    let request = Box::new(RiResourceRequest {
1411        request_id: request_id_str,
1412        device_type: dtype,
1413        required_capabilities: capabilities,
1414        priority: 5,
1415        timeout_secs: 60,
1416        sla_class: None,
1417        resource_weights: None,
1418        affinity: None,
1419        anti_affinity: None,
1420    });
1421    Box::into_raw(request) as jlong
1422}
1423
1424#[no_mangle]
1425pub extern "system" fn Java_com_dunimd_ri_device_RiResourceRequest_getRequestId0<'local>(
1426    mut env: JNIEnv<'local>,
1427    _class: JClass<'local>,
1428    ptr: jlong,
1429) -> jstring {
1430    if !check_not_null(&mut env, ptr, "RiResourceRequest") {
1431        return std::ptr::null_mut();
1432    }
1433    
1434    let request = unsafe { &*(ptr as *const RiResourceRequest) };
1435    match env.new_string(&request.request_id) {
1436            Ok(s) => s.into_raw(),
1437            Err(_) => std::ptr::null_mut(),
1438        }
1439}
1440
1441#[no_mangle]
1442pub extern "system" fn Java_com_dunimd_ri_device_RiResourceRequest_getDeviceType0(
1443    mut env: JNIEnv,
1444    _class: JClass,
1445    ptr: jlong,
1446) -> jint {
1447    if !check_not_null(&mut env, ptr, "RiResourceRequest") {
1448        return 0;
1449    }
1450    
1451    let request = unsafe { &*(ptr as *const RiResourceRequest) };
1452    request.device_type as jint
1453}
1454
1455#[no_mangle]
1456pub extern "system" fn Java_com_dunimd_ri_device_RiResourceRequest_getRequiredCapabilities0(
1457    mut env: JNIEnv,
1458    _class: JClass,
1459    ptr: jlong,
1460) -> jlong {
1461    if !check_not_null(&mut env, ptr, "RiResourceRequest") {
1462        return 0;
1463    }
1464    
1465    let request = unsafe { &*(ptr as *const RiResourceRequest) };
1466    let capabilities = Box::new(request.required_capabilities.clone());
1467    Box::into_raw(capabilities) as jlong
1468}
1469
1470#[no_mangle]
1471pub extern "system" fn Java_com_dunimd_ri_device_RiResourceRequest_getPriority0(
1472    mut env: JNIEnv,
1473    _class: JClass,
1474    ptr: jlong,
1475) -> jint {
1476    if !check_not_null(&mut env, ptr, "RiResourceRequest") {
1477        return 0;
1478    }
1479    
1480    let request = unsafe { &*(ptr as *const RiResourceRequest) };
1481    request.priority as jint
1482}
1483
1484#[no_mangle]
1485pub extern "system" fn Java_com_dunimd_ri_device_RiResourceRequest_setPriority0(
1486    mut env: JNIEnv,
1487    _class: JClass,
1488    ptr: jlong,
1489    priority: jint,
1490) {
1491    if !check_not_null(&mut env, ptr, "RiResourceRequest") {
1492        return;
1493    }
1494    
1495    let request = unsafe { &mut *(ptr as *mut RiResourceRequest) };
1496    request.priority = priority as u8;
1497}
1498
1499#[no_mangle]
1500pub extern "system" fn Java_com_dunimd_ri_device_RiResourceRequest_getTimeoutSecs0(
1501    mut env: JNIEnv,
1502    _class: JClass,
1503    ptr: jlong,
1504) -> jlong {
1505    if !check_not_null(&mut env, ptr, "RiResourceRequest") {
1506        return 0;
1507    }
1508    
1509    let request = unsafe { &*(ptr as *const RiResourceRequest) };
1510    request.timeout_secs as jlong
1511}
1512
1513#[no_mangle]
1514pub extern "system" fn Java_com_dunimd_ri_device_RiResourceRequest_setTimeoutSecs0(
1515    mut env: JNIEnv,
1516    _class: JClass,
1517    ptr: jlong,
1518    timeout_secs: jlong,
1519) {
1520    if !check_not_null(&mut env, ptr, "RiResourceRequest") {
1521        return;
1522    }
1523    
1524    let request = unsafe { &mut *(ptr as *mut RiResourceRequest) };
1525    request.timeout_secs = timeout_secs as u64;
1526}
1527
1528#[no_mangle]
1529pub extern "system" fn Java_com_dunimd_ri_device_RiResourceRequest_free0(
1530    _env: JNIEnv,
1531    _class: JClass,
1532    ptr: jlong,
1533) {
1534    if ptr != 0 {
1535        unsafe {
1536            let _ = Box::from_raw(ptr as *mut RiResourceRequest);
1537        }
1538    }
1539}
1540
1541// =============================================================================
1542// RiResourceAllocation JNI Bindings
1543// =============================================================================
1544
1545#[no_mangle]
1546pub extern "system" fn Java_com_dunimd_ri_device_RiResourceAllocation_getAllocationId0<'local>(
1547    mut env: JNIEnv<'local>,
1548    _class: JClass<'local>,
1549    ptr: jlong,
1550) -> jstring {
1551    if !check_not_null(&mut env, ptr, "RiResourceAllocation") {
1552        return std::ptr::null_mut();
1553    }
1554    
1555    let allocation = unsafe { &*(ptr as *const RiResourceAllocation) };
1556    match env.new_string(&allocation.allocation_id) {
1557            Ok(s) => s.into_raw(),
1558            Err(_) => std::ptr::null_mut(),
1559        }
1560}
1561
1562#[no_mangle]
1563pub extern "system" fn Java_com_dunimd_ri_device_RiResourceAllocation_getDeviceId0<'local>(
1564    mut env: JNIEnv<'local>,
1565    _class: JClass<'local>,
1566    ptr: jlong,
1567) -> jstring {
1568    if !check_not_null(&mut env, ptr, "RiResourceAllocation") {
1569        return std::ptr::null_mut();
1570    }
1571    
1572    let allocation = unsafe { &*(ptr as *const RiResourceAllocation) };
1573    match env.new_string(&allocation.device_id) {
1574            Ok(s) => s.into_raw(),
1575            Err(_) => std::ptr::null_mut(),
1576        }
1577}
1578
1579#[no_mangle]
1580pub extern "system" fn Java_com_dunimd_ri_device_RiResourceAllocation_getDeviceName0<'local>(
1581    mut env: JNIEnv<'local>,
1582    _class: JClass<'local>,
1583    ptr: jlong,
1584) -> jstring {
1585    if !check_not_null(&mut env, ptr, "RiResourceAllocation") {
1586        return std::ptr::null_mut();
1587    }
1588    
1589    let allocation = unsafe { &*(ptr as *const RiResourceAllocation) };
1590    match env.new_string(&allocation.device_name) {
1591            Ok(s) => s.into_raw(),
1592            Err(_) => std::ptr::null_mut(),
1593        }
1594}
1595
1596#[no_mangle]
1597pub extern "system" fn Java_com_dunimd_ri_device_RiResourceAllocation_getAllocatedAt0<'local>(
1598    mut env: JNIEnv<'local>,
1599    _class: JClass<'local>,
1600    ptr: jlong,
1601) -> jstring {
1602    if !check_not_null(&mut env, ptr, "RiResourceAllocation") {
1603        return std::ptr::null_mut();
1604    }
1605    
1606    let allocation = unsafe { &*(ptr as *const RiResourceAllocation) };
1607    match env.new_string(&allocation.allocated_at.to_rfc3339()) {
1608            Ok(s) => s.into_raw(),
1609            Err(_) => std::ptr::null_mut(),
1610        }
1611}
1612
1613#[no_mangle]
1614pub extern "system" fn Java_com_dunimd_ri_device_RiResourceAllocation_getExpiresAt0<'local>(
1615    mut env: JNIEnv<'local>,
1616    _class: JClass<'local>,
1617    ptr: jlong,
1618) -> jstring {
1619    if !check_not_null(&mut env, ptr, "RiResourceAllocation") {
1620        return std::ptr::null_mut();
1621    }
1622    
1623    let allocation = unsafe { &*(ptr as *const RiResourceAllocation) };
1624    match env.new_string(&allocation.expires_at.to_rfc3339()) {
1625            Ok(s) => s.into_raw(),
1626            Err(_) => std::ptr::null_mut(),
1627        }
1628}
1629
1630#[no_mangle]
1631pub extern "system" fn Java_com_dunimd_ri_device_RiResourceAllocation_isExpired0(
1632    mut env: JNIEnv,
1633    _class: JClass,
1634    ptr: jlong,
1635) -> jboolean {
1636    if !check_not_null(&mut env, ptr, "RiResourceAllocation") {
1637        return 1;
1638    }
1639    
1640    let allocation = unsafe { &*(ptr as *const RiResourceAllocation) };
1641    (chrono::Utc::now() > allocation.expires_at) as jboolean
1642}
1643
1644#[no_mangle]
1645pub extern "system" fn Java_com_dunimd_ri_device_RiResourceAllocation_getRemainingTimeSecs0(
1646    mut env: JNIEnv,
1647    _class: JClass,
1648    ptr: jlong,
1649) -> jlong {
1650    if !check_not_null(&mut env, ptr, "RiResourceAllocation") {
1651        return 0;
1652    }
1653    
1654    let allocation = unsafe { &*(ptr as *const RiResourceAllocation) };
1655    (allocation.expires_at - chrono::Utc::now()).num_seconds().max(0) as jlong
1656}
1657
1658#[no_mangle]
1659pub extern "system" fn Java_com_dunimd_ri_device_RiResourceAllocation_getRequest0(
1660    mut env: JNIEnv,
1661    _class: JClass,
1662    ptr: jlong,
1663) -> jlong {
1664    if !check_not_null(&mut env, ptr, "RiResourceAllocation") {
1665        return 0;
1666    }
1667    
1668    let allocation = unsafe { &*(ptr as *const RiResourceAllocation) };
1669    let request = Box::new(allocation.request.clone());
1670    Box::into_raw(request) as jlong
1671}
1672
1673#[no_mangle]
1674pub extern "system" fn Java_com_dunimd_ri_device_RiResourceAllocation_free0(
1675    _env: JNIEnv,
1676    _class: JClass,
1677    ptr: jlong,
1678) {
1679    if ptr != 0 {
1680        unsafe {
1681            let _ = Box::from_raw(ptr as *mut RiResourceAllocation);
1682        }
1683    }
1684}
1685
1686// =============================================================================
1687// RiDeviceController JNI Bindings
1688// =============================================================================
1689
1690#[no_mangle]
1691pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceController_new0(
1692    _env: JNIEnv,
1693    _class: JClass,
1694) -> jlong {
1695    Box::into_raw(Box::new(RiDeviceController::new())) as jlong
1696}
1697
1698#[no_mangle]
1699pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceController_getAllDevices0(
1700    mut env: JNIEnv,
1701    _class: JClass,
1702    ptr: jlong,
1703) -> jlongArray {
1704    if !check_not_null(&mut env, ptr, "RiDeviceController") {
1705        return std::ptr::null_mut();
1706    }
1707
1708    let controller = unsafe { &*(ptr as *const RiDeviceController) };
1709    let devices = controller.get_all_devices();
1710
1711    // Each device is boxed into its own native pointer owned by the Java wrapper.
1712    let ptrs: Vec<jlong> = devices
1713        .into_iter()
1714        .map(|d| Box::into_raw(Box::new(d)) as jlong)
1715        .collect();
1716
1717    match env.new_long_array(ptrs.len() as i32) {
1718        Ok(array) => {
1719            if ptrs.is_empty() {
1720                return array.into_raw();
1721            }
1722            match env.set_long_array_region(&array, 0, &ptrs) {
1723                Ok(()) => array.into_raw(),
1724                Err(_) => std::ptr::null_mut(),
1725            }
1726        }
1727        Err(_) => std::ptr::null_mut(),
1728    }
1729}
1730
1731#[no_mangle]
1732pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceController_getDevice0(
1733    mut env: JNIEnv,
1734    _class: JClass,
1735    ptr: jlong,
1736    device_id: JString,
1737) -> jlong {
1738    if !check_not_null(&mut env, ptr, "RiDeviceController") {
1739        return 0;
1740    }
1741
1742    let id: String = match env.get_string(&device_id) {
1743        Ok(s) => s.into(),
1744        Err(_) => {
1745            throw_ri_error(&mut env, "Failed to read device id");
1746            return 0;
1747        }
1748    };
1749
1750    let controller = unsafe { &*(ptr as *const RiDeviceController) };
1751    match block_on_local(&mut env, "RiDeviceController::get_device", async {
1752        controller.get_device(&id).await
1753    }) {
1754        Some(Some(device)) => Box::into_raw(Box::new(device)) as jlong,
1755        Some(None) => 0,
1756        None => 0,
1757    }
1758}
1759
1760#[no_mangle]
1761pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceController_addDevice0(
1762    mut env: JNIEnv,
1763    _class: JClass,
1764    ptr: jlong,
1765    device_ptr: jlong,
1766) {
1767    if !check_not_null(&mut env, ptr, "RiDeviceController") {
1768        return;
1769    }
1770    if !check_not_null(&mut env, device_ptr, "RiDevice") {
1771        return;
1772    }
1773
1774    // Clone the device into the controller; the Java side keeps ownership of its own pointer.
1775    let device = unsafe { (*(device_ptr as *const RiDevice)).clone() };
1776    let controller = unsafe { &mut *(ptr as *mut RiDeviceController) };
1777    if let Some(result) = block_on_local(&mut env, "RiDeviceController::add_device", async {
1778        controller.add_device(device, String::new()).await
1779    }) {
1780        if let Err(e) = result {
1781            throw_ri_error(&mut env, &e.to_string());
1782        }
1783    }
1784}
1785
1786#[no_mangle]
1787pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceController_removeDevice0(
1788    mut env: JNIEnv,
1789    _class: JClass,
1790    ptr: jlong,
1791    device_id: JString,
1792) -> jboolean {
1793    if !check_not_null(&mut env, ptr, "RiDeviceController") {
1794        return 0;
1795    }
1796
1797    let id: String = match env.get_string(&device_id) {
1798        Ok(s) => s.into(),
1799        Err(_) => {
1800            throw_ri_error(&mut env, "Failed to read device id");
1801            return 0;
1802        }
1803    };
1804
1805    let controller = unsafe { &mut *(ptr as *mut RiDeviceController) };
1806    match block_on_local(&mut env, "RiDeviceController::remove_device", async {
1807        controller.remove_device(&id).await
1808    }) {
1809        Some(Ok(())) => 1,
1810        Some(Err(e)) => {
1811            throw_ri_error(&mut env, &e.to_string());
1812            0
1813        }
1814        None => 0,
1815    }
1816}
1817
1818#[no_mangle]
1819pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceController_getDeviceCount0(
1820    mut env: JNIEnv,
1821    _class: JClass,
1822    ptr: jlong,
1823) -> jint {
1824    if !check_not_null(&mut env, ptr, "RiDeviceController") {
1825        return 0;
1826    }
1827
1828    let controller = unsafe { &*(ptr as *const RiDeviceController) };
1829    controller.get_all_devices().len() as jint
1830}
1831
1832#[no_mangle]
1833pub extern "system" fn Java_com_dunimd_ri_device_RiDeviceController_free0(
1834    _env: JNIEnv,
1835    _class: JClass,
1836    ptr: jlong,
1837) {
1838    if ptr != 0 {
1839        unsafe {
1840            let _ = Box::from_raw(ptr as *mut RiDeviceController);
1841        }
1842    }
1843}