Skip to content

Commit d8f59d0

Browse files
committed
Fixing warnings, improving code quality
1 parent 1aa0bf4 commit d8f59d0

7 files changed

Lines changed: 44 additions & 75 deletions

File tree

canopen-common/src/sdo.rs

Lines changed: 2 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
// sdo.rs - Updated for the new connection architecture
2-
use socketcan::{CanSocket, Socket, CanFrame, StandardId};
2+
use socketcan::{CanFrame, StandardId};
33
use socketcan::EmbeddedFrame as Frame;
4-
use std::time::{Duration, Instant};
54
use std::error::Error;
65
use std::fmt;
76

@@ -24,17 +23,7 @@ pub enum SdoCommand {
2423
}
2524

2625
impl SdoCommand {
27-
fn from_u8(value: u8) -> Option<Self> {
28-
match value & 0xE0 { // Mask the command specifier bits
29-
0x40 => Some(Self::InitiateUploadRequest),
30-
0x60 => Some(Self::UploadSegmentRequest),
31-
0x00 => Some(Self::UploadSegmentResponse),
32-
0x80 => Some(Self::AbortTransfer),
33-
_ => None,
34-
}
35-
}
36-
37-
fn is_expedited_response(value: u8) -> bool {
26+
pub(crate) fn is_expedited_response(value: u8) -> bool {
3827
(value & 0xE0) == 0x40 && (value & 0x02) != 0
3928
}
4029
}
@@ -68,15 +57,6 @@ impl SdoDataType {
6857
_ => None,
6958
}
7059
}
71-
72-
fn size_bytes(&self) -> Option<usize> {
73-
match self {
74-
Self::UInt8 | Self::Int8 => Some(1),
75-
Self::UInt16 | Self::Int16 => Some(2),
76-
Self::UInt32 | Self::Int32 | Self::Real32 => Some(4),
77-
Self::VisibleString | Self::OctetString => None, // Variable length
78-
}
79-
}
8060
}
8161

8262
/// SDO Request structure

canopen-viewer/src/canopen/connect.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3,16 +3,17 @@ use socketcan::{CanSocket, Socket, CanFrame, StandardId, EmbeddedFrame};
33
use std::collections::HashMap;
44
use std::sync::{Arc, Mutex};
55
use std::time::Duration;
6-
use tokio::sync::{mpsc, oneshot, RwLock};
6+
use tokio::sync::{mpsc, oneshot};
77
use tokio::task::JoinHandle;
88
use std::error::Error;
99
use std::fmt;
1010

11-
use canopen_common::{SdoRequest, SdoResponse, SdoError, create_sdo_request_frame, parse_sdo_response};
11+
use canopen_common::{SdoRequest, SdoResponse, SdoError, parse_sdo_response};
1212

