aboutsummaryrefslogtreecommitdiffstats
path: root/target/linux/bcm27xx/patches-5.10/950-0616-media-rpivid-Improve-values-returned-when-setting-ou.patch
diff options
context:
space:
mode:
authorÁlvaro Fernández Rojas <noltari@gmail.com>2021-08-21 10:54:34 +0200
committerÁlvaro Fernández Rojas <noltari@gmail.com>2021-08-21 19:07:07 +0200
commit8299d1f057439f94c6a4412e2e5c5082b82a30c9 (patch)
tree1bf678d61f11f7394493be464c7876e496f7faed /target/linux/bcm27xx/patches-5.10/950-0616-media-rpivid-Improve-values-returned-when-setting-ou.patch
parent33b6885975ce376ff075362b7f0890326043111b (diff)
downloadupstream-8299d1f057439f94c6a4412e2e5c5082b82a30c9.tar.gz
upstream-8299d1f057439f94c6a4412e2e5c5082b82a30c9.tar.bz2
upstream-8299d1f057439f94c6a4412e2e5c5082b82a30c9.zip
bcm27xx: add kernel 5.10 support
Rebased RPi foundation patches on linux 5.10.59, removed applied and reverted patches, wireless patches and defconfig patches. bcm2708: boot tested on RPi B+ v1.2 bcm2709: boot tested on RPi 4B v1.1 4G bcm2711: boot tested on RPi 4B v1.1 4G Signed-off-by: Álvaro Fernández Rojas <noltari@gmail.com>
Diffstat (limited to 'target/linux/bcm27xx/patches-5.10/950-0616-media-rpivid-Improve-values-returned-when-setting-ou.patch')
-rw-r--r--target/linux/bcm27xx/patches-5.10/950-0616-media-rpivid-Improve-values-returned-when-setting-ou.patch216
1 files changed, 216 insertions, 0 deletions
diff --git a/target/linux/bcm27xx/patches-5.10/950-0616-media-rpivid-Improve-values-returned-when-setting-ou.patch b/target/linux/bcm27xx/patches-5.10/950-0616-media-rpivid-Improve-values-returned-when-setting-ou.patch
new file mode 100644
index 0000000000..7aa3e22778
--- /dev/null
+++ b/target/linux/bcm27xx/patches-5.10/950-0616-media-rpivid-Improve-values-returned-when-setting-ou.patch
@@ -0,0 +1,216 @@
+From 60374506d427194b8ebb8963f5358bffd347c2e3 Mon Sep 17 00:00:00 2001
+From: John Cox <jc@kynesim.co.uk>
+Date: Thu, 1 Apr 2021 16:20:58 +0100
+Subject: [PATCH] media: rpivid: Improve values returned when setting
+ output format
+
+Guess a better value for the compressed bitstream buffer size
+
+Signed-off-by: John Cox <jc@kynesim.co.uk>
+---
+ drivers/staging/media/rpivid/rpivid_h265.c | 66 ++++-----------------
+ drivers/staging/media/rpivid/rpivid_video.c | 61 +++++++++++++++++--
+ drivers/staging/media/rpivid/rpivid_video.h | 4 ++
+ 3 files changed, 70 insertions(+), 61 deletions(-)
+
+--- a/drivers/staging/media/rpivid/rpivid_h265.c
++++ b/drivers/staging/media/rpivid/rpivid_h265.c
+@@ -18,6 +18,7 @@
+
+ #include "rpivid.h"
+ #include "rpivid_hw.h"
++#include "rpivid_video.h"
+
+ #define DEBUG_TRACE_P1_CMD 0
+ #define DEBUG_TRACE_EXECUTION 0
+@@ -115,41 +116,9 @@ static int gptr_realloc_new(struct rpivi
+ return 0;
+ }
+
+-/* floor(log2(x)) */
+-static unsigned int log2_size(size_t x)
+-{
+- unsigned int n = 0;
+-
+- if (x & ~0xffff) {
+- n += 16;
+- x >>= 16;
+- }
+- if (x & ~0xff) {
+- n += 8;
+- x >>= 8;
+- }
+- if (x & ~0xf) {
+- n += 4;
+- x >>= 4;
+- }
+- if (x & ~3) {
+- n += 2;
+- x >>= 2;
+- }
+- return (x & ~1) ? n + 1 : n;
+-}
+-
+-static size_t round_up_size(const size_t x)
+-{
+- /* Admit no size < 256 */
+- const unsigned int n = x < 256 ? 8 : log2_size(x) - 1;
+-
+- return x >= (3 << n) ? 4 << n : (3 << n);
+-}
+-
+ static size_t next_size(const size_t x)
+ {
+- return round_up_size(x + 1);
++ return rpivid_round_up_size(x + 1);
+ }
+
+ #define NUM_SCALING_FACTORS 4064 /* Not a typo = 0xbe0 + 0x400 */
+@@ -332,7 +301,7 @@ static int cmds_check_space(struct rpivi
+ if (de->cmd_len + n <= de->cmd_max)
+ return 0;
+
+- newmax = 2 << log2_size(de->cmd_len + n);
++ newmax = roundup_pow_of_two(de->cmd_len + n);
+
+ a = krealloc(de->cmd_fifo, newmax * sizeof(struct rpi_cmd),
+ GFP_KERNEL);
+@@ -1855,23 +1824,10 @@ static void rpivid_h265_setup(struct rpi
+ * slice as we can use the src buf directly
+ */
+ if (!s->frame_end && !de->bit_copy_gptr->ptr) {
+- const size_t wxh = s->sps.pic_width_in_luma_samples *
+- s->sps.pic_height_in_luma_samples;
+ size_t bits_alloc;
+-
+- /* Annex A gives a min compression of 2 @ lvl 3.1
+- * (wxh <= 983040) and min 4 thereafter but avoid
+- * the odity of 983041 having a lower limit than
+- * 983040.
+- * Multiply by 3/2 for 4:2:0
+- */
+- bits_alloc = wxh < 983040 ? wxh * 3 / 4 :
+- wxh < 983040 * 2 ? 983040 * 3 / 4 :
+- wxh * 3 / 8;
+- /* Allow for bit depth */
+- bits_alloc += (bits_alloc *
+- s->sps.bit_depth_luma_minus8) / 8;
+- bits_alloc = round_up_size(bits_alloc);
++ bits_alloc = rpivid_bit_buf_size(s->sps.pic_width_in_luma_samples,
++ s->sps.pic_height_in_luma_samples,
++ s->sps.bit_depth_luma_minus8);
+
+ if (gptr_alloc(dev, de->bit_copy_gptr,
+ bits_alloc,
+@@ -2454,17 +2410,15 @@ static int rpivid_h265_start(struct rpiv
+
+ // Finger in the air PU & Coeff alloc
+ // Will be realloced if too small
+- coeff_alloc = round_up_size(wxh);
+- pu_alloc = round_up_size(wxh / 4);
++ coeff_alloc = rpivid_round_up_size(wxh);
++ pu_alloc = rpivid_round_up_size(wxh / 4);
+ for (i = 0; i != ARRAY_SIZE(ctx->pu_bufs); ++i) {
+ // Don't actually need a kernel mapping here
+ if (gptr_alloc(dev, ctx->pu_bufs + i, pu_alloc,
+- DMA_ATTR_FORCE_CONTIGUOUS |
+- DMA_ATTR_NO_KERNEL_MAPPING))
++ DMA_ATTR_NO_KERNEL_MAPPING))
+ goto fail;
+ if (gptr_alloc(dev, ctx->coeff_bufs + i, coeff_alloc,
+- DMA_ATTR_FORCE_CONTIGUOUS |
+- DMA_ATTR_NO_KERNEL_MAPPING))
++ DMA_ATTR_NO_KERNEL_MAPPING))
+ goto fail;
+ }
+ aux_q_init(ctx);
+--- a/drivers/staging/media/rpivid/rpivid_video.c
++++ b/drivers/staging/media/rpivid/rpivid_video.c
+@@ -42,18 +42,69 @@ static inline unsigned int constrain2x(u
+ (x > y * 2) ? y : x;
+ }
+
++size_t rpivid_round_up_size(const size_t x)
++{
++ /* Admit no size < 256 */
++ const unsigned int n = x < 256 ? 8 : ilog2(x);
++
++ return x >= (3 << n) ? 4 << n : (3 << n);
++}
++
++size_t rpivid_bit_buf_size(unsigned int w, unsigned int h, unsigned int bits_minus8)
++{
++ const size_t wxh = w * h;
++ size_t bits_alloc;
++
++ /* Annex A gives a min compression of 2 @ lvl 3.1
++ * (wxh <= 983040) and min 4 thereafter but avoid
++ * the odity of 983041 having a lower limit than
++ * 983040.
++ * Multiply by 3/2 for 4:2:0
++ */
++ bits_alloc = wxh < 983040 ? wxh * 3 / 4 :
++ wxh < 983040 * 2 ? 983040 * 3 / 4 :
++ wxh * 3 / 8;
++ /* Allow for bit depth */
++ bits_alloc += (bits_alloc * bits_minus8) / 8;
++ return rpivid_round_up_size(bits_alloc);
++}
++
+ int rpivid_prepare_src_format(struct v4l2_pix_format_mplane *pix_fmt)
+ {
++ size_t size;
++ u32 w;
++ u32 h;
++
+ if (pix_fmt->pixelformat != V4L2_PIX_FMT_HEVC_SLICE)
+ return -EINVAL;
+
+- /* Zero bytes per line for encoded source. */
+- pix_fmt->plane_fmt[0].bytesperline = 0;
+- /* Choose some minimum size since this can't be 0 */
+- pix_fmt->plane_fmt[0].sizeimage = max_t(u32, SZ_1K,
+- pix_fmt->plane_fmt[0].sizeimage);
++ w = pix_fmt->width;
++ h = pix_fmt->height;
++ if (!w || !h) {
++ w = 1920;
++ h = 1080;
++ }
++ if (w > 4096)
++ w = 4096;
++ if (h > 4096)
++ h = 4096;
++
++ if (!pix_fmt->plane_fmt[0].sizeimage ||
++ pix_fmt->plane_fmt[0].sizeimage > SZ_32M) {
++ /* Unspecified or way too big - pick max for size */
++ size = rpivid_bit_buf_size(w, h, 2);
++ }
++ /* Set a minimum */
++ size = max_t(u32, SZ_4K, pix_fmt->plane_fmt[0].sizeimage);
++
++ pix_fmt->width = w;
++ pix_fmt->height = h;
+ pix_fmt->num_planes = 1;
+ pix_fmt->field = V4L2_FIELD_NONE;
++ /* Zero bytes per line for encoded source. */
++ pix_fmt->plane_fmt[0].bytesperline = 0;
++ pix_fmt->plane_fmt[0].sizeimage = size;
++
+ return 0;
+ }
+
+--- a/drivers/staging/media/rpivid/rpivid_video.h
++++ b/drivers/staging/media/rpivid/rpivid_video.h
+@@ -24,6 +24,10 @@ extern const struct v4l2_ioctl_ops rpivi
+
+ int rpivid_queue_init(void *priv, struct vb2_queue *src_vq,
+ struct vb2_queue *dst_vq);
++
++size_t rpivid_bit_buf_size(unsigned int w, unsigned int h, unsigned int bits_minus8);
++size_t rpivid_round_up_size(const size_t x);
++
+ int rpivid_prepare_src_format(struct v4l2_pix_format_mplane *pix_fmt);
+ int rpivid_prepare_dst_format(struct v4l2_pix_format_mplane *pix_fmt);
+