1 From b4c0c420e616e1cdf7abd309000e779b350fb2da Mon Sep 17 00:00:00 2001
2 From: Dave Stevenson <dave.stevenson@raspberrypi.org>
3 Date: Mon, 24 Sep 2018 17:33:37 +0100
4 Subject: [PATCH] staging: mmal-vchiq: Make a mmal_buf struct for
7 The callback from vchi_mmal to the client was growing lots of extra
8 parameters. Consolidate them into a single struct instead of
9 growing the list further.
10 The struct is associated with the client buffer, therefore there
11 are various changes to setup various containers for the struct,
12 and pass the appropriate members.
14 Signed-off-by: Dave Stevenson <dave.stevenson@raspberrypi.org>
16 .../bcm2835-camera/bcm2835-camera.c | 60 ++++++++++++-------
17 .../vc04_services/vchiq-mmal/mmal-common.h | 5 ++
18 .../vc04_services/vchiq-mmal/mmal-vchiq.c | 29 ++++++---
19 .../vc04_services/vchiq-mmal/mmal-vchiq.h | 3 +-
20 4 files changed, 63 insertions(+), 34 deletions(-)
22 --- a/drivers/staging/vc04_services/bcm2835-camera/bcm2835-camera.c
23 +++ b/drivers/staging/vc04_services/bcm2835-camera/bcm2835-camera.c
24 @@ -72,6 +72,12 @@ static const struct v4l2_fract
25 tpf_max = {.numerator = 1, .denominator = FPS_MIN},
26 tpf_default = {.numerator = 1000, .denominator = 30000};
28 +/* Container for MMAL and VB2 buffers*/
29 +struct vb2_mmal_buffer {
30 + struct vb2_v4l2_buffer vb;
31 + struct mmal_buffer mmal;
35 static struct mmal_fmt formats[] = {
37 @@ -258,14 +264,15 @@ static int buffer_init(struct vb2_buffer
39 struct bm2835_mmal_dev *dev = vb2_get_drv_priv(vb->vb2_queue);
40 struct vb2_v4l2_buffer *vb2 = to_vb2_v4l2_buffer(vb);
41 - struct mmal_buffer *buf = container_of(vb2, struct mmal_buffer, vb);
42 + struct vb2_mmal_buffer *buf =
43 + container_of(vb2, struct vb2_mmal_buffer, vb);
45 v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev, "%s: dev:%p, vb %p\n",
47 - buf->buffer = vb2_plane_vaddr(&buf->vb.vb2_buf, 0);
48 - buf->buffer_size = vb2_plane_size(&buf->vb.vb2_buf, 0);
49 + buf->mmal.buffer = vb2_plane_vaddr(&buf->vb.vb2_buf, 0);
50 + buf->mmal.buffer_size = vb2_plane_size(&buf->vb.vb2_buf, 0);
52 - return mmal_vchi_buffer_init(dev->instance, buf);
53 + return mmal_vchi_buffer_init(dev->instance, &buf->mmal);
56 static int buffer_prepare(struct vb2_buffer *vb)
57 @@ -294,11 +301,13 @@ static void buffer_cleanup(struct vb2_bu
59 struct bm2835_mmal_dev *dev = vb2_get_drv_priv(vb->vb2_queue);
60 struct vb2_v4l2_buffer *vb2 = to_vb2_v4l2_buffer(vb);
61 - struct mmal_buffer *buf = container_of(vb2, struct mmal_buffer, vb);
62 + struct vb2_mmal_buffer *buf =
63 + container_of(vb2, struct vb2_mmal_buffer, vb);
65 v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev, "%s: dev:%p, vb %p\n",
67 - mmal_vchi_buffer_cleanup(buf);
69 + mmal_vchi_buffer_cleanup(&buf->mmal);
72 static inline bool is_capturing(struct bm2835_mmal_dev *dev)
73 @@ -310,14 +319,16 @@ static inline bool is_capturing(struct b
74 static void buffer_cb(struct vchiq_mmal_instance *instance,
75 struct vchiq_mmal_port *port,
77 - struct mmal_buffer *buf,
78 - unsigned long length, u32 mmal_flags, s64 dts, s64 pts)
79 + struct mmal_buffer *mmal_buf)
81 struct bm2835_mmal_dev *dev = port->cb_ctx;
82 + struct vb2_mmal_buffer *buf =
83 + container_of(mmal_buf, struct vb2_mmal_buffer, mmal);
85 v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
86 "%s: status:%d, buf:%p, length:%lu, flags %u, pts %lld\n",
87 - __func__, status, buf, length, mmal_flags, pts);
88 + __func__, status, buf, mmal_buf->length, mmal_buf->mmal_flags,
92 /* error in transfer */
93 @@ -328,7 +339,7 @@ static void buffer_cb(struct vchiq_mmal_
98 + if (mmal_buf->length == 0) {
100 if (dev->capture.frame_count) {
101 /* empty buffer whilst capturing - expected to be an
102 @@ -344,7 +355,8 @@ static void buffer_cb(struct vchiq_mmal_
103 &dev->capture.frame_count,
104 sizeof(dev->capture.frame_count));
106 - if (vchiq_mmal_submit_buffer(instance, port, buf))
107 + if (vchiq_mmal_submit_buffer(instance, port,
109 v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
110 "Failed to return EOS buffer");
112 @@ -371,14 +383,14 @@ static void buffer_cb(struct vchiq_mmal_
113 buf->vb.vb2_buf.timestamp);
114 } else if (mmal_buf->pts != 0) {
116 - s64 runtime_us = pts -
117 + s64 runtime_us = mmal_buf->pts -
118 dev->capture.vc_start_timestamp;
119 timestamp = ktime_add_us(dev->capture.kernel_start_ts,
121 v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
122 "Convert start time %llu and %llu with offset %llu to %llu\n",
123 ktime_to_ns(dev->capture.kernel_start_ts),
124 - dev->capture.vc_start_timestamp, pts,
125 + dev->capture.vc_start_timestamp, mmal_buf->pts,
126 ktime_to_ns(timestamp));
127 if (timestamp < dev->capture.last_timestamp) {
128 v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
129 @@ -407,8 +419,8 @@ static void buffer_cb(struct vchiq_mmal_
130 buf->vb.sequence = dev->capture.sequence++;
131 buf->vb.field = V4L2_FIELD_NONE;
133 - vb2_set_plane_payload(&buf->vb.vb2_buf, 0, length);
134 - if (mmal_flags & MMAL_BUFFER_HEADER_FLAG_KEYFRAME)
135 + vb2_set_plane_payload(&buf->vb.vb2_buf, 0, mmal_buf->length);
136 + if (mmal_buf->mmal_flags & MMAL_BUFFER_HEADER_FLAG_KEYFRAME)
137 buf->vb.flags |= V4L2_BUF_FLAG_KEYFRAME;
139 v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
140 @@ -416,7 +428,7 @@ static void buffer_cb(struct vchiq_mmal_
141 dev->capture.last_timestamp);
142 vb2_buffer_done(&buf->vb.vb2_buf, VB2_BUF_STATE_DONE);
144 - if (mmal_flags & MMAL_BUFFER_HEADER_FLAG_EOS &&
145 + if (mmal_buf->mmal_flags & MMAL_BUFFER_HEADER_FLAG_EOS &&
147 v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
148 "Grab another frame as buffer has EOS");
149 @@ -500,14 +512,16 @@ static void buffer_queue(struct vb2_buff
151 struct bm2835_mmal_dev *dev = vb2_get_drv_priv(vb->vb2_queue);
152 struct vb2_v4l2_buffer *vb2 = to_vb2_v4l2_buffer(vb);
153 - struct mmal_buffer *buf = container_of(vb2, struct mmal_buffer, vb);
154 + struct vb2_mmal_buffer *buf =
155 + container_of(vb2, struct vb2_mmal_buffer, vb);
158 v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
159 "%s: dev:%p buf:%p, idx %u\n",
160 __func__, dev, buf, vb2->vb2_buf.index);
162 - ret = vchiq_mmal_submit_buffer(dev->instance, dev->capture.port, buf);
163 + ret = vchiq_mmal_submit_buffer(dev->instance, dev->capture.port,
166 v4l2_err(&dev->v4l2_dev, "%s: error submitting buffer\n",
168 @@ -621,7 +635,7 @@ static void stop_streaming(struct vb2_qu
169 dev->capture.frame_count = 0;
171 /* ensure a format has actually been set */
172 - if (!dev->capture.port) {
174 v4l2_err(&dev->v4l2_dev,
175 "no capture port - stream not started?\n");
177 @@ -641,11 +655,11 @@ static void stop_streaming(struct vb2_qu
179 /* disable the connection from camera to encoder */
180 ret = vchiq_mmal_port_disable(dev->instance, dev->capture.camera_port);
181 - if (!ret && dev->capture.camera_port != dev->capture.port) {
182 + if (!ret && dev->capture.camera_port != port) {
183 v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
185 - ret = vchiq_mmal_port_disable(dev->instance, dev->capture.port);
186 - } else if (dev->capture.camera_port != dev->capture.port) {
187 + ret = vchiq_mmal_port_disable(dev->instance, port);
188 + } else if (dev->capture.camera_port != port) {
189 v4l2_err(&dev->v4l2_dev, "port_disable failed, error %d\n",
192 @@ -1947,7 +1961,7 @@ static int bcm2835_mmal_probe(struct pla
193 q->type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
194 q->io_modes = VB2_MMAP | VB2_USERPTR | VB2_READ;
196 - q->buf_struct_size = sizeof(struct mmal_buffer);
197 + q->buf_struct_size = sizeof(struct vb2_mmal_buffer);
198 q->ops = &bm2835_mmal_video_qops;
199 q->mem_ops = &vb2_vmalloc_memops;
200 q->timestamp_flags = V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC;
201 --- a/drivers/staging/vc04_services/vchiq-mmal/mmal-common.h
202 +++ b/drivers/staging/vc04_services/vchiq-mmal/mmal-common.h
203 @@ -49,6 +49,11 @@ struct mmal_buffer {
204 unsigned long buffer_size; /* size of allocated buffer */
206 struct mmal_msg_context *msg_context;
208 + unsigned long length;
215 --- a/drivers/staging/vc04_services/vchiq-mmal/mmal-vchiq.c
216 +++ b/drivers/staging/vc04_services/vchiq-mmal/mmal-vchiq.c
217 @@ -258,17 +258,25 @@ static void buffer_work_cb(struct work_s
219 struct mmal_msg_context *msg_context =
220 container_of(work, struct mmal_msg_context, u.bulk.work);
221 + struct mmal_buffer *buffer = msg_context->u.bulk.buffer;
224 + pr_err("%s: ctx: %p, No mmal buffer to pass details\n",
225 + __func__, msg_context);
229 + buffer->length = msg_context->u.bulk.buffer_used;
230 + buffer->mmal_flags = msg_context->u.bulk.mmal_flags;
231 + buffer->dts = msg_context->u.bulk.dts;
232 + buffer->pts = msg_context->u.bulk.pts;
234 atomic_dec(&msg_context->u.bulk.port->buffers_with_vpu);
236 msg_context->u.bulk.port->buffer_cb(msg_context->u.bulk.instance,
237 msg_context->u.bulk.port,
238 msg_context->u.bulk.status,
239 - msg_context->u.bulk.buffer,
240 - msg_context->u.bulk.buffer_used,
241 - msg_context->u.bulk.mmal_flags,
242 - msg_context->u.bulk.dts,
243 - msg_context->u.bulk.pts);
244 + msg_context->u.bulk.buffer);
247 /* workqueue scheduled callback to handle receiving buffers
248 @@ -1326,11 +1334,14 @@ static int port_disable(struct vchiq_mma
249 mmalbuf = list_entry(buf_head, struct mmal_buffer,
252 - if (port->buffer_cb)
253 + if (port->buffer_cb) {
254 + mmalbuf->length = 0;
255 + mmalbuf->mmal_flags = 0;
256 + mmalbuf->dts = MMAL_TIME_UNKNOWN;
257 + mmalbuf->pts = MMAL_TIME_UNKNOWN;
258 port->buffer_cb(instance,
259 - port, 0, mmalbuf, 0, 0,
261 - MMAL_TIME_UNKNOWN);
266 spin_unlock_irqrestore(&port->slock, flags);
267 --- a/drivers/staging/vc04_services/vchiq-mmal/mmal-vchiq.h
268 +++ b/drivers/staging/vc04_services/vchiq-mmal/mmal-vchiq.h
269 @@ -44,8 +44,7 @@ struct vchiq_mmal_port;
270 typedef void (*vchiq_mmal_buffer_cb)(
271 struct vchiq_mmal_instance *instance,
272 struct vchiq_mmal_port *port,
273 - int status, struct mmal_buffer *buffer,
274 - unsigned long length, u32 mmal_flags, s64 dts, s64 pts);
275 + int status, struct mmal_buffer *buffer);
277 struct vchiq_mmal_port {