1313
#[derive(Debug)]
1414
pub enum CANopenError {
1515
SocketError(String),
16+
#[allow(dead_code)] // Reserved for future use
1617
NodeNotConnected(u8),
1718
RequestFailed(String),
1819
}
@@ -47,6 +48,7 @@ enum ConnectionMessage {
4748
node_id: u8,
4849
response_tx: oneshot::Sender<Result<(), CANopenError>>,
4950
},
51+
#[allow(dead_code)] // Reserved for future cleanup functionality
5052
RemoveNode {
5153
node_id: u8,
5254
response_tx: oneshot::Sender<Result<(), CANopenError>>,
@@ -63,7 +65,6 @@ struct PendingSdoRequest {
6365

6466
/// Per-node state management
6567
struct NodeState {
66-
node_id: u8,
6768
// Queue of pending SDO requests (FIFO)
6869
pending_requests: std::collections::VecDeque<PendingSdoRequest>,
6970
// Currently active request (if any)
@@ -73,9 +74,8 @@ struct NodeState {
7374
}
7475

7576
impl NodeState {
76-
fn new(node_id: u8, timeout: Duration) -> Self {
77+
fn new(_node_id: u8, timeout: Duration) -> Self {
7778
Self {
78-
node_id,
7979
pending_requests: std::collections::VecDeque::new(),
8080
active_request: None,
8181
timeout,

canopen-viewer/src/canopen/mod.rs

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,8 @@ pub mod connect;
44
// SDO protocol is now in the common library
55
// Re-export from canopen-common for backwards compatibility
66
pub use canopen_common::{
7-
SdoRequest, SdoResponse, SdoResponseData, SdoDataType, SdoError,
8-
create_sdo_request_frame, parse_sdo_response, parse_payload,
9-
get_abort_code_description, SdoCommand
7+
SdoRequest, SdoDataType
108
};
119

12-
pub use connect::{CANopenConnection, CANopenNodeHandle, CANopenError};
10+
pub use connect::{CANopenConnection, CANopenNodeHandle};
1311

canopen-viewer/src/communication.rs

Lines changed: 13 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -2,24 +2,25 @@ use std::sync::mpsc::{Receiver, Sender};
22
use std::path::PathBuf;
33
use configparser::ini::Ini;
44
use std::collections::{BTreeMap, HashMap};
5-
use rand::Rng;
6-
use tokio::{sync::{mpsc as tokio_mpsc, oneshot}, task::JoinHandle};
5+
use tokio::task::JoinHandle;
76
use std::time::Duration;
87
use crate::canopen::{
98
CANopenConnection, CANopenNodeHandle,
10-
SdoRequest, SdoDataType, SdoError
9+
SdoRequest, SdoDataType
1110
};
1211

1312

1413
#[derive(Debug, Clone)]
1514
pub struct SdoSubObject {
15+
#[allow(dead_code)] // Stored from EDS for reference
1616
pub sub_index: u8,
1717
pub name: String,
1818
pub data_type: String,
1919
}
2020

2121
#[derive(Debug, Clone)]
2222
pub struct SdoObject {
23+
#[allow(dead_code)] // Used internally by BTreeMap, needed for EDS parsing
2324
pub index: u16,
2425
pub name: String,
2526
/// We use a BTreeMap to keep sub-objects automatically sorted by their sub_index (the u8 key).
@@ -29,6 +30,7 @@ pub struct SdoObject {
2930
#[derive(Debug, Clone, Eq, Hash, PartialEq)]
3031
pub struct SdoAddress {
3132
pub index: u16,
33+
#[allow(dead_code)] // Used in HashMap key, accessed via pattern matching
3234
pub sub_index: u8,
3335
}
3436

@@ -39,37 +41,24 @@ pub enum Command {
3941
Subscribe {
4042
address: SdoAddress,
4143
interval_ms: u64,
44+
data_type: SdoDataType,
4245
},
4346
Unsubscribe(SdoAddress),
4447
}
4548

4649
#[derive(Debug)]
4750
pub enum Update {
4851
SdoList(BTreeMap<u16, SdoObject>),
52+
#[allow(dead_code)] // TODO: Will be used in Priority 1 fixes for connection status
4953
ConnectionSuccess(BTreeMap<u16, SdoObject>),
54+
#[allow(dead_code)] // TODO: Will be used in Priority 1 fixes for error reporting
5055
ConnectionFailed(String),
5156
SdoData {
5257
address: SdoAddress,
5358
value: String,
5459
},
5560
}
5661

57-
async fn simulation_task(address: SdoAddress, interval_ms: u64, update_tx: Sender<Update>) {
58-
println!("Starting simulation task for address {:?} with interval {} ms", &address, interval_ms);
59-
let mut interval = tokio::time::interval(std::time::Duration::from_millis(interval_ms));
60-
61-
62-
loop {
63-
interval.tick().await;
64-
let mut rng = rand::thread_rng();
65-
let random_value = rng.gen_range(0..100);
66-
let _ = update_tx.send(Update::SdoData {
67-
address: address.clone(),
68-
value: format!("{}", random_value),
69-
});
70-
}
71-
}
72-
7362
async fn sdo_polling_task(
7463
address: SdoAddress,
7564
interval_ms: u64,
@@ -113,7 +102,8 @@ pub fn communication_thread_main(
113102

114103
let rt = tokio::runtime::Runtime::new().unwrap();
115104
let mut subscription_handles: HashMap<SdoAddress, JoinHandle<()>> = HashMap::new();
116-
let mut connection: Option<CANopenConnection> = None;
105+
// Keep connection alive - it owns the background CAN reader task
106+
let mut _connection_handle: Option<CANopenConnection> = None;
117107
let mut node_handle: Option<CANopenNodeHandle> = None;
118108

119109

@@ -126,7 +116,7 @@ pub fn communication_thread_main(
126116
Ok::<(CANopenConnection, CANopenNodeHandle), Box<dyn std::error::Error>>((conn, handle))
127117
}){
128118
Ok((conn, handle)) => {
129-
connection = Some(conn);
119+
_connection_handle = Some(conn);
130120
node_handle = Some(handle);
131121
},
132122
Err(err) => {
@@ -149,7 +139,7 @@ pub fn communication_thread_main(
149139
let _ = update_tx.send(Update::SdoList(BTreeMap::new()));
150140
}
151141
},
152-
Command::Subscribe { address, interval_ms } => {
142+
Command::Subscribe { address, interval_ms, data_type } => {
153143
if let Some(ref handle) = node_handle {
154144
println!("Subscribing to address {:?} with interval {} ms", &address, interval_ms);
155145

@@ -161,7 +151,7 @@ pub fn communication_thread_main(
161151
interval_ms,
162152
update_tx_clone,
163153
handle_clone,
164-
SdoDataType::Real32,
154+
data_type,
165155
));
166156

167157
subscription_handles.insert(address, subscription_handle);
@@ -177,7 +167,6 @@ pub fn communication_thread_main(
177167
subscription_handle.abort();
178168
}
179169
}
180-
_ => {}
181170
}
182171
}
183172
}

canopen-viewer/src/main.rs

Lines changed: 14 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,8 @@ mod communication;
44
mod canopen;
55

66
use std::collections::{BTreeMap, HashMap, VecDeque};
7-
use std::ops::Deref;
87
use communication::{Command, Update, SdoAddress, SdoObject};
8+
use canopen_common::SdoDataType;
99

1010
use eframe::{egui, NativeOptions, egui::Color32, egui::ColorImage};
1111
use std::process::Command as process_command;
@@ -34,15 +34,6 @@ struct ScreenshotInfo {
3434
rect: egui::Rect,
3535
}
3636

37-
impl ScreenshotInfo {
38-
fn new(file_name: String, rect: egui::Rect) -> Self {
39-
Self {
40-
filename: file_name,
41-
rect,
42-
}
43-
}
44-
}
45-
4637
struct MyApp {
4738
current_view: AppView,
4839
available_can_interfaces: Vec<String>,
@@ -402,7 +393,7 @@ impl MyApp {
402393
ui.label(&plot_title);
403394
ui.separator();
404395

405-
let plot_response = Plot::new(plot_id)
396+
Plot::new(plot_id)
406397
.legend(egui_plot::Legend::default())
407398
.view_aspect(2.0)
408399
.allow_scroll(false)
@@ -472,8 +463,19 @@ impl MyApp {
472463
});
473464
if ui.button("Start Reading").clicked() {
474465
if let Ok(interval_ms) = self.modal_interval_str.parse::<u64>() {
466+
// Look up the data type from the EDS
467+
let data_type = self.sdo_data.as_ref()
468+
.and_then(|sdo_map| sdo_map.get(&address.index))
469+
.and_then(|sdo_object| sdo_object.sub_objects.get(&address.sub_index))
470+
.and_then(|sub_object| SdoDataType::from_eds_type(&sub_object.data_type))
471+
.unwrap_or(SdoDataType::Real32); // Fallback to Real32 if type unknown
472+
475473
if let Some(tx) = &self.command_tx {
476-
tx.send(Command::Subscribe { address: address.clone(), interval_ms }).unwrap();
474+
tx.send(Command::Subscribe {
475+
address: address.clone(),
476+
interval_ms,
477+
data_type,
478+
}).unwrap();
477479
}
478480
self.subscriptions.insert(address.clone(), SdoSubscription {
479481
interval_ms,

mock-canopen-node/src/object_dictionary.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -92,7 +92,7 @@ impl ObjectDictionary {
9292
0x01,
9393
|| {
9494
let mut rng = rand::rng();
95-
let temp: f32 = rng.gen_range(20.0..30.0); // Random temperature between 20-30°C
95+
let temp: f32 = rng.random_range(20.0..30.0); // Random temperature between 20-30°C
9696
temp.to_le_bytes().to_vec()
9797
},
9898
SdoDataType::Real32,
@@ -104,7 +104,7 @@ impl ObjectDictionary {
104104
0x02,
105105
|| {
106106
let mut rng = rand::rng();
107-
let pressure: f32 = rng.gen_range(95.0..105.0); // Random pressure 95-105 kPa
107+
let pressure: f32 = rng.random_range(95.0..105.0); // Random pressure 95-105 kPa
108108
pressure.to_le_bytes().to_vec()
109109
},
110110
SdoDataType::Real32,
@@ -132,7 +132,7 @@ impl ObjectDictionary {
132132
0x01,
133133
|| {
134134
let mut rng = rand::rng();
135-
let voltage: f32 = rng.gen_range(11.5..12.5); // Random voltage 11.5-12.5V
135+
let voltage: f32 = rng.random_range(11.5..12.5); // Random voltage 11.5-12.5V
136136
voltage.to_le_bytes().to_vec()
137137
},
138138
SdoDataType::Real32,
@@ -144,7 +144,7 @@ impl ObjectDictionary {
144144
0x02,
145145
|| {
146146
let mut rng = rand::rng();
147-
let current: f32 = rng.gen_range(0.5..5.0); // Random current 0.5-5.0A
147+
let current: f32 = rng.random_range(0.5..5.0); // Random current 0.5-5.0A
148148
current.to_le_bytes().to_vec()
149149
},
150150
SdoDataType::Real32,
@@ -162,7 +162,7 @@ impl ObjectDictionary {
162162
0x01,
163163
|| {
164164
let mut rng = rand::rng();
165-
let rpm: i32 = rng.gen_range(1000..3000); // Random RPM 1000-3000
165+
let rpm: i32 = rng.random_range(1000..3000); // Random RPM 1000-3000
166166
rpm.to_le_bytes().to_vec()
167167
},
168168
SdoDataType::Int32,

mock-canopen-node/src/sdo_server.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
11
//! SDO Server implementation for responding to SDO upload requests
22
33
use socketcan::{CanFrame, StandardId, EmbeddedFrame};
4-
use canopen_common::{SdoDataType, SdoCommand};
4+
use canopen_common::SdoDataType;
55
use crate::object_dictionary::ObjectDictionary;
66

77
pub struct SdoServer {
8-
node_id: u8,
8+
_node_id: u8, // Stored for potential future use (logging, multi-node support)
99
object_dict: ObjectDictionary,
1010
request_cob_id: u16, // 0x600 + node_id
1111
response_cob_id: u16, // 0x580 + node_id
@@ -14,7 +14,7 @@ pub struct SdoServer {
1414
impl SdoServer {
1515
pub fn new(node_id: u8, object_dict: ObjectDictionary) -> Self {
1616
Self {
17-
node_id,
17+
_node_id: node_id,
1818
object_dict,
1919
request_cob_id: 0x600 + node_id as u16,
2020
response_cob_id: 0x580 + node_id as u16,

0 commit comments

Comments
 (0)