Move to rust sha1 impl (#782)

* Move to rust sha1 impl

* Use onstack buffer

Signed-off-by: GG Bond <whatever@tagkong.com>

---------

Signed-off-by: GG Bond <whatever@tagkong.com>
Co-authored-by: GG Bond <whatever@tagkong.com>
This commit is contained in:
Vladimir DostoyevskiyandGG Bond authored and GitHub committed 2024-02-25 14:07:32 +08:00
1 parent 6a6da6f059
commit 422062226d
4 files changed
+38 -43

No files matched your search

+1 -1
View File
@@ -85,5 +85,5 @@ FetchContent_MakeAvailable(Corrosion)
corrosion_import_crate(MANIFEST_PATH ../rust/Cargo.toml)
# Build and link our app's native lib
add_library(${PROJECT_NAME} SHARED archive.c border.c gifutils.c hash.c natsort/strnatcmp.c)
add_library(${PROJECT_NAME} SHARED archive.c border.c gifutils.c natsort/strnatcmp.c)
target_link_libraries(${PROJECT_NAME} ehviewer_rust archive_static log jnigraphics)
-39
View File
@@ -1,39 +0,0 @@
#include <unistd.h>
#include <jni.h>
#include <sha1.h>
#include "ehviewer.h"
#define BUFFER_SIZE 8192
typedef uint8_t byte;
const char hex_digits[] = "0123456789abcdef";
JNIEXPORT jstring JNICALL
Java_com_hippo_ehviewer_jni_HashKt_sha1(JNIEnv *env, jclass clazz, jint fd) {
EH_UNUSED(clazz);
struct sha1_ctx ctx;
sha1_init(&ctx);
size_t bytes_read;
byte buffer[BUFFER_SIZE];
while ((bytes_read = read(fd, buffer, BUFFER_SIZE)) > 0) {
sha1_update(&ctx, bytes_read, buffer);
}
byte digest[SHA1_DIGEST_SIZE];
sha1_digest(&ctx, SHA1_DIGEST_SIZE, digest);
byte byte;
char hex_digest[2 * SHA1_DIGEST_SIZE + 1];
for (int i = 0; i < SHA1_DIGEST_SIZE; i++) {
byte = digest[i];
hex_digest[2 * i] = hex_digits[byte >> 4 & 0xF];
hex_digest[2 * i + 1] = hex_digits[byte & 0xF];
}
hex_digest[2 * SHA1_DIGEST_SIZE] = '\0';
return (*env)->NewStringUTF(env, hex_digest);
}
+2
View File
@@ -17,6 +17,8 @@ android_logger = { default-features = false, version = "0.13" }
once_cell = { default-features = false, version = "1.19" }
serde_cbor = "0.11"
serde = { version = "1.0", features = ["derive"] }
sha1 = { version = "0.10" }
base16ct = { version = "0.2" }
[profile.release]
panic = "abort"
+35 -3
View File
@@ -1,6 +1,7 @@
mod parser;
extern crate android_logger;
extern crate base16ct;
extern crate jni;
extern crate jni_fn;
extern crate log;
@@ -8,16 +9,22 @@ extern crate once_cell;
extern crate quick_xml;
extern crate regex_lite;
extern crate serde;
extern crate sha1;
extern crate tl;
use android_logger::Config;
use jni::objects::JByteBuffer;
use jni::sys::{jint, JavaVM, JNI_VERSION_1_6};
use base16ct::lower::encode_str;
use jni::objects::{JByteBuffer, JClass};
use jni::sys::{jint, jstring, JavaVM, JNI_VERSION_1_6};
use jni::JNIEnv;
use jni_fn::jni_fn;
use log::LevelFilter;
use serde::Serialize;
use sha1::{Digest, Sha1};
use std::ffi::c_void;
use std::io::Cursor;
use std::fs::File;
use std::io::{copy, Cursor};
use std::os::fd::BorrowedFd;
use std::ptr::slice_from_raw_parts_mut;
use std::str::from_utf8_unchecked;
use tl::{Bytes, Node, NodeHandle, Parser, VDom};
@@ -122,3 +129,28 @@ pub extern "system" fn JNI_OnLoad(_: JavaVM, _: *mut c_void) -> jint {
android_logger::init_once(Config::default().with_max_level(LevelFilter::Debug));
JNI_VERSION_1_6
}
#[no_mangle]
#[allow(non_snake_case)]
#[jni_fn("com.hippo.ehviewer.jni.HashKt")]
pub fn sha1(mut env: JNIEnv, _class: JClass, fd: jint) -> jstring {
let mut sha = Sha1::new();
let borrowed_fd = unsafe { BorrowedFd::borrow_raw(fd) };
let owned_fd = match borrowed_fd.try_clone_to_owned() {
Ok(fd) => fd,
Err(err) => return throw_msg(&mut env, &format!("{err}")) as jstring,
};
if let Err(err) = copy(&mut File::from(owned_fd), &mut sha) {
return throw_msg(&mut env, &format!("{err}")) as jstring;
};
let digest = sha.finalize();
let mut hex_digest = [0u8; 40];
let hex = match encode_str(&digest, &mut hex_digest) {
Ok(str) => str,
Err(err) => return throw_msg(&mut env, &format!("{err}")) as jstring,
};
match env.new_string(hex) {
Ok(obj) => obj.into_raw(),
Err(err) => throw_msg(&mut env, &format!("{err}")) as jstring,
}
}