ipc: static_vrings: Support DT-defined buffer size

Recently OpenAMP introduced the possibility to set the sizes for TX and
RX buffers per created instance. Expose this also to Zephyr users by
using a DT property "zephyr,buffer-size".

For the sake of simplicity use the same DT property to set the buffer
size for both TX and RX buffers.

Signed-off-by: Carlo Caione <ccaione@baylibre.com>
This commit is contained in:
Carlo Caione 2022-05-24 12:58:40 +02:00 committed by Carles Cufí
commit 01305942f6
7 changed files with 35 additions and 12 deletions

View file

@ -44,3 +44,10 @@ properties:
When this property is missing a default priority of <0 PRIO_COOP> is
assumed.
zephyr,buffer-size:
type: int
required: false
description: |
The size of the buffer used to send data between host and remote. Default
value is RPMSG_BUFFER_SIZE. This property must be the same for host and remote.

View file

@ -91,6 +91,7 @@ struct ipc_rpmsg_instance {
*
* @param instance Pointer to the RPMsg instance struct.
* @param role Host / Remote role.
* @param buffer_size Size of the buffer used to send data between host and remote.
* @param shm_io SHM IO region pointer.
* @param vdev VirtIO device pointer.
* @param shb Shared memory region pointer.
@ -105,6 +106,7 @@ struct ipc_rpmsg_instance {
*/
int ipc_rpmsg_init(struct ipc_rpmsg_instance *instance,
unsigned int role,
unsigned int buffer_size,
struct metal_io_region *shm_io,
struct virtio_device *vdev,
void *shb, size_t size,

View file

@ -42,6 +42,7 @@
mbox-names = "tx", "rx";
role = "host";
zephyr,priority = <1 PRIO_COOP>;
zephyr,buffer-size = <128>;
status = "okay";
};
};

View file

@ -42,6 +42,7 @@
mbox-names = "rx", "tx";
role = "remote";
zephyr,priority = <2 PRIO_PREEMPT>;
zephyr,buffer-size = <128>;
status = "okay";
};
};

View file

@ -56,6 +56,7 @@ struct backend_config_t {
unsigned int wq_prio_type;
unsigned int wq_prio;
unsigned int id;
unsigned int buffer_size;
};
static void rpmsg_service_unbind(struct rpmsg_endpoint *ep)
@ -226,15 +227,15 @@ static int vr_shm_configure(struct ipc_static_vrings *vr, const struct backend_c
{
unsigned int num_desc;
num_desc = optimal_num_desc(conf->shm_size);
num_desc = optimal_num_desc(conf->shm_size, conf->buffer_size);
if (num_desc == 0) {
return -ENOMEM;
}
vr->shm_addr = conf->shm_addr + VDEV_STATUS_SIZE;
vr->shm_size = shm_size(num_desc) - VDEV_STATUS_SIZE;
vr->shm_size = shm_size(num_desc, conf->buffer_size) - VDEV_STATUS_SIZE;
vr->rx_addr = vr->shm_addr + VRING_COUNT * vq_ring_size(num_desc);
vr->rx_addr = vr->shm_addr + VRING_COUNT * vq_ring_size(num_desc, conf->buffer_size);
vr->tx_addr = vr->rx_addr + vring_size(num_desc, VRING_ALIGNMENT);
vr->status_reg_addr = conf->shm_addr;
@ -473,7 +474,8 @@ static int open(const struct device *instance)
rpmsg_inst->bound_cb = bound_cb;
rpmsg_inst->cb = ept_cb;
err = ipc_rpmsg_init(rpmsg_inst, data->role, data->vr.shm_io, &data->vr.vdev,
err = ipc_rpmsg_init(rpmsg_inst, data->role, conf->buffer_size,
data->vr.shm_io, &data->vr.vdev,
(void *) data->vr.shm_device.regions->virt,
data->vr.shm_device.regions->size, ns_bind_cb);
if (err != 0) {
@ -619,6 +621,8 @@ static int backend_init(const struct device *instance)
.wq_prio_type = COND_CODE_1(DT_INST_NODE_HAS_PROP(i, zephyr_priority), \
(DT_INST_PROP_BY_IDX(i, zephyr_priority, 1)), \
(PRIO_COOP)), \
.buffer_size = DT_INST_PROP_OR(i, zephyr_buffer_size, \
RPMSG_BUFFER_SIZE), \
.id = i, \
}; \
\

View file

@ -138,24 +138,24 @@
#define ROLE_HOST VIRTIO_DEV_DRIVER
#define ROLE_REMOTE VIRTIO_DEV_DEVICE
static inline size_t vq_ring_size(unsigned int num)
static inline size_t vq_ring_size(unsigned int num, unsigned int buf_size)
{
return (RPMSG_BUFFER_SIZE * num);
return (buf_size * num);
}
static inline size_t shm_size(unsigned int num)
static inline size_t shm_size(unsigned int num, unsigned int buf_size)
{
return (VDEV_STATUS_SIZE + (VRING_COUNT * vq_ring_size(num)) +
return (VDEV_STATUS_SIZE + (VRING_COUNT * vq_ring_size(num, buf_size)) +
(VRING_COUNT * vring_size(num, VRING_ALIGNMENT)));
}
static inline unsigned int optimal_num_desc(size_t shm_size)
static inline unsigned int optimal_num_desc(size_t shm_size, unsigned int buf_size)
{
size_t available, single_alloc;
unsigned int num_desc;
available = shm_size - VDEV_STATUS_SIZE;
single_alloc = VRING_COUNT * (vq_ring_size(1) + vring_size(1, VRING_ALIGNMENT));
single_alloc = VRING_COUNT * (vq_ring_size(1, buf_size) + vring_size(1, VRING_ALIGNMENT));
num_desc = (unsigned int) (available / single_alloc);

View file

@ -71,6 +71,7 @@ int ipc_rpmsg_register_ept(struct ipc_rpmsg_instance *instance, unsigned int rol
int ipc_rpmsg_init(struct ipc_rpmsg_instance *instance,
unsigned int role,
unsigned int buffer_size,
struct metal_io_region *shm_io,
struct virtio_device *vdev,
void *shb, size_t size,
@ -87,9 +88,16 @@ int ipc_rpmsg_init(struct ipc_rpmsg_instance *instance,
}
if (role == RPMSG_HOST) {
struct rpmsg_virtio_config config;
config.h2r_buf_size = (uint32_t) buffer_size;
config.r2h_buf_size = (uint32_t) buffer_size;
rpmsg_virtio_init_shm_pool(&instance->shm_pool, shb, size);
return rpmsg_init_vdev(&instance->rvdev, vdev, bind_cb,
shm_io, &instance->shm_pool);
return rpmsg_init_vdev_with_config(&instance->rvdev, vdev, bind_cb,
shm_io, &instance->shm_pool,
&config);
} else {
return rpmsg_init_vdev(&instance->rvdev, vdev, bind_cb, shm_io, NULL);
}