summaryrefslogtreecommitdiff
path: root/sys
diff options
context:
space:
mode:
authorYouness Alaoui <youness.alaoui@collabora.co.uk>2012-10-30 09:45:55 -0400
committerNicolas Dufresne <nicolas.dufresne@collabora.com>2016-01-21 13:47:02 -0500
commit691ab727b01930c97d8474080ebb0e11b1a550a6 (patch)
treecd0f3d539ded07936fb394266f87e473b9fe072b /sys
parentc85df6807dfa79c068cd45070f5fe3920229fdf3 (diff)
downloadgstreamer-plugins-bad-691ab727b01930c97d8474080ebb0e11b1a550a6.tar.gz
androicamera: if buffer size increases, then readd new buffers to the queue and drop old ones
The on_preview callback gets called with NULL if the buffer in the queue is too small, so we need to handle the case where the array is NULL. Also there is a bug in the android source which makes it drop one of the buffers so if we had 5 buffers, and we renegotiate to a higher resolution, then we'd only get 4 calls to on_preview_frame with NULL, with one being dropped. This means we can't reallocate the buffers in the if (data == NULL) case because we might end up with 0 buffers in the end.
Diffstat (limited to 'sys')
-rw-r--r--sys/androidcamera/gstahcsrc.c27
1 files changed, 19 insertions, 8 deletions
diff --git a/sys/androidcamera/gstahcsrc.c b/sys/androidcamera/gstahcsrc.c
index 7ec14a2ca..8ee70d617 100644
--- a/sys/androidcamera/gstahcsrc.c
+++ b/sys/androidcamera/gstahcsrc.c
@@ -324,7 +324,6 @@ static gboolean
gst_ahc_src_setcaps (GstBaseSrc * src, GstCaps * caps)
{
GstAHCSrc *self = GST_AHC_SRC (src);
- JNIEnv *env = gst_dvm_get_env ();
gboolean ret = FALSE;
GstAHCParameters *params = NULL;
@@ -337,9 +336,8 @@ gst_ahc_src_setcaps (GstBaseSrc * src, GstCaps * caps)
if (params) {
GstVideoFormat format;
gint fmt;
- gint width, height, fps_n, fps_d;
+ gint width, height, fps_n, fps_d, buffer_size;
GList *ranges, *l;
- gint i;
gint range_size = G_MAXINT;
if (!gst_video_format_parse_caps (caps, &format, &width, &height) ||
@@ -418,15 +416,22 @@ gst_ahc_src_setcaps (GstBaseSrc * src, GstCaps * caps)
self->width = width;
self->height = height;
self->format = fmt;
- self->buffer_size = width * height *
+ buffer_size = width * height *
((double) gst_ag_imageformat_get_bits_per_pixel (fmt) / 8);
+ if (buffer_size > self->buffer_size) {
+ JNIEnv *env = gst_dvm_get_env ();
+ gint i;
- for (i = 0; i < NUM_CALLBACK_BUFFERS; i++) {
- jbyteArray array = (*env)->NewByteArray (env, self->buffer_size);
+ for (i = 0; i < NUM_CALLBACK_BUFFERS; i++) {
+ jbyteArray array = (*env)->NewByteArray (env, buffer_size);
- gst_ah_camera_add_callback_buffer (self->camera, array);
- (*env)->DeleteLocalRef (env, array);
+ if (array) {
+ gst_ah_camera_add_callback_buffer (self->camera, array);
+ (*env)->DeleteLocalRef (env, array);
+ }
+ }
}
+ self->buffer_size = buffer_size;
ret = TRUE;
}
@@ -518,6 +523,11 @@ gst_ahc_src_on_preview_frame (jbyteArray data, gpointer user_data)
GstClockTime duration = 0;
GstClock *clock;
+ if (data == NULL) {
+ GST_DEBUG_OBJECT (self, "Size of array in queue is too small, dropping it");
+ return;
+ }
+
if ((clock = GST_ELEMENT_CLOCK (self))) {
GstClockTime base_time = GST_ELEMENT_CAST (self)->base_time;
GstClockTime current_ts;
@@ -580,6 +590,7 @@ gst_ahc_src_open (GstAHCSrc * self)
self->texture = gst_ag_surfacetexture_new (0);
gst_ah_camera_set_preview_texture (self->camera, self->texture);
+ self->buffer_size = 0;
} else {
GST_ELEMENT_ERROR (self, RESOURCE, NOT_FOUND,
("Unable to open device '%d'.", 0), GST_ERROR_SYSTEM);