ra8-firmware 0.1.0
Bare-metal firmware for the Renesas RA8 family (RA8D2 / RA8P1)
Loading...
Searching...
No Matches
c6_cam_camera.c
Go to the documentation of this file.
1
18
19#include <stdint.h>
20
21#include "c6_camera_server.h"
22#include "ra8_attributes.h"
23#include "ra8_board_ek_ra8d2.h"
24#include "ra8_camera.h"
27#include "ra8_ceu.h"
28#include "ra8_ov5640.h"
29#include "ra8_time.h"
30
60
62[[gnu::section(".sdram_data"), gnu::aligned(32)]] static uint8_t s_capture[k_sw_cam_source_bytes];
63[[gnu::section(".sdram_data"), gnu::aligned(8)]] static uint8_t s_rgb[k_sw_cam_rgb_bytes];
64[[gnu::section(".sdram_data"), gnu::aligned(8)]] static uint8_t s_jpeg[k_sw_cam_jpeg_bytes];
71
86{
87 const ra8_ov5640_bus_t bus = {
90 .delay_ms = ra8_board_camera_delay_ms,
91 .ctx = nullptr,
92 };
93 return ra8_ov5640_init(&s_camera_sensor, &bus);
94}
95
109{
110 const ra8_ceu_config_t ceu = {
111 .width_px = (uint16_t)k_sw_cam_source_width,
112 .height_px = (uint16_t)k_sw_cam_source_height,
113 .x_capture_px = (uint16_t)k_sw_cam_source_stride,
114 .y_capture_lines = (uint16_t)k_sw_cam_source_height,
115 .dst_stride = (uint16_t)k_sw_cam_source_stride,
116 .bytes_per_pixel = 2U,
117 .capture_format = k_ra8_ceu_fmt_data_synchronous,
118 .capture_mode = k_ra8_ceu_capture_single,
119 .data_bus = k_ra8_ceu_bus_8_bit,
120 .hsync_polarity = k_ra8_ceu_pol_high_active,
121 .vsync_polarity = k_ra8_ceu_pol_high_active,
122 .field_polarity = k_ra8_ceu_pol_high_active,
123 .input_order = k_ra8_ceu_input_cb0_y0_cr0_y1,
124 .output_format = k_ra8_ceu_output_ycbcr_422,
125 .burst_mode = k_ra8_ceu_burst_32,
126 .first_field = k_ra8_ceu_field_immediate,
127 .edge = {k_ra8_ceu_edge_rising,
131 .byte_swap = {false, true, true},
132 .scale = {0U, 0U, 0U, 0U, (uint16_t)k_sw_cam_source_width, (uint16_t)k_sw_cam_source_height},
133 };
135 .ceu = ceu,
136 .output =
137 {
138 .frame_bytes_max = (uint32_t)k_sw_cam_source_bytes,
139 .stride_bytes = (uint32_t)k_sw_cam_source_stride,
140 .width = (uint16_t)k_sw_cam_source_width,
141 .height = (uint16_t)k_sw_cam_source_height,
143 },
144 .poll_interval_ms = (uint32_t)k_sw_cam_poll_ms,
145 .poll_attempts = (uint32_t)k_sw_cam_poll_attempts,
146 };
147}
148
150{
152 if (err != k_ra8_ok) {
153 return err;
154 }
156 if (err != k_ra8_ok) {
157 return err;
158 }
161 if (err != k_ra8_ok) {
162 return err;
163 }
165 if (err != k_ra8_ok) {
166 return err;
167 }
168 uint16_t chip_id = 0U;
169 if ((ra8_ov5640_probe(&s_camera_sensor, &chip_id) != k_ra8_ok) ||
170 (chip_id != (uint16_t)k_ra8_ov5640_chip_id)) {
172 }
174 if (err != k_ra8_ok) {
175 return err;
176 }
178 if (err != k_ra8_ok) {
179 return err;
180 }
183 if (err != k_ra8_ok) {
184 return err;
185 }
186 const ra8_camera_codec_jpeg_sw_cfg_t codec_cfg = {
187 .rgb_workspace = s_rgb,
188 .rgb_workspace_capacity = (uint32_t)sizeof(s_rgb),
189 .output_width = (uint16_t)k_sw_cam_stream_width,
190 .output_height = (uint16_t)k_sw_cam_stream_height,
191 .quality = (uint8_t)k_sw_cam_jpeg_quality,
192 };
194}
195
196ra8_err_t c6_cam_camera_capture_jpeg(const uint8_t** out_jpeg,
197 uint32_t* out_bytes,
198 c6_cam_frame_timing_t* out_timing)
199{
200 if ((out_jpeg == nullptr) || (out_bytes == nullptr) || (out_timing == nullptr)) {
201 return k_ra8_err_null_ptr;
202 }
203 *out_jpeg = nullptr;
204 *out_bytes = 0U;
205 *out_timing = (c6_cam_frame_timing_t){};
206 const uint32_t capture_start = ra8_time_ms();
207 out_timing->timestamp_ms = capture_start;
208 const ra8_camera_buffer_t capture_buffer = {
209 .data = s_capture,
210 .capacity = (uint32_t)sizeof(s_capture),
211 };
212 ra8_camera_frame_t captured = {};
213 ra8_err_t err = ra8_camera_source_capture(&s_source, &capture_buffer, &captured);
214 const uint32_t capture_end = ra8_time_ms();
215 out_timing->capture_ms = capture_end - capture_start;
216 if (err != k_ra8_ok) {
217 return err;
218 }
219 const ra8_camera_buffer_t encoded_buffer = {
220 .data = s_jpeg,
221 .capacity = (uint32_t)sizeof(s_jpeg),
222 };
223 ra8_camera_frame_t encoded = {};
224 err = ra8_camera_codec_encode(&s_codec, &captured, &encoded_buffer, &encoded);
225 out_timing->encode_ms = ra8_time_ms() - capture_end;
226 if (err != k_ra8_ok) {
227 return err;
228 }
229 *out_jpeg = encoded.data;
230 *out_bytes = encoded.bytes;
231 return k_ra8_ok;
232}
233
235{
236 return "frame=640x480 UYVY software-codec=320x240 JPEG";
237}
238
240{
241 uint32_t events = 0U;
243 c6_cam_puts(" ceu_events=");
244 c6_cam_put_u32(events);
245 }
246}
static ra8_camera_codec_t s_codec
static uint8_t s_rgb[k_sw_cam_rgb_bytes]
static ra8_ov5640_t s_camera_sensor
Transport-independent OV5640 instance bound to the EK-RA8D2 SCCB bus.
ra8_err_t c6_cam_camera_init(void)
Camera image and board-switch initialization, then one CEU capture.
static ra8_camera_codec_jpeg_sw_state_t s_codec_state
static uint8_t s_jpeg[k_sw_cam_jpeg_bytes]
static ra8_err_t internal_c6_cam_sensor_bind(void)
Bind the software-JPEG sensor instance to board SCCB callbacks.
ra8_err_t c6_cam_camera_capture_jpeg(const uint8_t **out_jpeg, uint32_t *out_bytes, c6_cam_frame_timing_t *out_timing)
sw_cam_cfg_t
Software-camera backend geometry, buffers, and sensor timing.
@ k_sw_cam_rgb_bytes
RGB conversion workspace bytes.
@ k_sw_cam_source_height
OV5640 capture height.
@ k_sw_cam_jpeg_quality
Software JPEG quality.
@ k_sw_cam_jpeg_bytes
Worst-case JPEG buffer bytes.
@ k_sw_cam_source_width
OV5640 capture width.
@ k_sw_cam_source_stride
Packed UYVY row bytes.
@ k_sw_cam_xclk_hz
OV5640 input clock.
@ k_sw_cam_source_bytes
Packed UYVY frame bytes.
@ k_sw_cam_poll_ms
CEU completion poll period.
@ k_sw_cam_stream_height
Encoded JPEG height.
@ k_sw_cam_poll_attempts
CEU completion poll limit.
@ k_sw_cam_mode_settle_ms
Sensor routing settle delay.
@ k_sw_cam_stream_width
Encoded JPEG width.
static ra8_camera_source_ceu_state_t s_source_state
void c6_cam_camera_report_last_error(void)
Emit backend-specific diagnostics for the last capture failure.
const char * c6_cam_camera_description(void)
Human-readable description of the selected camera backend.
static ra8_camera_source_ceu_cfg_t internal_c6_cam_source_config(void)
Build the CEU configuration for packed VGA capture.
Shared contracts for ESP32-C6 browser camera servers.
void c6_cam_put_u32(uint32_t value)
Write one unsigned decimal value to SCI8.
void c6_cam_puts(const char *text)
Write a bounded NUL-terminated string to SCI8.
static tc_capture_t s_capture
The single calibration capture the shims fill.
Definition main.c:160
static uint8_t s_source[k_image_source_bytes]
Complete fetched encoded image.
Annotation-attribute framework macros for ra8-firmware.
#define RA8_INTERNAL
Marker that a function is intended to be static (file-local).
Board-support layer for the Renesas EK-RA8D2 v1 evaluation kit.
ra8_err_t ra8_board_camera_reset(void)
Pulse the J35 camera reset input and leave the sensor released.
ra8_err_t ra8_board_camera_sccb_write_reg(void *ctx, uint8_t address, uint16_t reg, uint8_t value)
Write one 16-bit-addressed SCCB register on the J35 camera bus.
ra8_err_t ra8_board_camera_sccb_read_reg(void *ctx, uint8_t address, uint16_t reg, uint8_t *out_value)
Read one 16-bit-addressed SCCB register on the J35 camera bus.
ra8_err_t ra8_board_camera_xclk_start(uint32_t frequency_hz)
Start the J35 camera sensor input clock (XCLK) on P501/GTIOC12A.
ra8_err_t ra8_board_camera_route_parallel_pins(void)
Route J35 D[7:0], VSYNC, HSYNC and PCLK to the CEU peripheral.
ra8_err_t ra8_board_camera_select_parallel(void)
Drive only SW4-6 ON through U15, selecting J35 parallel DVP.
void ra8_board_camera_delay_ms(void *ctx, uint32_t milliseconds)
Millisecond delay adapter for transport-independent camera drivers.
Transport-neutral camera source and image-codec facade.
@ k_ra8_camera_format_uyvy422
Packed Cb, Y0, Cr, Y1 pixel pairs.
Definition ra8_camera.h:65
ra8_err_t ra8_camera_source_capture(ra8_camera_source_t *source, const ra8_camera_buffer_t *buffer, ra8_camera_frame_t *out_frame)
Capture one frame into a caller-owned buffer.
Definition ra8_camera.c:146
ra8_err_t ra8_camera_codec_encode(ra8_camera_codec_t *codec, const ra8_camera_frame_t *input, const ra8_camera_buffer_t *output_buffer, ra8_camera_frame_t *out_frame)
Encode or transform one frame through a bound codec.
Definition ra8_camera.c:187
RGB888-to-JPEG software codec backend for ra8_camera.
ra8_err_t ra8_camera_codec_jpeg_sw_init(ra8_camera_codec_t *codec, ra8_camera_codec_jpeg_sw_state_t *state, const ra8_camera_codec_jpeg_sw_cfg_t *cfg)
Bind the software baseline-JPEG encoder backend.
RA8 CEU capture backend for the transport-neutral camera facade.
ra8_err_t ra8_camera_source_ceu_get_last_events(const ra8_camera_source_ceu_state_t *state, uint32_t *out_events)
Read the most recent CEU event snapshot retained by the backend.
ra8_err_t ra8_camera_source_ceu_init(ra8_camera_source_t *source, ra8_camera_source_ceu_state_t *state, const ra8_camera_source_ceu_cfg_t *cfg)
Initialize the CEU and bind it as a generic camera source.
Capture Engine Unit (CEU) camera-capture driver.
@ k_ra8_ceu_input_cb0_y0_cr0_y1
Cb0 Y0 Cr0 Y1.
@ k_ra8_ceu_burst_32
32-byte bus bursts.
@ k_ra8_ceu_capture_single
CE auto-clears after CPE.
@ k_ra8_ceu_fmt_data_synchronous
Raw synchronous data fetch.
@ k_ra8_ceu_field_immediate
Capture starts at next VD.
@ k_ra8_ceu_pol_high_active
Sync signal is active high.
@ k_ra8_ceu_bus_8_bit
VIO_D[7:0] used.
@ k_ra8_ceu_edge_rising
Sample on rising VIO_CLK edge.
@ k_ra8_ceu_output_ycbcr_422
Pass-through (no conversion).
@ k_ra8_err_hw_init_failed
Hardware peripheral failed to initialise.
Definition ra8_err.h:290
@ k_ra8_ok
Success – operation completed with all postconditions satisfied.
Definition ra8_err.h:119
@ k_ra8_err_null_ptr
Pointer was NULL where a valid pointer was required.
Definition ra8_err.h:478
ra8_err_codes_t ra8_err_t
Canonical error-return type used by every ra8-firmware API.
Definition ra8_err.h:546
Transport-independent OmniVision OV5640 sensor driver.
@ k_ra8_ov5640_chip_id
Expected combined chip identifier.
Definition ra8_ov5640.h:31
ra8_err_t ra8_ov5640_configure(ra8_ov5640_t *dev, ra8_ov5640_mode_t mode)
Software-reset and program one validated output mode.
Definition ra8_ov5640.c:801
ra8_err_t ra8_ov5640_probe(ra8_ov5640_t *dev, uint16_t *out_id)
Probe both legal SCCB addresses and verify chip ID 0x5640.
Definition ra8_ov5640.c:612
@ k_ra8_ov5640_mode_vga_uyvy
Packed VGA UYVY DVP stream.
Definition ra8_ov5640.h:41
ra8_err_t ra8_ov5640_init(ra8_ov5640_t *dev, const ra8_ov5640_bus_t *bus)
Bind a caller-supplied SCCB transport without touching the sensor.
Definition ra8_ov5640.c:484
SysTick-based tick counter, delay and timestamp helpers.
void ra8_delay_ms(uint32_t ms)
Busy-wait for at least ms milliseconds.
Definition ra8_time.c:129
uint32_t ra8_time_ms(void)
Get the current 1 kHz tick count.
Definition ra8_time.c:108
Per-frame pipeline latency exposed in HTTP Server-Timing headers.
uint32_t timestamp_ms
Capture-start monotonic timestamp.
uint32_t capture_ms
Camera capture latency.
uint32_t encode_ms
Codec latency.
Caller-owned writable byte-buffer description.
Definition ra8_camera.h:80
Configuration and caller-owned RGB workspace for software JPEG.
Caller-owned private state for the software JPEG backend.
Caller-owned handle binding one image codec and its context.
Definition ra8_camera.h:145
Immutable view of one captured or encoded image.
Definition ra8_camera.h:96
const uint8_t * data
Borrowed immutable image bytes.
Definition ra8_camera.h:97
uint32_t bytes
Valid bytes beginning at data.
Definition ra8_camera.h:98
Backend configuration, including native CEU register descriptor.
Caller-owned CEU source state.
Caller-owned handle binding one source backend and its context.
Definition ra8_camera.h:131
Full configuration descriptor for ra8_ceu_init.
Injected SCCB and time services.
Definition ra8_ov5640.h:60
Caller-owned sensor instance; supports multiple independent parts.
Definition ra8_ov5640.h:68