#[cfg(test)]
mod tests {
    #[test]
    fn it_works() {
        assert_eq!(2 + 2, 4);
    }
}

// use std::ffi::{CStr, CString};
// use std::os::raw::{c_char, c_uchar, c_ulong};

// #[no_mangle]
// pub extern "C" fn dlsmk_decode(
//     key: *const c_uchar,
//     qrcode: *const c_uchar,
//     qrlen: c_ulong,
// ) -> *mut c_char {
//     CString::new("Hello ".to_owned()).unwrap().into_raw()
// }

// #[cfg(target_os = "android")]
#[cfg(any(target_family = "unix", target_os = "android"))]
// #[cfg(target_family = "unix")]
#[allow(non_snake_case)]
pub mod android {
    extern crate jni;

    use self::jni::objects::{JClass, JObject, JString};
    use self::jni::sys::{jboolean, jlong, JNI_FALSE, JNI_TRUE};
    use self::jni::JNIEnv;
    // use super::*;
    use libc;
    use std::slice;

    use dlqrcode::DaliQrCode;

    #[no_mangle]
    pub unsafe extern "C" fn Java_com_supwisdom_dlsmk_DLSMKQrCode_decode(
        env: JNIEnv,
        _: JClass,
        key_hex: JString,
        qrcode: JString,
        offset: jlong,
        result: JObject,
    ) -> jboolean {
        // Our Java companion code might pass-in "world" as a string, hence the name.
        let key = env
            .get_string(key_hex)
            .expect("invalid key string")
            .as_ptr();
        let keylen = libc::strlen(key);

        println!("decode test, key length {}", keylen);
        let key = {
            let k: &[u8] = slice::from_raw_parts(key as *const u8, keylen);
            println!("key is : {}", String::from_utf8_lossy(k));
            let mut key = [0u8; 32];
            if let Ok(v) = hex::decode(k) {
                key.clone_from_slice(v.as_slice());
                key
            } else {
                return JNI_FALSE;
            }
        };

        let qrcode = env
            .get_string(qrcode)
            .expect("invalid qrcode string")
            .as_ptr();
        let qrlen = libc::strlen(qrcode);


        let decode = match DaliQrCode::new(key, None, None, None, None) {
            Ok(d) => d,
            Err(e) => panic!("invalid key {}", e),
        };

        println!("decode qrcode begin , length : {}...", qrlen);
        match decode.decode(qrcode as *const u8, qrlen, offset as i32) {
            Ok(d) => {
                let qrdata = env.get_map(result).expect("invalid qrdata map");
                qrdata
                    .put(
                        *env.new_string("cardno").unwrap(),
                        *env.new_string(d.cardno).unwrap(),
                    )
                    .unwrap();
                qrdata
                    .put(
                        *env.new_string("cardtype").unwrap(),
                        *env.new_string(d.cardtype).unwrap(),
                    )
                    .unwrap();
                qrdata
                    .put(
                        *env.new_string("uid").unwrap(),
                        *env.new_string(d.uid).unwrap(),
                    )
                    .unwrap();
                return JNI_TRUE;
            }
            Err(e) => {
                println!("Error {:?}", e);
                return JNI_FALSE;
            },
        };
    }
}
