Merge branch 'akpm' (patches from Andrew)
[linux/fpc-iii.git] / Documentation / media / v4l-drivers / sh_mobile_ceu_camera.rst
blob822fcb8368ae2c885337e24d8fe43b57f03bc57a
1 .. SPDX-License-Identifier: GPL-2.0
3 Cropping and Scaling algorithm, used in the sh_mobile_ceu_camera driver
4 =======================================================================
6 Author: Guennadi Liakhovetski <g.liakhovetski@gmx.de>
8 Terminology
9 -----------
11 sensor scales: horizontal and vertical scales, configured by the sensor driver
12 host scales: -"- host driver
13 combined scales: sensor_scale * host_scale
16 Generic scaling / cropping scheme
17 ---------------------------------
19 .. code-block:: none
21         -1--
22         |
23         -2-- -\
24         |      --\
25         |         --\
26         +-5-- .      -- -3-- -\
27         |      `...            -\
28         |          `... -4-- .   - -7..
29         |                     `.
30         |                       `. .6--
31         |
32         |                        . .6'-
33         |                      .´
34         |           ... -4'- .´
35         |       ...´             - -7'.
36         +-5'- .´               -/
37         |            -- -3'- -/
38         |         --/
39         |      --/
40         -2'- -/
41         |
42         |
43         -1'-
45 In the above chart minuses and slashes represent "real" data amounts, points and
46 accents represent "useful" data, basically, CEU scaled and cropped output,
47 mapped back onto the client's source plane.
49 Such a configuration can be produced by user requests:
51 S_CROP(left / top = (5) - (1), width / height = (5') - (5))
52 S_FMT(width / height = (6') - (6))
54 Here:
56 (1) to (1') - whole max width or height
57 (1) to (2)  - sensor cropped left or top
58 (2) to (2') - sensor cropped width or height
59 (3) to (3') - sensor scale
60 (3) to (4)  - CEU cropped left or top
61 (4) to (4') - CEU cropped width or height
62 (5) to (5') - reverse sensor scale applied to CEU cropped width or height
63 (2) to (5)  - reverse sensor scale applied to CEU cropped left or top
64 (6) to (6') - CEU scale - user window
67 S_FMT
68 -----
70 Do not touch input rectangle - it is already optimal.
72 1. Calculate current sensor scales:
74         scale_s = ((2') - (2)) / ((3') - (3))
76 2. Calculate "effective" input crop (sensor subwindow) - CEU crop scaled back at
77 current sensor scales onto input window - this is user S_CROP:
79         width_u = (5') - (5) = ((4') - (4)) * scale_s
81 3. Calculate new combined scales from "effective" input window to requested user
82 window:
84         scale_comb = width_u / ((6') - (6))
86 4. Calculate sensor output window by applying combined scales to real input
87 window:
89         width_s_out = ((7') - (7)) = ((2') - (2)) / scale_comb
91 5. Apply iterative sensor S_FMT for sensor output window.
93         subdev->video_ops->s_fmt(.width = width_s_out)
95 6. Retrieve sensor output window (g_fmt)
97 7. Calculate new sensor scales:
99         scale_s_new = ((3')_new - (3)_new) / ((2') - (2))
101 8. Calculate new CEU crop - apply sensor scales to previously calculated
102 "effective" crop:
104         width_ceu = (4')_new - (4)_new = width_u / scale_s_new
105         left_ceu = (4)_new - (3)_new = ((5) - (2)) / scale_s_new
107 9. Use CEU cropping to crop to the new window:
109         ceu_crop(.width = width_ceu, .left = left_ceu)
111 10. Use CEU scaling to scale to the requested user window:
113         scale_ceu = width_ceu / width
116 S_CROP
117 ------
119 The :ref:`V4L2 crop API <crop-scale>` says:
121 "...specification does not define an origin or units. However by convention
122 drivers should horizontally count unscaled samples relative to 0H."
124 We choose to follow the advise and interpret cropping units as client input
125 pixels.
127 Cropping is performed in the following 6 steps:
129 1. Request exactly user rectangle from the sensor.
131 2. If smaller - iterate until a larger one is obtained. Result: sensor cropped
132    to 2 : 2', target crop 5 : 5', current output format 6' - 6.
134 3. In the previous step the sensor has tried to preserve its output frame as
135    good as possible, but it could have changed. Retrieve it again.
137 4. Sensor scaled to 3 : 3'. Sensor's scale is (2' - 2) / (3' - 3). Calculate
138    intermediate window: 4' - 4 = (5' - 5) * (3' - 3) / (2' - 2)
140 5. Calculate and apply host scale = (6' - 6) / (4' - 4)
142 6. Calculate and apply host crop: 6 - 7 = (5 - 2) * (6' - 6) / (5' - 5)