From cbc000392d9c0d3eced4269463a0987c17e4675f Mon Sep 17 00:00:00 2001 From: Karolis Stasaitis Date: Sat, 5 Sep 2026 10:01:49 +0200 Subject: [PATCH 1/2] platform: sh68f83 --- src/isp_device.rs | 55 ++++++++++++++++++++++++++------------------ src/platform_spec.rs | 16 +++++++++++++ 2 files changed, 48 insertions(+), 23 deletions(-) diff --git a/src/isp_device.rs b/src/isp_device.rs index a4e6689..afa1188 100644 --- a/src/isp_device.rs +++ b/src/isp_device.rs @@ -6,7 +6,7 @@ use hidra::{HidDevice, HidError}; use hidra::{NativeDevice, NusbDevice}; use thiserror::Error; -use crate::{device_spec::*, VerificationError}; +use crate::{device_spec::*, platform_spec::InitOperand, VerificationError}; const COMMAND_LENGTH: usize = 6; @@ -187,16 +187,31 @@ impl ISPDevice { Ok(()) } - /// Initializes the read operation / sets the initial read address - pub async fn init_read(&self, start_addr: usize) -> Result<(), ISPError> { - let cmd: [u8; COMMAND_LENGTH] = [ - REPORT_ID_CMD, - CMD_INIT_READ, - (start_addr & 0xff) as u8, - (start_addr >> 8) as u8, - 0, - 0, - ]; + fn init_command(&self, command: u8, start_addr: usize, length: usize) -> [u8; COMMAND_LENGTH] { + match self.device_spec.platform.init_operand { + InitOperand::Address => [ + REPORT_ID_CMD, + command, + (start_addr & 0xff) as u8, + (start_addr >> 8) as u8, + 0, + 0, + ], + InitOperand::Length => [ + REPORT_ID_CMD, + command, + 0, + 0, + (length & 0xff) as u8, + (length >> 8) as u8, + ], + } + } + + /// Initializes the read operation / sets the initial read address or the + /// total read length, depending on the platform's [`InitOperand`]. + pub async fn init_read(&self, start_addr: usize, length: usize) -> Result<(), ISPError> { + let cmd = self.init_command(CMD_INIT_READ, start_addr, length); self.cmd_device .send_feature_report(&cmd) .await @@ -204,16 +219,10 @@ impl ISPDevice { Ok(()) } - /// Initializes the write operation / sets the initial write address - pub async fn init_write(&self, start_addr: usize) -> Result<(), ISPError> { - let cmd: [u8; COMMAND_LENGTH] = [ - REPORT_ID_CMD, - CMD_INIT_WRITE, - (start_addr & 0xff) as u8, - (start_addr >> 8) as u8, - 0, - 0, - ]; + /// Initializes the write operation / sets the initial write address or the + /// total write length, depending on the platform's [`InitOperand`]. + pub async fn init_write(&self, start_addr: usize, length: usize) -> Result<(), ISPError> { + let cmd = self.init_command(CMD_INIT_WRITE, start_addr, length); self.cmd_device .send_feature_report(&cmd) .await @@ -289,7 +298,7 @@ impl ISPDevice { let page_size = self.device_spec.platform.page_size; let num_page = length / page_size; - self.init_read(start_addr).await?; + self.init_read(start_addr, length).await?; let mut result: Vec = vec![]; for i in 0..num_page { @@ -312,7 +321,7 @@ impl ISPDevice { let page_size = self.device_spec.platform.page_size; let num_page = self.device_spec.num_pages(); - self.init_write(start_addr).await?; + self.init_write(start_addr, num_page * page_size).await?; for i in 0..num_page { self.write_page(&buffer[(i * page_size)..((i + 1) * page_size)]) diff --git a/src/platform_spec.rs b/src/platform_spec.rs index a5cdbef..aa332b2 100644 --- a/src/platform_spec.rs +++ b/src/platform_spec.rs @@ -3,17 +3,25 @@ use phf::{phf_map, Map}; const DEFAULT_BOOTLOADER_SIZE: usize = 4096; const DEFAULT_PAGE_SIZE: usize = 2048; +#[derive(Clone, Copy, PartialEq)] +pub enum InitOperand { + Address, + Length, +} + #[derive(Clone, Copy, PartialEq)] pub struct PlatformSpec { pub firmware_size: usize, pub bootloader_size: usize, pub page_size: usize, + pub init_operand: InitOperand, } const PLATFORM_DEFAULT: PlatformSpec = PlatformSpec { firmware_size: 0, bootloader_size: DEFAULT_BOOTLOADER_SIZE, page_size: DEFAULT_PAGE_SIZE, + init_operand: InitOperand::Address, }; pub const PLATFORM_SH68F90: PlatformSpec = PlatformSpec { @@ -38,7 +46,15 @@ pub const PLATFORM_SH68F902: PlatformSpec = PlatformSpec { ..PLATFORM_DEFAULT }; +pub const PLATFORM_SH68F83: PlatformSpec = PlatformSpec { + firmware_size: 16384 - 2048, + bootloader_size: 2048, + init_operand: InitOperand::Length, + ..PLATFORM_DEFAULT +}; + pub static PLATFORMS: Map<&'static str, PlatformSpec> = phf_map! { + "sh68f83" => PLATFORM_SH68F83, "sh68f89" => PLATFORM_SH68F89, "sh68f881" => PLATFORM_SH68F881, "sh68f90" => PLATFORM_SH68F90, From 7f9f0941dd69cbe94b91e07d3e953a54150f68d4 Mon Sep 17 00:00:00 2001 From: Karolis Stasaitis Date: Sat, 5 Sep 2026 10:05:29 +0200 Subject: [PATCH 2/2] device: crowview-note --- src/device_spec.rs | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/src/device_spec.rs b/src/device_spec.rs index 768fad8..9575a31 100644 --- a/src/device_spec.rs +++ b/src/device_spec.rs @@ -1,7 +1,8 @@ use phf::{phf_map, Map}; use crate::platform_spec::{ - PlatformSpec, PLATFORM_SH68F881, PLATFORM_SH68F89, PLATFORM_SH68F90, PLATFORM_SH68F902, + PlatformSpec, PLATFORM_SH68F83, PLATFORM_SH68F881, PLATFORM_SH68F89, PLATFORM_SH68F90, + PLATFORM_SH68F902, }; const DEFAULT_ISP_IFACE_NUM: i32 = 1; @@ -85,6 +86,16 @@ pub const DEVICE_BASE_SH68F902: DeviceSpec = DeviceSpec { isp_transform: None, }; +pub const DEVICE_BASE_SH68F83: DeviceSpec = DeviceSpec { + vendor_id: 0x0000, + product_id: 0x0000, + platform: PLATFORM_SH68F83, + isp_iface_num: DEFAULT_ISP_IFACE_NUM, + isp_report_id: DEFAULT_ISP_REPORT_ID, + reboot: DEFAULT_REBOOT, + isp_transform: None, +}; + pub const DEVICE_AOKO_K101: DeviceSpec = DeviceSpec { vendor_id: 0x258a, product_id: 0x0155, @@ -115,6 +126,12 @@ pub const DEVICE_CIY_X77: DeviceSpec = DeviceSpec { ..DEVICE_BASE_SH68F89 }; +pub const DEVICE_CROWVIEW_NOTE: DeviceSpec = DeviceSpec { + vendor_id: 0x6080, + product_id: 0x8060, + ..DEVICE_BASE_SH68F83 +}; + pub const DEVICE_DELTACO_WK95R: DeviceSpec = DeviceSpec { vendor_id: 0x258a, product_id: 0x0049, @@ -382,6 +399,7 @@ pub static DEVICES: Map<&'static str, DeviceSpec> = phf_map! { "aula-f75" => DEVICE_AULA_F75, "aula-f87" => DEVICE_AULA_F87, "ciy-x77" => DEVICE_CIY_X77, + "crowview-note" => DEVICE_CROWVIEW_NOTE, "deltaco-wk95r" => DEVICE_DELTACO_WK95R, "dierya-dk68se" => DEVICE_DIERYA_DK68SE, "digitalalliance-meca-warrior-x" => DEVICE_DIGITALALLIANCE_MECA_WARRIOR_X,