aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/rpmsg/virtio_rpmsg_bus.c
diff options
context:
space:
mode:
authorSuman Anna <s-anna@ti.com>2014-09-16 14:33:07 -0400
committerOhad Ben-Cohen <ohad@wizery.com>2014-11-26 11:24:36 -0500
commitb1b9891441fa33fd0d49b5cb3aa7f04bca1cc1db (patch)
tree50101517ccd4202654ac1146e6d2d2d9e3c9668f /drivers/rpmsg/virtio_rpmsg_bus.c
parent5d01410fe4d92081f349b013a2e7a95429e4f2c9 (diff)
rpmsg: use less buffers when vrings are small
Adjust the number of rpmsg buffers to rely on the size of the vring, instead of using the hard coded value of 512 (256 per direction). This is needed when small vrings are being used, where 256 buffers are too much to fit in a vring. While considering the vring size, keep using the 512 hard coded value as an upper limit to avoid wacky resource tables consuming unreasonable amount of memory. NOTE: The number of buffers is already assumed to be symmetrical in each direction, and that logic is unchanged. Signed-off-by: Suman Anna <s-anna@ti.com> [edit commit message, small code and comment simplification] Signed-off-by: Ohad Ben-Cohen <ohad@wizery.com>
Diffstat (limited to 'drivers/rpmsg/virtio_rpmsg_bus.c')
-rw-r--r--drivers/rpmsg/virtio_rpmsg_bus.c44
1 files changed, 30 insertions, 14 deletions
diff --git a/drivers/rpmsg/virtio_rpmsg_bus.c b/drivers/rpmsg/virtio_rpmsg_bus.c
index b6135d4d54eb..92f6af6da699 100644
--- a/drivers/rpmsg/virtio_rpmsg_bus.c
+++ b/drivers/rpmsg/virtio_rpmsg_bus.c
@@ -41,6 +41,7 @@
41 * @svq: tx virtqueue 41 * @svq: tx virtqueue
42 * @rbufs: kernel address of rx buffers 42 * @rbufs: kernel address of rx buffers
43 * @sbufs: kernel address of tx buffers 43 * @sbufs: kernel address of tx buffers
44 * @num_bufs: total number of buffers for rx and tx
44 * @last_sbuf: index of last tx buffer used 45 * @last_sbuf: index of last tx buffer used
45 * @bufs_dma: dma base addr of the buffers 46 * @bufs_dma: dma base addr of the buffers
46 * @tx_lock: protects svq, sbufs and sleepers, to allow concurrent senders. 47 * @tx_lock: protects svq, sbufs and sleepers, to allow concurrent senders.
@@ -60,6 +61,7 @@ struct virtproc_info {
60 struct virtio_device *vdev; 61 struct virtio_device *vdev;
61 struct virtqueue *rvq, *svq; 62 struct virtqueue *rvq, *svq;
62 void *rbufs, *sbufs; 63 void *rbufs, *sbufs;
64 unsigned int num_bufs;
63 int last_sbuf; 65 int last_sbuf;
64 dma_addr_t bufs_dma; 66 dma_addr_t bufs_dma;
65 struct mutex tx_lock; 67 struct mutex tx_lock;
@@ -86,13 +88,14 @@ struct rpmsg_channel_info {
86#define to_rpmsg_driver(d) container_of(d, struct rpmsg_driver, drv) 88#define to_rpmsg_driver(d) container_of(d, struct rpmsg_driver, drv)
87 89
88/* 90/*
89 * We're allocating 512 buffers of 512 bytes for communications, and then 91 * We're allocating buffers of 512 bytes each for communications. The
90 * using the first 256 buffers for RX, and the last 256 buffers for TX. 92 * number of buffers will be computed from the number of buffers supported
93 * by the vring, upto a maximum of 512 buffers (256 in each direction).
91 * 94 *
92 * Each buffer will have 16 bytes for the msg header and 496 bytes for 95 * Each buffer will have 16 bytes for the msg header and 496 bytes for
93 * the payload. 96 * the payload.
94 * 97 *
95 * This will require a total space of 256KB for the buffers. 98 * This will utilize a maximum total space of 256KB for the buffers.
96 * 99 *
97 * We might also want to add support for user-provided buffers in time. 100 * We might also want to add support for user-provided buffers in time.
98 * This will allow bigger buffer size flexibility, and can also be used 101 * This will allow bigger buffer size flexibility, and can also be used
@@ -102,9 +105,8 @@ struct rpmsg_channel_info {
102 * can change this without changing anything in the firmware of the remote 105 * can change this without changing anything in the firmware of the remote
103 * processor. 106 * processor.
104 */ 107 */
105#define RPMSG_NUM_BUFS (512) 108#define MAX_RPMSG_NUM_BUFS (512)
106#define RPMSG_BUF_SIZE (512) 109#define RPMSG_BUF_SIZE (512)
107#define RPMSG_TOTAL_BUF_SPACE (RPMSG_NUM_BUFS * RPMSG_BUF_SIZE)
108 110
109/* 111/*
110 * Local addresses are dynamically allocated on-demand. 112 * Local addresses are dynamically allocated on-demand.
@@ -579,7 +581,7 @@ static void *get_a_tx_buf(struct virtproc_info *vrp)
579 * either pick the next unused tx buffer 581 * either pick the next unused tx buffer
580 * (half of our buffers are used for sending messages) 582 * (half of our buffers are used for sending messages)
581 */ 583 */
582 if (vrp->last_sbuf < RPMSG_NUM_BUFS / 2) 584 if (vrp->last_sbuf < vrp->num_bufs / 2)
583 ret = vrp->sbufs + RPMSG_BUF_SIZE * vrp->last_sbuf++; 585 ret = vrp->sbufs + RPMSG_BUF_SIZE * vrp->last_sbuf++;
584 /* or recycle a used one */ 586 /* or recycle a used one */
585 else 587 else
@@ -948,6 +950,7 @@ static int rpmsg_probe(struct virtio_device *vdev)
948 struct virtproc_info *vrp; 950 struct virtproc_info *vrp;
949 void *bufs_va; 951 void *bufs_va;
950 int err = 0, i; 952 int err = 0, i;
953 size_t total_buf_space;
951 954
952 vrp = kzalloc(sizeof(*vrp), GFP_KERNEL); 955 vrp = kzalloc(sizeof(*vrp), GFP_KERNEL);
953 if (!vrp) 956 if (!vrp)
@@ -968,10 +971,22 @@ static int rpmsg_probe(struct virtio_device *vdev)
968 vrp->rvq = vqs[0]; 971 vrp->rvq = vqs[0];
969 vrp->svq = vqs[1]; 972 vrp->svq = vqs[1];
970 973
974 /* we expect symmetric tx/rx vrings */
975 WARN_ON(virtqueue_get_vring_size(vrp->rvq) !=
976 virtqueue_get_vring_size(vrp->svq));
977
978 /* we need less buffers if vrings are small */
979 if (virtqueue_get_vring_size(vrp->rvq) < MAX_RPMSG_NUM_BUFS / 2)
980 vrp->num_bufs = virtqueue_get_vring_size(vrp->rvq) * 2;
981 else
982 vrp->num_bufs = MAX_RPMSG_NUM_BUFS;
983
984 total_buf_space = vrp->num_bufs * RPMSG_BUF_SIZE;
985
971 /* allocate coherent memory for the buffers */ 986 /* allocate coherent memory for the buffers */
972 bufs_va = dma_alloc_coherent(vdev->dev.parent->parent, 987 bufs_va = dma_alloc_coherent(vdev->dev.parent->parent,
973 RPMSG_TOTAL_BUF_SPACE, 988 total_buf_space, &vrp->bufs_dma,
974 &vrp->bufs_dma, GFP_KERNEL); 989 GFP_KERNEL);
975 if (!bufs_va) { 990 if (!bufs_va) {
976 err = -ENOMEM; 991 err = -ENOMEM;
977 goto vqs_del; 992 goto vqs_del;
@@ -984,10 +999,10 @@ static int rpmsg_probe(struct virtio_device *vdev)
984 vrp->rbufs = bufs_va; 999 vrp->rbufs = bufs_va;
985 1000
986 /* and half is dedicated for TX */ 1001 /* and half is dedicated for TX */
987 vrp->sbufs = bufs_va + RPMSG_TOTAL_BUF_SPACE / 2; 1002 vrp->sbufs = bufs_va + total_buf_space / 2;
988 1003
989 /* set up the receive buffers */ 1004 /* set up the receive buffers */
990 for (i = 0; i < RPMSG_NUM_BUFS / 2; i++) { 1005 for (i = 0; i < vrp->num_bufs / 2; i++) {
991 struct scatterlist sg; 1006 struct scatterlist sg;
992 void *cpu_addr = vrp->rbufs + i * RPMSG_BUF_SIZE; 1007 void *cpu_addr = vrp->rbufs + i * RPMSG_BUF_SIZE;
993 1008
@@ -1023,8 +1038,8 @@ static int rpmsg_probe(struct virtio_device *vdev)
1023 return 0; 1038 return 0;
1024 1039
1025free_coherent: 1040free_coherent:
1026 dma_free_coherent(vdev->dev.parent->parent, RPMSG_TOTAL_BUF_SPACE, 1041 dma_free_coherent(vdev->dev.parent->parent, total_buf_space,
1027 bufs_va, vrp->bufs_dma); 1042 bufs_va, vrp->bufs_dma);
1028vqs_del: 1043vqs_del:
1029 vdev->config->del_vqs(vrp->vdev); 1044 vdev->config->del_vqs(vrp->vdev);
1030free_vrp: 1045free_vrp:
@@ -1042,6 +1057,7 @@ static int rpmsg_remove_device(struct device *dev, void *data)
1042static void rpmsg_remove(struct virtio_device *vdev) 1057static void rpmsg_remove(struct virtio_device *vdev)
1043{ 1058{
1044 struct virtproc_info *vrp = vdev->priv; 1059 struct virtproc_info *vrp = vdev->priv;
1060 size_t total_buf_space = vrp->num_bufs * RPMSG_BUF_SIZE;
1045 int ret; 1061 int ret;
1046 1062
1047 vdev->config->reset(vdev); 1063 vdev->config->reset(vdev);
@@ -1057,8 +1073,8 @@ static void rpmsg_remove(struct virtio_device *vdev)
1057 1073
1058 vdev->config->del_vqs(vrp->vdev); 1074 vdev->config->del_vqs(vrp->vdev);
1059 1075
1060 dma_free_coherent(vdev->dev.parent->parent, RPMSG_TOTAL_BUF_SPACE, 1076 dma_free_coherent(vdev->dev.parent->parent, total_buf_space,
1061 vrp->rbufs, vrp->bufs_dma); 1077 vrp->rbufs, vrp->bufs_dma);
1062 1078
1063 kfree(vrp); 1079 kfree(vrp);
1064} 1080}