vsp-lib: SRU and rotation are not perfectly emulated by gen-image
[renesas/vsp-tests.git] / scripts / vsp-lib.sh
1 #!/bin/sh
2
3 genimage='./gen-image'
4 mediactl='media-ctl'
5 yavta='yavta'
6 frames_dir=/tmp/
7
8 # ------------------------------------------------------------------------------
9 # Miscellaneous
10 #
11
12 vsp1_device() {
13         $mediactl -d $mdev -p | grep 'bus info' | sed 's/.*platform://'
14 }
15
16 vsp1_has_feature() {
17         local feature=$1
18         local entity_name=$(echo $feature | sed 's/\[.*//')
19
20         ($mediactl -d $mdev -p | grep -q -- "- entity.*$entity_name") || return
21
22         local option=$(echo $feature | cut -d '[' -f 2 -s | cut -d ']' -f 1)
23
24         [ -z $option ] && return
25
26         local key=$(echo $option | sed 's/:.*//')
27         local value=$(echo $option | sed "s/.*:'\(.*\)'/\1/")
28
29         case $key in
30         control)
31                 vsp1_has_control $entity_name "$value"
32                 return
33                 ;;
34         *)
35                 return 1
36                 ;;
37         esac
38 }
39
40 vsp1_count_rpfs() {
41         $mediactl -d $mdev -p | grep -- '- entity.*rpf.[0-9] [^i]' | wc -l
42 }
43
44 vsp1_count_wpfs() {
45         $mediactl -d $mdev -p | grep -- '- entity.*wpf.[0-9] [^o]' | wc -l
46 }
47
48 vsp1_count_bru_inputs() {
49         local num_pads=`media-ctl -p | grep 'entity.*bru' | sed 's/.*(\([0-9]\) pads.*/\1/'`
50         echo $((num_pads-1))
51 }
52
53 vsp1_entity_subdev() {
54         $mediactl -d $mdev -e "$dev $1"
55 }
56
57 vsp1_entity_get_size() {
58         local entity=$1
59         local pad=$2
60
61         $mediactl -d $mdev --get-v4l2 "'$dev $entity':$pad" | grep fmt | \
62               sed 's/.*\/\([0-9x]*\).*/\1/'
63 }
64
65 vsp1_has_control() {
66         local subdev=$(vsp1_entity_subdev $1)
67         local control_name=$(echo $2 | tr '+' ' ')
68
69         $yavta --no-query -l $subdev | grep -q -- "$control_name"
70 }
71
72 vsp1_set_control() {
73         local entity=$1
74         local control_name=$(echo $2 | tr '+' ' ')
75         local value=$3
76
77         local subdev=$(vsp1_entity_subdev $entity)
78         local control=$($yavta --no-query -l $subdev | grep -- "$control_name" | cut -d ' ' -f 2)
79
80         echo "Setting control $control_name ($control) to $value" | ./logger.sh "$entity" >> $logfile
81         $yavta --no-query -w "$control $value" $subdev | ./logger.sh "$entity" >> $logfile
82 }
83
84 # -----------------------------------------------------------------------------
85 # Referance frame generation
86 #
87
88 reference_frame() {
89         local file=$1
90         local in_format=$2
91         local out_format=$3
92         local size=$4
93         shift 4
94
95         local alpha=
96         local options=
97
98         # Start with the input format to compute the alpha value being used by
99         # the RPF after unpacking. Keep in sync with generate_input_frame.
100         case $in_format in
101         ARGB555)
102                 # The 1-bit alpha value is expanded to 8 bits by copying the
103                 # high order bits, resulting in value of 255 after unpacking.
104                 alpha=255
105                 ;;
106         ABGR32 | ARGB32)
107                 # 8-bit alpha value, hardcoded to 200.
108                 alpha=200
109                 ;;
110         *)
111                 # In all other cases the alpha value is set through a control
112                 # whose default value is 255.
113                 alpha=255
114                 ;;
115         esac
116
117         # Convert the input alpha value based on the output format.
118         case $out_format in
119         ARGB555 | ABGR32 | ARGB32)
120                 # Pass the 8-bit alpha value unchanged to the image generator.
121                 ;;
122         XRGB555)
123                 # The format has the X bit hardcoded to 0.
124                 alpha=0
125                 ;;
126         *)
127                 # In all other cases the alpha value is set through a control
128                 # whose default value is 255.
129                 alpha=255
130                 ;;
131         esac
132
133         local arg
134         for arg in $* ; do
135                 local name=$(echo $arg | cut -d '=' -f 1)
136                 local value=$(echo $arg | cut -d '=' -f 2)
137
138                 case $name in
139                 clu)
140                         options="$options --clu $value"
141                         ;;
142                 hflip)
143                         [ x$value = x1 ] && options="$options --hflip"
144                         ;;
145                 lut)
146                         options="$options --lut $value"
147                         ;;
148                 rotate)
149                         [ x$value = x90 ] && {
150                                 options="$options --rotate" ;
151                                 __vsp_pixel_perfect=false ;
152                         }
153                         ;;
154                 vflip)
155                         [ x$value = x1 ] && options="$options --vflip"
156                         ;;
157                 esac
158         done
159
160         [ x$__vsp_bru_inputs != x ] && options="$options -c $__vsp_bru_inputs"
161
162         $genimage -i $in_format -f $out_format -s $size -a $alpha $options -o $file \
163                 frames/frame-reference-1024x768.pnm
164 }
165
166 reference_histogram() {
167         local file=$1
168         local format=$2
169         local size=$3
170
171         $genimage -i $format -f $format -s $size -H $file \
172                 frames/frame-reference-1024x768.pnm
173 }
174
175 # ------------------------------------------------------------------------------
176 # Image and histogram comparison
177 #
178
179 #
180 # Compare the two frames for exact match.
181 #
182 compare_frame_exact() {
183         local img_a=$3
184         local img_b=$4
185
186         local match='fail'
187         diff -q $img_a $img_b > /dev/null && match='pass'
188
189         echo "Compared $img_a and $img_b: $match" | ./logger.sh check >> $logfile
190
191         if [ $match = 'pass' ] ; then
192                 return 0
193         else
194                 return 1
195         fi
196 }
197
198 #
199 # Compare the two frames using a fuzzy match algorithm to account for errors
200 # introduced by the YUV packing. Accept a maximum 1% mean average error over
201 # the whole frame with no more than 5% of the pixels differing.
202 #
203 compare_frame_fuzzy() {
204         local fmt=$(echo $1 | sed 's/M$/P/')
205         local size=$2
206         local img_a=$3
207         local img_b=$4
208
209         local pnm_a=${img_a/bin/pnm}
210         local pnm_b=${img_b/bin/pnm}
211
212         raw2rgbpnm -f $fmt -s $size $img_a $pnm_a > /dev/null
213         raw2rgbpnm -f $fmt -s $size $img_b $pnm_b > /dev/null
214
215         local ae=$(compare -metric ae $pnm_a $pnm_b /dev/null 2>&1)
216         local mae=$(compare -metric mae $pnm_a $pnm_b /dev/null 2>&1 | sed 's/.*(\(.*\))/\1/')
217
218         rm $pnm_a
219         rm $pnm_b
220
221         local width=$(echo $size | cut -d 'x' -f 1)
222         local height=$(echo $size | cut -d 'x' -f 2)
223
224         local ae_match=$(echo $ae $width $height | awk '{ if ($1 / $2 / $3 < 0.05) { print "pass" } else { print "fail" } }')
225         local mae_match=$(echo $mae | awk '{ if ($1 < 0.01) { print "pass" } else { print "fail" } }')
226
227         echo "Compared $img_a and $img_b: ae $ae ($ae_match) mae $mae ($mae_match)" | ./logger.sh check >> $logfile
228
229         if [ $ae_match = 'pass' -a $mae_match = 'pass' ] ; then
230                 return 0
231         else
232                 return 1
233         fi
234 }
235
236 compare_frames() {
237         local args=$*
238         local in_format=$__vsp_rpf_format
239         local out_format=$__vsp_wpf_format
240         local wpf=$__vsp_wpf_index
241
242         local in_fmt=$(echo $in_format | tr '[:upper:]' '[:lower:]')
243         local out_fmt=$(echo $out_format | tr '[:upper:]' '[:lower:]')
244         local size=$(vsp1_entity_get_size wpf.$wpf 1)
245         local method=exact
246
247         if [ $__vsp_pixel_perfect != xtrue ] ; then
248                 method=fuzzy
249         fi
250
251         reference_frame ${frames_dir}ref-frame.bin $in_format $out_format $size $args
252
253         local result="pass"
254         local params=${args// /-}
255         params=${params:+-$params}
256         params=${params//\//_}
257         params=$in_fmt-$out_fmt-$size$params
258
259         for frame in ${frames_dir}frame-*.bin ; do
260                 local match="true"
261
262                 (compare_frame_$method $out_format $size $frame ${frames_dir}ref-frame.bin) ||  {
263                         match="false" ;
264                         result="fail" ;
265                 }
266
267                 if [ $match = "false" -o x$VSP_KEEP_FRAMES = x1 ] ; then
268                         mv $frame ${0/.sh/}-$(basename ${frame/.bin/-$params.bin})
269                 fi
270         done
271
272         if [ x$VSP_KEEP_FRAMES = x1 -o $result = "fail" ] ; then
273                 mv ${frames_dir}ref-frame.bin ${0/.sh/}-ref-frame-$params.bin
274         else
275                 rm -f ${frames_dir}ref-frame.bin
276                 rm -f ${frames_dir}frame-*.bin
277         fi
278
279         echo $result
280 }
281
282 compare_histogram() {
283         local histo_a=$1
284         local histo_b=$2
285
286         local match='fail'
287         diff -q $histo_a $histo_b > /dev/null && match='pass'
288
289         echo "Compared $histo_a and $histo_b: $match" | ./logger.sh check >> $logfile
290
291         if [ $match = 'pass' ] ; then
292                 return 0
293         else
294                 return 1
295         fi
296 }
297
298 compare_histograms() {
299         local format=$__vsp_wpf_format
300         local wpf=$__vsp_wpf_index
301
302         local fmt=$(echo $format | tr '[:upper:]' '[:lower:]')
303         local size=$(vsp1_entity_get_size wpf.$wpf 1)
304
305         reference_histogram ${frames_dir}ref-histogram.bin $format $size
306
307         local result="pass"
308         for histo in ${frames_dir}histo-*.bin ; do
309                 (compare_histogram $histo ${frames_dir}ref-histogram.bin) || {
310                         mv $histo ${0/.sh/}-$(basename ${histo/.bin/-$fmt.bin}) ;
311                         result="fail"
312                 }
313         done
314
315         if [ $result = "fail" ] ; then
316                 mv ${frames_dir}ref-histogram.bin ${0/.sh/}-ref-histogram-$fmt.bin
317         else
318                 rm -f ${frames_dir}ref-histogram.bin
319                 rm -f ${frames_dir}histo-*.bin
320         fi
321
322         echo $result
323 }
324
325 # ------------------------------------------------------------------------------
326 # Pipeline configuration
327 #
328
329 pipe_none() {
330         # Nothing to be done
331         return
332 }
333
334 pipe_rpf_bru() {
335         local ninputs=$1
336
337         local bru_output=$(vsp1_count_bru_inputs)
338
339         for input in `seq 0 1 $((ninputs-1))` ; do
340                 $mediactl -d $mdev -l "'$dev rpf.$input':1 -> '$dev bru':$input [1]"
341         done
342         $mediactl -d $mdev -l "'$dev bru':$bru_output -> '$dev wpf.0':0 [1]"
343         $mediactl -d $mdev -l "'$dev wpf.0':1 -> '$dev wpf.0 output':0 [1]"
344
345         __vsp_bru_inputs=$ninputs
346         __vsp_wpf_index=0
347 }
348
349 pipe_rpf_bru_uds() {
350         local bru_output=$(vsp1_count_bru_inputs)
351
352         $mediactl -d $mdev -l "'$dev rpf.0':1 -> '$dev bru':0 [1]"
353         $mediactl -d $mdev -l "'$dev bru':$bru_output -> '$dev uds.0':0 [1]"
354         $mediactl -d $mdev -l "'$dev uds.0':1 -> '$dev wpf.0':0 [1]"
355         $mediactl -d $mdev -l "'$dev wpf.0':1 -> '$dev wpf.0 output':0 [1]"
356
357         __vsp_wpf_index=0
358 }
359
360 pipe_rpf_clu() {
361         $mediactl -d $mdev -l "'$dev rpf.0':1 -> '$dev clu':0 [1]"
362         $mediactl -d $mdev -l "'$dev clu':1 -> '$dev wpf.0':0 [1]"
363         $mediactl -d $mdev -l "'$dev wpf.0':1 -> '$dev wpf.0 output':0 [1]"
364
365         __vsp_wpf_index=0
366 }
367
368 pipe_rpf_hgo() {
369         $mediactl -d $mdev -l "'$dev rpf.0':1 -> '$dev wpf.0':0 [1]"
370         $mediactl -d $mdev -l "'$dev rpf.0':1 -> '$dev hgo':0 [1]"
371         $mediactl -d $mdev -l "'$dev wpf.0':1 -> '$dev wpf.0 output':0 [1]"
372
373         __vsp_wpf_index=0
374 }
375
376 pipe_rpf_lut() {
377         $mediactl -d $mdev -l "'$dev rpf.0':1 -> '$dev lut':0 [1]"
378         $mediactl -d $mdev -l "'$dev lut':1 -> '$dev wpf.0':0 [1]"
379         $mediactl -d $mdev -l "'$dev wpf.0':1 -> '$dev wpf.0 output':0 [1]"
380
381         __vsp_wpf_index=0
382 }
383
384 pipe_rpf_uds() {
385         $mediactl -d $mdev -l "'$dev rpf.0':1 -> '$dev uds.0':0 [1]"
386         $mediactl -d $mdev -l "'$dev uds.0':1 -> '$dev wpf.0':0 [1]"
387         $mediactl -d $mdev -l "'$dev wpf.0':1 -> '$dev wpf.0 output':0 [1]"
388
389         __vsp_wpf_index=0
390 }
391
392 pipe_rpf_uds_bru() {
393         local bru_output=$(vsp1_count_bru_inputs)
394
395         $mediactl -d $mdev -l "'$dev rpf.0':1 -> '$dev uds.0':0 [1]"
396         $mediactl -d $mdev -l "'$dev uds.0':1 -> '$dev bru':0 [1]"
397         $mediactl -d $mdev -l "'$dev bru':$bru_output -> '$dev wpf.0':0 [1]"
398         $mediactl -d $mdev -l "'$dev wpf.0':1 -> '$dev wpf.0 output':0 [1]"
399
400         __vsp_wpf_index=0
401 }
402
403 pipe_rpf_sru() {
404         $mediactl -d $mdev -l "'$dev rpf.0':1 -> '$dev sru':0 [1]"
405         $mediactl -d $mdev -l "'$dev sru':1 -> '$dev wpf.0':0 [1]"
406         $mediactl -d $mdev -l "'$dev wpf.0':1 -> '$dev wpf.0 output':0 [1]"
407
408         __vsp_wpf_index=0
409 }
410
411 pipe_rpf_wpf() {
412         local rpf=$1
413         local wpf=$2
414
415         $mediactl -d $mdev -l "'$dev rpf.$rpf':1 -> '$dev wpf.$wpf':0 [1]"
416         $mediactl -d $mdev -l "'$dev wpf.$wpf':1 -> '$dev wpf.$wpf output':0 [1]"
417
418         __vsp_wpf_index=$wpf
419 }
420
421 pipe_reset() {
422         $mediactl -d $mdev -r
423
424         __vsp_bru_inputs=
425         __vsp_rpf_format=
426         __vsp_wpf_index=
427         __vsp_wpf_format=
428         __vsp_pixel_perfect=true
429 }
430
431 pipe_configure() {
432         local pipe=${1//-/_}
433         shift 1
434
435         pipe_reset
436         pipe_$pipe $*
437 }
438
439 # ------------------------------------------------------------------------------
440 # Format Configuration
441 #
442
443 format_v4l2_to_mbus() {
444         case $1 in
445         RGB332 | ARGB555 | XRGB555 | RGB565 | BGR24 | RGB24 | XBGR32 | XRGB32 | ABGR32 | ARGB32)
446                 echo "ARGB32";
447                 ;;
448
449         UYVY | VYUY | YUYV | YVYU | NV12M | NV16M | NV21M | NV61M | YUV420M | YUV422M | YUV444M)
450                 echo "AYUV32"
451                 ;;
452
453         *)
454                 echo "Invalid format $1" >&2
455                 echo -e "Valid formats are
456 \tRGB332, ARGB555, XRGB555, RGB565, BGR24, RGB24,
457 \tXBGR32, XRGB32, ABGR32, ARGB32,
458 \tUYVY, VYUY, YUYV, YVYU,
459 \tNV12M, NV16M, NV21M, NV61M,
460 \tYUV420M, YUV422M, YUV444M" >&2
461                 exit 1
462         esac
463 }
464
465 format_v4l2_is_yuv() {
466         local format=$(format_v4l2_to_mbus $1)
467         [ $format = 'AYUV32' ]
468 }
469
470 format_rpf() {
471         local format=$(format_v4l2_to_mbus $1)
472         local size=$2
473         local rpf=$3
474
475         $mediactl -d $mdev -V "'$dev rpf.$rpf':0 [fmt:$format/$size]"
476
477         __vsp_rpf_format=$1
478 }
479
480 format_rpf_bru() {
481         local format=$(format_v4l2_to_mbus $1)
482         local size=$2
483         local ninputs=$3
484         local offset=0
485
486         local bru_output=$(vsp1_count_bru_inputs)
487
488         for input in `seq 0 1 $((ninputs-1))` ; do
489                 offset=$((offset+50))
490                 $mediactl -d $mdev -V "'$dev rpf.$input':0 [fmt:$format/$size]"
491                 $mediactl -d $mdev -V "'$dev bru':$input   [fmt:$format/$size compose:($offset,$offset)/$size]"
492         done
493
494         $mediactl -d $mdev -V "'$dev bru':$bru_output [fmt:$format/$size]"
495         $mediactl -d $mdev -V "'$dev wpf.0':0 [fmt:$format/$size]"
496         $mediactl -d $mdev -V "'$dev wpf.0':1 [fmt:$format/$size]"
497
498         __vsp_rpf_format=$1
499         __vsp_wpf_format=$1
500 }
501
502 format_rpf_bru_uds() {
503         local infmt=$(format_v4l2_to_mbus $1)
504         local insize=$2
505         local outfmt=$(format_v4l2_to_mbus $3)
506         local outsize=$4
507
508         local bru_output=$(vsp1_count_bru_inputs)
509
510         $mediactl -d $mdev -V "'$dev rpf.0':0 [fmt:$infmt/$insize]"
511         $mediactl -d $mdev -V "'$dev bru':0 [fmt:$infmt/$insize]"
512         $mediactl -d $mdev -V "'$dev bru':$bru_output [fmt:$infmt/$insize]"
513         $mediactl -d $mdev -V "'$dev uds.0':0 [fmt:$infmt/$insize]"
514         $mediactl -d $mdev -V "'$dev uds.0':1 [fmt:$infmt/$outsize]"
515         $mediactl -d $mdev -V "'$dev wpf.0':0 [fmt:$infmt/$outsize]"
516         $mediactl -d $mdev -V "'$dev wpf.0':1 [fmt:$outfmt/$outsize]"
517
518         [ $insize != $outsize ] && __vsp_pixel_perfect=false
519         __vsp_rpf_format=$1
520         __vsp_wpf_format=$3
521 }
522
523 format_rpf_clu() {
524         local format=$(format_v4l2_to_mbus $1)
525         local size=$2
526
527         $mediactl -d $mdev -V "'$dev rpf.0':0 [fmt:$format/$size]"
528         $mediactl -d $mdev -V "'$dev clu':0 [fmt:$format/$size]"
529         $mediactl -d $mdev -V "'$dev clu':1 [fmt:$format/$size]"
530         $mediactl -d $mdev -V "'$dev wpf.0':0 [fmt:$format/$size]"
531         $mediactl -d $mdev -V "'$dev wpf.0':1 [fmt:$format/$size]"
532
533         __vsp_rpf_format=$1
534         __vsp_wpf_format=$1
535 }
536
537 format_rpf_hgo() {
538         local format=$(format_v4l2_to_mbus $1)
539         local size=$2
540         local crop=${3:+crop:$3}
541         local compose=${4:+compose:$4}
542
543         $mediactl -d $mdev -V "'$dev rpf.0':0 [fmt:$format/$size]"
544         $mediactl -d $mdev -V "'$dev wpf.0':0 [fmt:$format/$size]"
545         $mediactl -d $mdev -V "'$dev wpf.0':1 [fmt:$format/$size]"
546         $mediactl -d $mdev -V "'$dev hgo':0   [fmt:$format/$size $crop $compose]"
547
548         __vsp_rpf_format=$1
549         __vsp_wpf_format=$1
550 }
551
552 format_rpf_lut() {
553         local format=$(format_v4l2_to_mbus $1)
554         local size=$2
555
556         $mediactl -d $mdev -V "'$dev rpf.0':0 [fmt:$format/$size]"
557         $mediactl -d $mdev -V "'$dev lut':0 [fmt:$format/$size]"
558         $mediactl -d $mdev -V "'$dev lut':1 [fmt:$format/$size]"
559         $mediactl -d $mdev -V "'$dev wpf.0':0 [fmt:$format/$size]"
560         $mediactl -d $mdev -V "'$dev wpf.0':1 [fmt:$format/$size]"
561
562         __vsp_rpf_format=$1
563         __vsp_wpf_format=$1
564 }
565
566 format_rpf_uds() {
567         local infmt=$(format_v4l2_to_mbus $1)
568         local insize=$2
569         local outfmt=$(format_v4l2_to_mbus $3)
570         local outsize=$4
571
572         $mediactl -d $mdev -V "'$dev rpf.0':0 [fmt:$infmt/$insize]"
573         $mediactl -d $mdev -V "'$dev uds.0':0 [fmt:$infmt/$insize]"
574         $mediactl -d $mdev -V "'$dev uds.0':1 [fmt:$infmt/$outsize]"
575         $mediactl -d $mdev -V "'$dev wpf.0':0 [fmt:$infmt/$outsize]"
576         $mediactl -d $mdev -V "'$dev wpf.0':1 [fmt:$outfmt/$outsize]"
577
578         [ $insize != $outsize ] && __vsp_pixel_perfect=false
579         __vsp_rpf_format=$1
580         __vsp_wpf_format=$3
581 }
582
583 format_rpf_uds_bru() {
584         local infmt=$(format_v4l2_to_mbus $1)
585         local insize=$2
586         local outfmt=$(format_v4l2_to_mbus $3)
587         local outsize=$4
588
589         local bru_output=$(vsp1_count_bru_inputs)
590
591         $mediactl -d $mdev -V "'$dev rpf.0':0 [fmt:$infmt/$insize]"
592         $mediactl -d $mdev -V "'$dev uds.0':0 [fmt:$infmt/$insize]"
593         $mediactl -d $mdev -V "'$dev uds.0':1 [fmt:$infmt/$outsize]"
594         $mediactl -d $mdev -V "'$dev bru':0 [fmt:$infmt/$outsize]"
595         $mediactl -d $mdev -V "'$dev bru':$bru_output [fmt:$infmt/$outsize]"
596         $mediactl -d $mdev -V "'$dev wpf.0':0 [fmt:$infmt/$outsize]"
597         $mediactl -d $mdev -V "'$dev wpf.0':1 [fmt:$outfmt/$outsize]"
598
599         [ $insize != $outsize ] && __vsp_pixel_perfect=false
600         __vsp_rpf_format=$1
601         __vsp_wpf_format=$3
602 }
603
604 format_rpf_sru() {
605         local infmt=$(format_v4l2_to_mbus $1)
606         local insize=$2
607         local outfmt=$(format_v4l2_to_mbus $3)
608         local outsize=$4
609
610         $mediactl -d $mdev -V "'$dev rpf.0':0 [fmt:$infmt/$insize]"
611         $mediactl -d $mdev -V "'$dev sru':0 [fmt:$infmt/$insize]"
612         $mediactl -d $mdev -V "'$dev sru':1 [fmt:$infmt/$outsize]"
613         $mediactl -d $mdev -V "'$dev wpf.0':0 [fmt:$infmt/$outsize]"
614         $mediactl -d $mdev -V "'$dev wpf.0':1 [fmt:$outfmt/$outsize]"
615
616         __vsp_pixel_perfect=false
617         __vsp_rpf_format=$1
618         __vsp_wpf_format=$3
619 }
620
621 format_rpf_wpf() {
622         local rpf=$1
623         local wpf=$2
624         local infmt=$(format_v4l2_to_mbus $3)
625         local size=$4
626         local outfmt=$(format_v4l2_to_mbus $5)
627         local crop=$6
628         local outsize=
629
630         if [ x$crop != 'x' ] ; then
631                 crop="crop:$crop"
632                 outsize=$(echo $crop | sed 's/.*\///')
633         else
634                 outsize=$size
635         fi
636
637         $mediactl -d $mdev -V "'$dev rpf.$rpf':0 [fmt:$infmt/$size]"
638         $mediactl -d $mdev -V "'$dev wpf.$wpf':0 [fmt:$infmt/$size $crop]"
639         $mediactl -d $mdev -V "'$dev wpf.$wpf':1 [fmt:$outfmt/$outsize]"
640
641         __vsp_rpf_format=$3
642         __vsp_wpf_format=$5
643 }
644
645 format_wpf() {
646         local format=$(format_v4l2_to_mbus $1)
647         local size=$2
648         local wpf=$3
649
650         $mediactl -d $mdev -V "'$dev wpf.$wpf':0 [fmt:$format/$size]"
651         $mediactl -d $mdev -V "'$dev wpf.$wpf':1 [fmt:$format/$size]"
652
653         __vsp_wpf_format=$1
654 }
655
656 format_configure() {
657         local pipe=${1//-/_}
658         shift 1
659
660         format_$pipe $*
661 }
662
663 # ------------------------------------------------------------------------------
664 # Frame capture and output
665 #
666
667 generate_input_frame() {
668         local file=$1
669         local format=$2
670         local size=$3
671
672         local alpha=
673         local options=
674
675         case $format in
676         ARGB555)
677                 alpha=255
678                 ;;
679         ABGR32 | ARGB32)
680                 alpha=200
681                 ;;
682         XRGB555 | XBGR32 | XRGB32)
683                 alpha=0
684                 ;;
685         *)
686                 alpha=255
687                 ;;
688         esac
689
690         $(format_v4l2_is_yuv $format) && options="$options -C -i YUV444M"
691
692         $genimage -f $format -s $size -a $alpha $options -o $file \
693                 frames/frame-reference-1024x768.pnm
694 }
695
696 vsp_runner() {
697         local entity=$1
698         shift
699
700         local option
701         local buffers=4
702         local count=10
703         local pause=
704         local skip=7
705
706         for option in $* ; do
707                 case $option in
708                 --buffers=*)
709                         buffers=${option/--buffers=/}
710                         ;;
711
712                 --count=*)
713                         count=${option/--count=/}
714                         ;;
715
716                 --pause=*)
717                         pause=${option/--pause=/}
718                         ;;
719
720                 --skip=*)
721                         skip=${option/--skip=/}
722                         ;;
723
724                 *)
725                         return 1
726                         ;;
727                 esac
728         done
729
730         local file
731         local videodev
732         local format
733         local size
734
735         case $entity in
736         hgo)
737                 videodev=$(vsp1_entity_subdev "hgo histo")
738                 file="${frames_dir}histo-#.bin"
739                 buffers=10
740                 ;;
741
742         rpf.*)
743                 videodev=$(vsp1_entity_subdev "$entity input")
744                 format=$__vsp_rpf_format
745                 size=$(vsp1_entity_get_size $entity 0)
746                 file=${frames_dir}${entity}.bin
747                 generate_input_frame $file $format $size
748                 ;;
749
750         wpf.*)
751                 videodev=$(vsp1_entity_subdev "$entity output")
752                 format=$__vsp_wpf_format
753                 size=$(vsp1_entity_get_size $entity 1)
754                 file="${frames_dir}frame-#.bin"
755                 ;;
756         esac
757
758         $yavta -c$count -n $buffers ${format:+-f $format} ${size:+-s $size} \
759                 ${skip:+--skip $skip} ${file:+--file=$file} ${pause:+-p$pause} \
760                 $videodev | ./logger.sh $entity >> $logfile
761 }
762
763 vsp_runner_find() {
764         local entity=$1
765         local videodev
766
767         case $entity in
768         hgo)
769                 videodev=$(vsp1_entity_subdev "hgo histo")
770                 ;;
771
772         rpf.*)
773                 videodev=$(vsp1_entity_subdev "$entity input")
774                 ;;
775
776         wpf.*)
777                 videodev=$(vsp1_entity_subdev "$entity output")
778                 ;;
779         esac
780
781         local pid
782
783         for pid in $(pidof yavta) ; do
784                 (ls -l /proc/$pid/fd/ | grep -q "$videodev$") && {
785                         echo $pid ;
786                         break
787                 }
788         done
789 }
790
791 vsp_runner_wait() {
792         local timeout=5
793         local pid
794
795         while [ $timeout != 0 ] ; do
796                 pid=$(vsp_runner_find $1)
797                 [ x$pid != x ] && break
798                 sleep 1
799                 timeout=$((timeout-1))
800         done
801
802         [ x$pid != x ] || return
803
804         while [ ! -f .yavta.wait.$pid ] ; do
805                 sleep 1
806         done
807 }
808
809 vsp_runner_resume() {
810         local pid=$(vsp_runner_find $1)
811
812         [ x$pid != x ] && kill -USR1 $pid
813 }
814
815 # ------------------------------------------------------------------------------
816 # Test run
817 #
818
819 test_init() {
820         export logfile=${1/sh/log}
821         local features=$2
822         local optional_features=$3
823
824         rm -f $logfile
825         rm -f ${1/.sh/}*.bin
826
827         local best_features_count=0
828         local best_mdev=
829
830         for mdev in /dev/media* ; do
831                 dev=$(vsp1_device $mdev)
832
833                 local match='true'
834                 for feature in $features ; do
835                         $(vsp1_has_feature "$feature") || {
836                                 match='false';
837                                 break;
838                         }
839                 done
840
841                 if [ $match == 'false' ] ; then
842                         continue
843                 fi
844
845                 if [ -z "$optional_features" ] ; then
846                         best_mdev=$mdev
847                         break
848                 fi
849
850                 local features_count=0
851                 for feature in $optional_features ; do
852                         $(vsp1_has_feature "$feature") && {
853                                 features_count=$((features_count+1))
854                                 match='false';
855                                 break;
856                         }
857                 done
858
859                 if [ $features_count -ge $best_features_count ] ; then
860                         best_mdev=$mdev
861                         best_features_count=$features_count
862                 fi
863         done
864
865         if [ -z $best_mdev ] ; then
866                 echo "No device found with feature set $features" | ./logger.sh config >> $logfile
867                 exit 1
868         fi
869
870         mdev=$best_mdev
871         dev=$(vsp1_device $mdev)
872         echo "Using device $mdev ($dev)" | ./logger.sh config >> $logfile
873
874         vsp_runner=./vsp-runner.sh
875 }
876
877 test_start() {
878         echo "Testing $1" | ./logger.sh >> $logfile
879         echo -n "Testing $1: " >&2
880 }
881
882 test_complete() {
883         echo "Done: $1" | ./logger.sh >> $logfile
884         echo $1 >&2
885
886         rm -f ${frames_dir}frame-*.bin
887         rm -f ${frames_dir}histo-*.bin
888         rm -f ${frames_dir}rpf.*.bin
889 }
890
891 test_run() {
892         test_main | ./logger.sh error >> $logfile
893 }