Skip to content

Commit 820975a

Browse files
ubiedakartben
authored andcommitted
sensor: afbr_s50: Add private channel to obtain pixel matrix
Each time this sensor gets a reading, it contains a matrix of 4 x 32 pixels containing distance readings, from which the 1-D result is calculated. The private channel would expose this array through Sensor APIs. Signed-off-by: Luis Ubieda <[email protected]>
1 parent f9d9e5b commit 820975a

File tree

4 files changed

+76
-3
lines changed

4 files changed

+76
-3
lines changed

drivers/sensor/broadcom/afbr_s50/afbr_s50.c

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@
1515
#include <zephyr/rtio/rtio.h>
1616
#include <zephyr/rtio/work.h>
1717

18+
#include <zephyr/drivers/sensor/afbr_s50.h>
19+
1820
#include <api/argus_api.h>
1921
#include <platform/argus_irq.h>
2022

@@ -83,7 +85,8 @@ static void data_ready_work_handler(struct rtio_iodev_sqe *iodev_sqe)
8385
}
8486

8587
edata->header.timestamp = sensor_clock_cycles_to_ns(cycles);
86-
edata->header.channels = afbr_s50_encode_channel(SENSOR_CHAN_DISTANCE);
88+
edata->header.channels = afbr_s50_encode_channel(SENSOR_CHAN_DISTANCE) |
89+
afbr_s50_encode_channel(SENSOR_CHAN_AFBR_S50_PIXELS);
8790
edata->header.events = cfg->is_streaming ? afbr_s50_encode_event(SENSOR_TRIG_DATA_READY) :
8891
0;
8992

drivers/sensor/broadcom/afbr_s50/afbr_s50_decoder.c

Lines changed: 40 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99

1010
#include <zephyr/drivers/sensor_clock.h>
1111
#include <api/argus_res.h>
12+
#include <zephyr/drivers/sensor/afbr_s50.h>
1213

1314
#include "afbr_s50_decoder.h"
1415

@@ -20,6 +21,8 @@ uint8_t afbr_s50_encode_channel(uint16_t chan)
2021
switch (chan) {
2122
case SENSOR_CHAN_DISTANCE:
2223
return BIT(0);
24+
case SENSOR_CHAN_AFBR_S50_PIXELS:
25+
return BIT(1);
2326
default:
2427
return 0;
2528
}
@@ -46,7 +49,8 @@ static int afbr_s50_decoder_get_frame_count(const uint8_t *buffer,
4649

4750
switch (chan_spec.chan_type) {
4851
case SENSOR_CHAN_DISTANCE:
49-
if (edata->header.channels & afbr_s50_encode_channel(SENSOR_CHAN_DISTANCE)) {
52+
case SENSOR_CHAN_AFBR_S50_PIXELS:
53+
if (edata->header.channels & afbr_s50_encode_channel(chan_spec.chan_type)) {
5054
*frame_count = 1;
5155
return 0;
5256
}
@@ -68,6 +72,11 @@ static int afbr_s50_decoder_get_size_info(struct sensor_chan_spec chan_spec,
6872
*base_size = sizeof(struct sensor_q31_data);
6973
*frame_size = sizeof(struct sensor_q31_sample_data);
7074
return 0;
75+
case SENSOR_CHAN_AFBR_S50_PIXELS:
76+
*base_size = sizeof(struct sensor_q31_data) +
77+
31 * sizeof(struct sensor_q31_sample_data);
78+
*frame_size = 32 * sizeof(struct sensor_q31_sample_data);
79+
return 0;
7180
default:
7281
return -ENOTSUP;
7382
}
@@ -107,6 +116,36 @@ static int afbr_s50_decoder_decode(const uint8_t *buffer,
107116
*fit = 1;
108117
return 1;
109118
}
119+
case SENSOR_CHAN_AFBR_S50_PIXELS: {
120+
struct sensor_q31_data *out = data_out;
121+
122+
if ((edata->header.channels &
123+
afbr_s50_encode_channel(SENSOR_CHAN_AFBR_S50_PIXELS)) == 0) {
124+
return -ENODATA;
125+
}
126+
127+
out->header.base_timestamp_ns = edata->header.timestamp;
128+
out->header.reading_count = 32;
129+
/* Result comes encoded in Q9.22 format */
130+
out->shift = 9;
131+
132+
for (size_t i = 0 ; i < 32 ; i++) {
133+
if (edata->payload.Pixels[i].Amplitude == 0xFFFF ||
134+
edata->payload.Pixels[i].Status != PIXEL_OK) {
135+
LOG_DBG("Invalid pixel: %zu, Amplitude: %u, Status: %u", i,
136+
edata->payload.Pixels[i].Amplitude,
137+
edata->payload.Pixels[i].Status);
138+
139+
out->readings[i].value = AFBR_PIXEL_INVALID_VALUE;
140+
} else {
141+
out->readings[i].value = edata->payload.Pixels[i].Range;
142+
}
143+
out->readings[i].timestamp_delta = 0;
144+
}
145+
146+
*fit = 1;
147+
return 1;
148+
}
110149
default:
111150
return -EINVAL;
112151
}

drivers/sensor/broadcom/afbr_s50/afbr_s50_decoder.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@
1616
struct afbr_s50_edata {
1717
struct {
1818
uint64_t timestamp;
19-
uint8_t channels : 1;
19+
uint8_t channels : 2;
2020
uint8_t events : 1;
2121
} header;
2222
argus_results_t payload;
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
/*
2+
* Copyright (c) 2025 Croxel Inc.
3+
* Copyright (c) 2025 CogniPilot Foundation
4+
*
5+
* SPDX-License-Identifier: Apache-2.0
6+
*/
7+
8+
#ifndef ZEPHYR_INCLUDE_DRIVERS_SENSOR_AFBR_S50_H_
9+
#define ZEPHYR_INCLUDE_DRIVERS_SENSOR_AFBR_S50_H_
10+
11+
#include <zephyr/drivers/sensor.h>
12+
13+
#ifdef __cplusplus
14+
extern "C" {
15+
#endif
16+
17+
/** Disregard pixel reading if contains this value */
18+
#define AFBR_PIXEL_INVALID_VALUE 0x80000000
19+
20+
/** Private sensor channel to obtain matrix of pixels with readings in meters.
21+
* This sensor supports up to 32 pixels in a single reading (4 x 8 matrix).
22+
*/
23+
enum sensor_channel_afbr_s50 {
24+
SENSOR_CHAN_AFBR_S50_PIXELS = SENSOR_CHAN_PRIV_START + 1,
25+
};
26+
27+
#ifdef __cplusplus
28+
}
29+
#endif
30+
31+
#endif /* ZEPHYR_INCLUDE_DRIVERS_SENSOR_AFBR_S50_H_ */

0 commit comments

Comments
 (0)