Skip to content

Commit 70e2962

Browse files
committed
fix(vdo): Address all PR #223 review feedback
Address all review comments. Fix GObject leak in Stream::drop. - Consume-by-value ownership: start(self), stop(self), unref(self) - Replace Iterator with next_buffer() -> Result - Merge Frame into StreamBuffer (VdoBuffer = VdoFrame) - Extract Map to separate module, keys as &CStr - Add Resolution enum, remove buffer_strategy, rename to custom_timestamp_us - Replace as_mut_slice with data_copy(), file_descriptor() returns Result Tested: cargo clippy clean, 33/33 tests pass on Artpec-9 device.
1 parent 7a382bb commit 70e2962

File tree

5 files changed

+701
-610
lines changed

5 files changed

+701
-610
lines changed

Cargo.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,8 +67,8 @@ licensekey = { path = "crates/licensekey" }
6767
licensekey-sys = { path = "crates/licensekey-sys" }
6868
mdb = { path = "crates/mdb" }
6969
mdb-sys = { path = "crates/mdb-sys" }
70-
vdo-sys = { path = "crates/vdo-sys" }
7170
vdo = { path = "crates/vdo" }
71+
vdo-sys = { path = "crates/vdo-sys" }
7272

7373
[workspace.package]
7474
edition = "2021"

apps/vdo_encode_client/src/main.rs

Lines changed: 21 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -8,16 +8,22 @@
88
//! - Frame capture and metadata access
99
//! - Proper resource cleanup
1010
11+
// These format tests run on the device as an ACAP application rather than as
12+
// unit tests because they require access to actual camera hardware via the VDO API.
13+
1114
use log::{error, info};
12-
use vdo::{Error, Stream, VdoFormat};
15+
use vdo::{Error, Resolution, Stream, VdoFormat};
1316

14-
fn test_format(name: &str, format: VdoFormat, num_frames: usize) -> Result<(), Error> {
17+
fn capture_format(name: &str, format: VdoFormat, num_frames: usize) -> Result<(), Error> {
1518
info!("=== Testing {} format ===", name);
1619

17-
let mut stream = Stream::builder()
20+
let stream = Stream::builder()
1821
.channel(0)
1922
.format(format)
20-
.resolution(640, 480)
23+
.resolution(Resolution::Exact {
24+
width: 640,
25+
height: 480,
26+
})
2127
.framerate(15)
2228
.build()?;
2329

@@ -29,14 +35,14 @@ fn test_format(name: &str, format: VdoFormat, num_frames: usize) -> Result<(), E
2935
stream_info.dump();
3036
}
3137

32-
let mut running = stream.start()?;
38+
let running = stream.start()?;
3339
info!("{}: Stream started", name);
3440

35-
for (i, buffer) in running.iter().take(num_frames).enumerate() {
36-
let frame = buffer.frame()?;
37-
let size = frame.size();
38-
let seq = frame.sequence_number();
39-
let ts = frame.timestamp();
41+
for i in 0..num_frames {
42+
let buffer = running.next_buffer()?;
43+
let size = buffer.size();
44+
let seq = buffer.sequence_number();
45+
let ts = buffer.timestamp();
4046

4147
info!(
4248
"{}: Frame {}: {} bytes, seq={}, timestamp={}us",
@@ -54,7 +60,7 @@ fn test_format(name: &str, format: VdoFormat, num_frames: usize) -> Result<(), E
5460
}
5561
}
5662

57-
running.stop()?;
63+
running.stop();
5864
info!("{}: Stream stopped successfully", name);
5965
info!("");
6066

@@ -69,25 +75,25 @@ fn main() {
6975
info!("");
7076

7177
// Test YUV (most portable format)
72-
match test_format("YUV", VdoFormat::VDO_FORMAT_YUV, 5) {
78+
match capture_format("YUV", VdoFormat::VDO_FORMAT_YUV, 5) {
7379
Ok(()) => info!("YUV test: PASSED"),
7480
Err(e) => error!("YUV test: FAILED - {}", e),
7581
}
7682

7783
// Test JPEG
78-
match test_format("JPEG", VdoFormat::VDO_FORMAT_JPEG, 5) {
84+
match capture_format("JPEG", VdoFormat::VDO_FORMAT_JPEG, 5) {
7985
Ok(()) => info!("JPEG test: PASSED"),
8086
Err(e) => error!("JPEG test: FAILED - {}", e),
8187
}
8288

8389
// Test H.264
84-
match test_format("H.264", VdoFormat::VDO_FORMAT_H264, 10) {
90+
match capture_format("H.264", VdoFormat::VDO_FORMAT_H264, 10) {
8591
Ok(()) => info!("H.264 test: PASSED"),
8692
Err(e) => error!("H.264 test: FAILED - {}", e),
8793
}
8894

8995
// Test H.265 (might not be supported on all platforms)
90-
match test_format("H.265", VdoFormat::VDO_FORMAT_H265, 5) {
96+
match capture_format("H.265", VdoFormat::VDO_FORMAT_H265, 5) {
9197
Ok(()) => info!("H.265 test: PASSED"),
9298
Err(e) => {
9399
if let Error::Vdo(ref vdo_err) = e {

crates/vdo/examples/basic.rs

Lines changed: 13 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
//! This example creates a video stream, captures a few frames, and prints
44
//! information about each frame.
55
6-
use vdo::{Stream, VdoFormat};
6+
use vdo::{Resolution, Stream, VdoFormat};
77

88
fn main() -> Result<(), Box<dyn std::error::Error>> {
99
// Initialize logging (optional)
@@ -12,30 +12,33 @@ fn main() -> Result<(), Box<dyn std::error::Error>> {
1212
println!("Creating video stream...");
1313

1414
// Create a stream with YUV format (most portable across platforms)
15-
let mut stream = Stream::builder()
15+
let stream = Stream::builder()
1616
.channel(0)
1717
.format(VdoFormat::VDO_FORMAT_YUV)
18-
.resolution(640, 480)
18+
.resolution(Resolution::Exact {
19+
width: 640,
20+
height: 480,
21+
})
1922
.framerate(15)
2023
.build()?;
2124

2225
println!("Starting stream...");
23-
let mut running = stream.start()?;
26+
let running = stream.start()?;
2427

2528
println!("Capturing frames...");
26-
for (i, buffer) in running.iter().take(10).enumerate() {
27-
let frame = buffer.frame()?;
29+
for i in 0..10 {
30+
let buffer = running.next_buffer()?;
2831
println!(
2932
"Frame {}: {} bytes, seq={}, timestamp={}us",
3033
i,
31-
frame.size(),
32-
frame.sequence_number(),
33-
frame.timestamp()
34+
buffer.size(),
35+
buffer.sequence_number(),
36+
buffer.timestamp()
3437
);
3538
}
3639

3740
println!("Stopping stream...");
38-
running.stop()?;
41+
running.stop();
3942

4043
println!("Done!");
4144
Ok(())

0 commit comments

Comments
 (0)