-
Notifications
You must be signed in to change notification settings - Fork 0
/
ZVBI.pm
3168 lines (2303 loc) · 123 KB
/
ZVBI.pm
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
#
# Copyright (C) 2006-2020 T. Zoerner.
#
# Man page descriptions are in part copied from libzvbi documentation:
#
# Copyright (C) 2002-2007 Michael H. Schimek
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# For a copy of the GPL refer to <http://www.gnu.org/licenses/>
#
# $Id: ZVBI.pm,v 1.8 2020/04/01 07:16:37 tom Exp tom $
#
package Video::ZVBI;
use strict;
use warnings;
use 5.007_001; # uvuni_to_utf8 - note: also in Makefile.PL and META.yml
require Exporter;
require DynaLoader;
our @ISA = ('Exporter', 'DynaLoader');
our $VERSION = "1.1.1"; # remember to update README and META.yml too
our @EXPORT = qw();
our @EXPORT_OK = qw(); # filled by XSUB
bootstrap Video::ZVBI $VERSION;
1;
__END__
=head1 NAME
Video::ZVBI - VBI decoding (teletext, closed caption, ...)
=head1 SYNOPSIS
use Video::ZVBI;
# OR: to import all constants
use Video::ZVBI qw(/^VBI_/);
=head1 DESCRIPTION
This module provides a Perl interface to B<libzvbi>. The ZVBI library
allows to access broadcast data services such as teletext or
closed caption via analog video or DVB capture devices.
Official library description:
"The ZVBI library provides routines to access raw VBI sampling devices
(currently the Linux V4L & V4L2 APIs and the FreeBSD, OpenBSD,
NetBSD and BSDi bktr driver API are supported), a versatile raw VBI
bit slicer, decoders for various data services and basic search, render
and export functions for text pages. The library was written for the
Zapping TV viewer and Zapzilla Teletext browser."
The ZVBI Perl module covers all exported libzvbi functions. Most of
the functions and parameters are exposed nearly identical, or with
minor adaptions for the Perl idiom.
Note: This manual page does not reproduce the full documentation provided
by libzvbi by means of doxygen: While method and parameter descriptions
are fully included, some data structures may not be not fully documented
here. Hence when additional details are needed, it's recommended to look
at libzvbi documentation, or directly at its source code.
Finally note there's also another, older, module which covers VBI
data capture: B<Video::Capture::VBI> and based on that another one which
covers Teletext caching: B<Video::TeletextDB>. Check for yourself which
one fits your needs better.
=head1 Class hierarchy
The following is an overview how functionality provided by I<libzvbi> is
structured into classes, and how the classes are connected:
=over 4
=item Class L</Video::ZVBI::capture>
This class allows receiving data through a video device. For
digital television transmissions (DVB) this mostly involves demultiplexing
of the data service sub-stream from the overall transmission stream.
For analog television transmission this involves capturing selected
lines within the Vertical Blanking Interval (VBI) and "demodulating"
the digitized wave form to raw data.
=item Blessed references I<VbiRawBufferPtr> and I<VbiSlicedBufferPtr>
The I<pull> variety of capture methods produce blessed references of types
I<VbiRawBufferPtr> and I<VbiSlicedBufferPtr> for raw VBI samples and
sliced VBI lines respectively. These are transparent pointers to C
structures, and thus not directly accesible from Perl (although there is
function I<Video::ZVBI::get_sliced_line()>, which allows unpacking a
I<VbiSlicedBufferPtr>). They are meant for efficiently and safely
transferring data to decoder methods of classes I<rawdec>, I<vt>,
I<dvb_mux>, and the analog de-multiplexer classes I<idl_demux>,
I<pfc_demux> and I<xds_demux>.
When data is intended to be processed by Perl directly, use the I<read>
variety of capture methods, which return captured data in form of plain
string scalars. Actually the decoder and de-multiplexer classes accept
these scalars too, but it is not recommended to use this as it is less
type-safe.
=item Class L</Video::ZVBI::rawdec>
This class can optionally be used for manually processing raw data
(i.e. direct output of the analog-to-digital conversion of the video
signal) optionally returned by the L</Video::ZVBI::capture> class via I<pull_raw()>
methods et.al. For most use-cases the processing (so-called "slicing")
done under control of the L</Video::ZVBI::capture> class using I<pull_sliced()> should
be sufficient, so this class is usually not needed. This class is not
applicable for DVB.
=item Class L</Video::ZVBI::proxy>
This class allows accessing VBI devices via a proxy daemon. An
instance of this class would be provided to the L</Video::ZVBI::capture> class
constructor. Using the proxy instead of capturing directly from a VBI
device allows multiple applications to capture concurrently (e.g. for
decoding multiple data services). Not applicable to DVB, as the proxy
does not support DVB. (Also at least the Linux DVB driver allows
multiple applications reading the same stream concurrently.)
=item Class L</Video::ZVBI::vt>
Class performing high level decoding of all supported services and storing
the data in an internal cache. The class takes input ("sliced data") from
the L</Video::ZVBI::capture> class. The class supports callback functions
for notifications about received data; various interfaces allow extracting
the data in form of instances of the L</Video::ZVBI::page> class, or
as an image in PPM or XPM formats.
=item Class L</Video::ZVBI::search>
This class allows searching the cache maintained by L</Video::ZVBI::vt> for
pages with text matching a pattern. The search returns instances of
class L</Video::ZVBI::page>.
=item Class L</Video::ZVBI::page>
Instances of this class are produced by the L</Video::ZVBI::vt> query
functions or L</Video::ZVBI::search>. Each instance represents a teletext
(sub-)page or Closed Caption page. The class has various interfaces for
extracting the text and properties of the page content.
=item Class L</Video::ZVBI::export>
This class allows rendering an instance of L</Video::ZVBI::page> in
specific formats, for example as plain-text or image in various formats
such as PNG or PPM. The result can be returned within a string, or written
directly to a file.
=back
In summary: For receiving live data, you'll need at least an instance of
the L</Video::ZVBI::capture> class. Your application is responsible for
calling the capture interface at 25 or 30 Hz intervals (ideally using a
separate thread that blocks on the capture function - but this is not
supported by the Perl module, or else using async I/O via select/poll, or
polling using a timer). For standard services such as Teletext, Closed
Caption, WSS or network identification you'll need to feed the captured
data into an instance of the L</Video::ZVBI::vt> class, which then drives
further processing via callback notifications. For other services you
may use the de-multiplexers listed below, or process the data within your
application directly. After that it depends on your application which
interfaces/classes you want to use for further processing of decoded data.
Special-purpose classes for DVB:
=over 4
=item Class L</Video::ZVBI::dvb_demux>
Class performing de-multiplexing of a transport stream received from a
DVB driver, i.e. separating "VBI" data from a DVB PES stream (EN 301
472, EN 301 775). Note this class is used internally by the
L</Video::ZVBI::capture> class for de-multiplexing. You should only use this
class directly when the data does not originate from a local device.
=item Class L</Video::ZVBI::dvb_mux>
This class converts sliced and optionally raw VBI data to a DVB
Packetized Elementary Stream or Transport Stream as defined in EN 300
472 "Digital Video Broadcasting (DVB); Specification for conveying
ITU-R System B Teletext in DVB bit-streams" and EN 301 775 "Digital
Video Broadcasting (DVB); Specification for the carriage of Vertical
Blanking Information (VBI) data in DVB bit-streams".
=back
The following classes are for de-multiplexing data services transmitted
within teletext packets. For PFC and IDL, libzvbi only supports the
protocol, but the application has to decode and store payload data. XDS is
supported by L</Video::ZVBI::vt> (decoding and event notifications). Most
likely none of these protocols are used anymore, as they were intended for
use via analog television broadcast:
=over 4
=item Class L</Video::ZVBI::idl_demux>
This class allows decoding data transmissions within a Teletext
packet stream using I<Independent Data Line> protocol (EN 300 708 section 6),
i.e. data transmissions based on packet 8/30.
=item Class L</Video::ZVBI::pfc_demux>
Class for separating data transmitted in I<Page Function Clear> teletext
packets (ETS 300 708 section 4), i.e. using regular packets on a dedicated
teletext page. Historically this protocol was used for I<Nextview EPG>,
(i.e. an Electronic Programming Guide for analog television).
=item Class L</Video::ZVBI::xds_demux>
Class for separating I<Extended Data Service> from a Closed Caption stream
(EIA 608). This service allows to transmit "now & next" EPG data in
addition to sub-titles.
=back
=head1 Video::ZVBI::capture
The following functions create and return capture contexts with the
given parameters. Upon success, the returned context can be passed
to the read, pull and other control functions. The context is automatically
deleted and the device closed when the object is destroyed. The meaning
of the parameters to these function is identical to the ZVBI C library.
Upon failure, these functions return I<undef> and an explanatory text
in B<errorstr>.
=over 4
=item $cap = v4l2_new($dev, $buffers, $services, $strict, $errorstr, $trace)
Initializes a device using the Video4Linux API version 2. The function
returns a blessed reference to a capture context. Upon error the function
returns C<undef> as result and an error message in I<$errorstr>
Parameters: I<$dev> is the path of the device to open, usually one of
C</dev/vbi0> or up. I<$buffers> is the number of device buffers for
raw VBI data if the driver supports streaming. Otherwise one bounce
buffer is allocated for I<$cap-E<gt>pull()>. I<$services> is a logical OR
of C<VBI_SLICED_*> symbols describing the data services to be decoded.
On return the services actually decodable will be stored here.
See I<rawdec::add_services()> for details. If you want to capture
raw data only, set to C<VBI_SLICED_VBI_525>, C<VBI_SLICED_VBI_625> or
both. If this parameter is C<undef>, no services will be installed.
You can do so later with I<$cap-E<gt>update_services()> (Note in this
case the I<$reset> parameter to that function will have to be set to 1.)
I<$strict> is passed internally to I<rawdec::add_services()>.
I<$errorstr> is used to return an error description. I<$trace> can be
used to enable output of progress messages on I<stderr>.
=item $cap = v4l_new($dev, $scanning, $services, $strict, $errorstr, $trace)
Initializes a device using the Video4Linux API version 1. Should only
be used after trying Video4Linux API version 2. The function returns
a blessed reference to a capture context. Upon error the function
returns C<undef> as result and an error message in I<$errorstr>
Parameters: I<$dev> is the path of the device to open, usually one of
C</dev/vbi0> or up. I<$scanning> can be used to specify the current
TV norm for old drivers which don't support ioctls to query the current
norm. Allowed values are: 625 for PAL/SECAM family; 525 for NTSC family;
0 if unknown or if you don't care about obsolete drivers. I<$services>,
I<$strict>, I<$errorstr>, I<$trace>: see function I<v4l2_new()> above.
=item $cap = v4l_sidecar_new($dev, $given_fd, $services, $strict, $errorstr, $trace)
Same as I<v4l_new()> however working on an already open device.
Parameter I<$given_fd> must be the numerical file handle, i.e. as
returned by Perl's B<fileno>.
=item $cap = bktr_new($dev, $scanning, $services, $strict, $errorstr, $trace)
Initializes a video device using the BSD "bktr" driver.
Result and parameters are identical to function I<v4l_new()>
=item $cap = dvb_new($dev, $scanning, $services, $strict, $errorstr, $trace)
Initializes a DVB video device. This function is deprecated as it has many
bugs (see libzvbi documentation for details). Use I<dvb_new2()> instead.
=item $cap = dvb_new2($dev, $pid, $errorstr, $trace)
Initializes a DVB video device. The function returns a blessed reference
to a capture context. Upon error the function returns C<undef> as result
and an error message in I<$errorstr>
Parameters: I<$dev> is the path of the DVB device to open. I<$pid>
specifies the number (PID) of a stream which contains the VBI data
service. You can pass 0 here and set or change the PID later with
I<$cap-E<gt>dvb_filter()>. I<$errorstr> is used to return an error
descriptions. I<$trace> can be used to enable output of progress messages
on I<stderr>.
B<Note> the PID value can often be derived from the PID for video in
C<channels.conf> by adding offsets in range 3 to 30. Alternatively you can
look up the PID via Internet services such as L<https://www.satindex.de/>.
=item $cap = $proxy->proxy_new($buffers, $scanning, $services, $strict, $errorstr)
Open a new connection to a VBI proxy to open a VBI device for the
given services. On side of the proxy daemon, one of the regular
capture context creation functions (e.g. I<v4l2_new()>) is invoked.
If the creation succeeds, and any of the requested services are
available, capturing is started and all captured data is forwarded
transparently to the client.
Whenever possible the proxy should be used instead of opening the device
directly, since it allows the user to start multiple VBI clients in
parallel. When this function fails (usually because the user hasn't
started the proxy daemon) applications should automatically fall back
to opening the device directly.
Result: The function returns a blessed reference to a capture context.
Upon error the function returns C<undef> as result and an error message
in I<$errorstr>
Parameters: I<$proxy> is a reference to a previously created proxy
client context (L</Video::ZVBI::proxy>.) The remaining
parameters have the same meaning as described above, as they are used
by the daemon when opening the device.
I<$buffers> specifies the number of intermediate buffers on server side
of the proxy socket connection. (Note this is not related to the
device buffer count.)
I<$scanning> indicates the current norm: 625 for PAL and
525 for NTSC; set to 0 if you don't know (you should not attempt
to query the device for the norm, as this parameter is only required
for old v4l1 drivers which don't support video standard query ioctls.)
I<$services> is a set of C<VBI_SLICED_*> symbols describing the data
services to be decoded. On return I<$services> contains actually
decodable services. See I<Video::ZVBI::rawdec::add_services()>
for details. If you want to capture raw data only, set to
C<VBI_SLICED_VBI_525>, C<VBI_SLICED_VBI_625> or both. If this
parameter is C<undef>, no services will be installed. I<$strict> has
the same meaning as described in the device-specific capture context
creation functions. I<$errorstr> is used to return an error message
when the function fails.
=back
The following functions are used to read raw and sliced VBI data from
a previously created capture context I<$cap> (the reference is implicitly
inserted as first parameter when the functions are invoked as listed
below.) All these functions return a status result code: -1 on error
(and an error indicator in C<$!>), 0 on timeout (i.e. no data arrived
within I<$timeout_ms> milliseconds) or 1 on success. The functions'
output parameters are valid only in case of the latter.
There are two different types of capture functions: The functions
named C<read...> copy captured data into the given Perl scalar. In
contrast the functions named C<pull...> leave the data in internal
buffers inside the capture context and just return a blessed reference
to this buffer. When you need to access the captured data directly
via Perl, choose the read functions. When you use functions of this
module for further decoding, you should use the pull functions since
these are usually more efficient.
=over 4
=item $cap->read_raw($raw_buf, $timestamp, $timeout_ms)
Read a raw VBI frame from the capture device into scalar I<$raw_buf>.
The buffer variable is automatically extended to the exact length
required for the frame's data. The function returns 1 upon success,
0 upon timeout and -1 upon error as described above. On success, the
the function additionally returns in I<$timestamp> the capture instant
in seconds and fractions since 1970-01-01 00:00 in double format.
Parameter I<$timeout_ms> gives the limit for waiting for data in
milliseconds; if no data arrives within the timeout, the function
returns 0. Note the function may fail if the device does not support
reading data in raw format.
Note the returned raw buffer contains all captured VBI lines consecutively
in a one-dimensional array. Length of a line can be queried from the
capture context using I<Video::ZVBI::capture.parameters()>, attribute
I<bytes_per_line>. The number of lines in the buffer is determined by the
values of I<count_a> plus I<count_b>.
=item $cap->read_sliced($sliced_buf, $n_lines, $timestamp, $timeout_ms)
Read a sliced VBI frame from the capture context into scalar
I<$sliced_buf>. The buffer is automatically extended to the length
required for the sliced data. Parameter I<$timeout_ms> specifies the
limit for waiting for data (in milliseconds.)
The function returns 1 upon success, 0 upon timeout and -1 upon error as
described above. On success, the function additionally returns in
I<$timestamp> the capture instant in seconds and fractions since
1970-01-01 00:00 in double format and in I<$n_lines> the number of sliced
lines in the buffer.
Note for efficiency the buffer holds an array of packed C structures of
type I<vbi_sliced>. Use I<get_sliced_line()> for extracting data of
individual VBI lines for processing by Perl, or pass the buffer directly
to class L</Video::ZVBI::vt> or other decoder objects.
Note: it's generally more efficient to use I<pull_sliced()>
instead, as that one may avoid having to copy sliced data into the
given buffer (e.g. for the VBI proxy)
=item $cap->read($raw_buf, $sliced_buf, $n_lines, $timestamp, $timeout_ms)
This function is a combination of I<read_raw()> and I<read_sliced()>, i.e.
reads a raw VBI frame from the capture context into I<$raw_buf> and
decodes it to sliced data which is returned in I<$sliced_buf>. For
details on parameters and results see above.
Note: Depending on the driver, captured raw data may have to be copied
from the capture buffer into the given buffer (e.g. for v4l2 streams which
use memory mapped buffers.) It's generally more efficient to use one of
the following "pull" interfaces, especially if you don't require access
to raw data at all.
=item $cap->pull_raw($ref, $timestamp, $timeout_ms)
Read a raw VBI frame from the capture context, which is returned in
I<$ref> in form of a blessed reference of type I<VbiRawBufferPtr>, which
refers to an internal C data structure. The data remains valid until the
next call to this or any other "pull" function. The reference can be
passed to the decoder function of class L</Video::ZVBI::rawdec>. For
processing raw data by Perl directly, I<read_raw()> is more efficient as
it may avoid copying the data.
The function returns 1 upon success, 0 upon timeout and -1 upon error as
described above. On success, the function additionally returns in
I<$timestamp> the capture instant in seconds and fractions since
1970-01-01 00:00 in double format. Parameter I<$timeout_ms> specifies the
limit for waiting for data (in milliseconds.) Note the function may fail
if the device does not support reading data in raw format.
=item $cap->pull_sliced($ref, $n_lines, $timestamp, $timeout_ms)
Read a sliced VBI frame from the capture context, which is returned in
I<$ref> in form of a blessed reference of type I<VbiSlicedBufferPtr>,
which refers to an internal C data structure. The data remains valid until
the next call to this or any other "pull" function. The reference can be
passed to I<get_sliced_line()> for extracting data of individual VBI lines
for processing the data in Perl, or it can be passed to a
L</Video::ZVBI::vt> decoder object.
The function returns 1 upon success, 0 upon timeout and -1 upon error as
described above. On success, the function additionally returns in
I<$timestamp> the capture instant in seconds and fractions since
1970-01-01 00:00 in double format and in I<$n_lines> the number of sliced
lines in the buffer. Parameter I<$timeout_ms> specifies the limit for
waiting for data (in milliseconds.)
=item $cap->pull($raw_ref, $sliced_ref, $sliced_lines, $timestamp, $timeout_ms)
This function is a combination of I<pull_raw()> and I<pull_sliced()>, i.e.
returns blessed references to an internal raw data buffer of type
I<VbiRawBufferPtr> in I<$raw_ref> and to a sliced data buffer of type
I<VbiSlicedBufferPtr> in I<$sliced_ref>. Scalar I<$sliced_lines> indicates
the number of valid sliced lines in I<$sliced_ref>. For details on
parameters and results see above.
=back
For reasons of efficiency, data is not immediately converted into Perl
structures. Functions of the "read" variety return a byte-string in the
given scalar which contains data of all VBI lines. Functions of the
"pull" variety just return a blessed reference (i.e. a C pointer) of types
I<VbiRawBufferPtr> and I<VbiSlicedBufferPtr> respectively which cannot be
used by Perl for other purposes than passing it to further processing
functions. To process either read or pulled sliced VBI lines by Perl
code, use the following function for extracting parameters and data of
individual VBI lines:
=over 4
=item ($data, $id, $line) = $cap->get_sliced_line($buffer, $line_idx)
The function takes a buffer which was filled by one of the slicer
or capture & slice functions and a line index. The index must be lower
than the line count returned by the slicer. The function returns
a list of three elements: sliced data from the respective line in
the buffer, sliced service type (C<VBI_SLICED_...>) and physical line
number in ITU-R line numbering scheme.
The structure of the data returned in the first element depends on
the kind of data in the VBI line (e.g. for teletext it's 42 bytes,
partly hamming 8/4 and parity encoded; the content in the scalar
after the 42 bytes is undefined.)
=back
The following methods can be used for querying or modifying a capture
context:
=over 4
=item $cap->parameters()
Returns a hash reference describing the physical parameters of the
VBI source. This hash can be used to initialize the raw decoder
context described below.
The hash array has the following members:
=over 8
=item scanning
Either 525 (M/NTSC, M/PAL) or 625 (PAL, SECAM), describing the scan
line system all line numbers refer to.
=item sampling_format
Format of the raw VBI data.
=item sampling_rate
Sampling rate in Hz, the number of samples or pixels captured per second.
=item bytes_per_line
Number of samples or pixels captured per scan line, in bytes. This
determines the raw VBI image width and you want it large enough to
cover all data transmitted in the line (with headroom).
=item offset
The distance from 0H (leading edge hsync, half amplitude point) to
the first sample (pixel) captured, in samples (pixels). You want an
offset small enough not to miss the start of the data transmitted.
=item start_a, start_b
First scan line to be captured, first and second field respectively,
according to the ITU-R line numbering scheme (see vbi_sliced). Set
to zero if the exact line number isn't known.
=item count_a, count_b
Number of scan lines captured, first and second field respectively.
This can be zero if only data from one field is required. The sum
count_a + count_b determines the raw VBI image height.
=item interlaced
In the raw vbi image, normally all lines of the second field are
supposed to follow all lines of the first field. When this flag is
set, the scan lines of first and second field will be interleaved in
memory. This implies count_a and count_b are equal.
=item synchronous
Fields must be stored in temporal order, i. e. as the lines have been
captured. It is assumed that the first field is also stored first in
memory, however if the hardware cannot reliable distinguish fields this
flag shall be cleared, which disables decoding of data services
depending on the field number.
=back
=item $services = $cap->update_services($reset, $commit, $services, $strict, $errorstr)
Adds and/or removes one or more services to an already initialized capture
context. Can be used to dynamically change the set of active services.
Internally the function will restart parameter negotiation with the
VBI device driver and then call I<$rd-E<gt>add_services()> on the internal raw
decoder context. You may set I<$reset> to rebuild your service mask from
scratch. Note that the number of VBI lines may change with this call
even if a negative result is returned.
Result: The function returns a bit-mask of supported services among those
requested (not including previously added services), 0 upon errors.
I<$reset> when set, clears all previous services before adding new
ones (by invoking I<$raw_dec-E<gt>reset()> at the appropriate time.)
I<$commit> when set, applies all previously added services to the device;
when doing subsequent calls of this function, commit should be set only
for the last call. Reading data cannot continue before changes were
committed (because capturing has to be suspended to allow resizing the
VBI image.) Note this flag is ignored when using the VBI proxy.
I<$services> contains a set of C<VBI_SLICED_*> symbols describing the
data services to be decoded. On return the services actually decodable
will be stored here, i.e. the behavior is identical to I<v4l2_new()> etc.
I<$strict> and I<$errorstr> are also same as during capture context
creation.
=item $cap->fd()
This function returns the file descriptor used to read from the
capture context's device. Note when using the proxy this will not
be the actual device, but a socket instead. Some devices may also
return -1 if they don't have anything similar, or upon internal errors.
The descriptor is intended be used in a I<select(2)> syscall. The
application especially must not read or write from it and must never
close the handle (instead destroy the capture context to free the
device.) In other words, the file handle is intended to allow capturing
asynchronously in the background; The handle will become readable
when new data is available.
=item $cap->get_scanning()
This function is intended to allow the application to check for
asynchronous norm changes, i.e. by a different application using the
same device. The function queries the capture device for the current
norm and returns value 625 for PAL/SECAM norms, 525 for NTSC;
0 if unknown, -1 on error.
=item $cap->flush()
After a channel change this function should be used to discard all
VBI data in intermediate buffers which may still originate from the
previous TV channel.
=item $cap->set_video_path($dev)
The function sets the path to the video device for TV norm queries.
Parameter I<$dev> must refer to the same hardware as the VBI device
which is used for capturing (e.g. C</dev/video0> when capturing from
C</dev/vbi0>) Note: only useful for old video4linux drivers which don't
support norm queries through VBI devices.
=item $cap->get_fd_flags()
Returns properties of the capture context's device. The result is an OR
of one or more C<VBI_FD_*> constants:
=over 8
=item VBI_FD_HAS_SELECT
Is set when I<select(2)> can be used on the file handle returned by
I<$cap-E<gt>fd()> to wait for new data on the capture device file handle.
=item VBI_FD_HAS_MMAP
Is set when the capture device supports "user-space DMA". In this case
it's more efficient to use one of the "pull" functions to read raw data
because otherwise the data has to be copied once more into the passed buffer.
=item VBI_FD_IS_DEVICE
Is not set when the capture device file handle is not the actual device.
In this case it can only be used for select(2) and not for ioctl(2)
=back
=item $cap->dvb_filter($pid)
Programs the DVB device transport stream demultiplexer to filter
out PES packets with the given I<$pid>. Returns -1 on failure,
0 on success.
=item $cap->dvb_last_pts()
Returns the presentation time stamp (33 bits) associated with the data
last read from the context. The PTS refers to the first sliced
VBI line, not the last packet containing data of that frame.
Note timestamps returned by VBI capture read functions contain
the sampling time of the data, that is the time at which the
packet containing the first sliced line arrived.
=back
=head1 Video::ZVBI::proxy
The following functions are used for receiving sliced or raw data from
VBI proxy daemon. Using the daemon instead of capturing directly from
a VBI device allows multiple applications to capture concurrently,
e.g. to decode multiple data services.
Note the proxy is only useful if all VBI applications use it. For
applications that do not support the proxy directly, there is a library
that can overload calls to C library, so that access to the VBI device is
redirected transparently through the daemon. Details are described in the
manual I<zvbi-chains(1)>. In principle it's as easy as as prepending
C<zvbi-chains -dev /dev/vbi0> to the application command line.
See C<examples/proxy-test.pl> for examples how to use these functions.
=over 4
=item $proxy = create($dev, $client_name, $flags, $errorstr, $trace)
Creates and returns a new proxy context, or C<undef> upon error.
(Note in reality this call will always succeed, since a connection to
the proxy daemon isn't established until you actually open a capture
context via I<$proxy-E<gt>proxy_new()>)
Parameters: I<$dev> contains the name of the device to open, usually one of
C</dev/vbi0> and up. Note: should be the same path as used by the proxy
daemon, else the client may not be able to connect. I<$client_name>
names the client application, typically identical to I<$0> (without the
path though) Can be used by the proxy daemon to fine-tune scheduling or
to present the user with a list of currently connected applications.
I<$flags> can contain one or more members of C<VBI_PROXY_CLIENT_*> flags.
I<$errorstr> is used to return an error descriptions. I<$trace> can be
used to enable output of progress messages on I<stderr>.
=item $proxy->get_capture_if()
This function is not supported as it does not make sense for the
Perl module. In libzvbi the function returns a reference to a capture
context created from the proxy context via I<$proxy-E<gt>proxy_new()>.
In Perl, you must keep the reference anyway, because otherwise the
capture context would be automatically closed and destroyed. So you
can just use the stored reference instead of using this function.
=item $proxy->set_callback(\&callback [, $user_data])
Installs or removes a callback function for asynchronous messages (e.g.
channel change notifications.) The callback function is typically invoked
while processing a read from the capture device.
Input parameters are a function reference I<$callback> and an optional
scalar I<$user_data> which is passed through to the callback unchanged.
Call without arguments to remove the callback again.
The callback function will receive the event mask (i.e. one of the
constants C<VBI_PROXY_EV_*> in the following list) and, if provided,
I<$user_data> as parameters.
=over 8
=item VBI_PROXY_EV_CHN_GRANTED
The channel control token was granted, so that the client may now change the
channel. Note: the client should return the token after the channel change
was completed (the channel will still remain reserved for the requested
time.)
=item VBI_PROXY_EV_CHN_CHANGED
The channel (e.g. TV tuner frequency) was changed by another proxy client.
=item VBI_PROXY_EV_NORM_CHANGED
The TV norm was changed by another client (in a way which affects VBI,
e.g. changes between PAL/SECAM are ignored.) The client must update
its services, else no data will be forwarded by the proxy until
the norm is changed back.
=item VBI_PROXY_EV_CHN_RECLAIMED
The proxy daemon requests to return the channel control token. The client
is no longer allowed to switch the channel and must immediately reply with
a channel notification with flag C<VBI_PROXY_CHN_TOKEN>
=item VBI_PROXY_EV_NONE
No news.
=back
=item $proxy->get_driver_api()
This function can be used to query which driver is behind the
device which is currently opened by the VBI proxy daemon.
Applications which only use libzvbi's capture API need not
care about this. The information is relevant to applications
which need to switch TV channels or norms.
Returns an identifier describing which API is used on server side,
i.e. one of the symbols
C<VBI_API_V4L1>,
C<VBI_API_V4L2>,
C<VBI_API_BKTR> or
C<VBI_API_UNKNOWN> upon error.
The function will fail if the client is currently not connected to
the proxy daemon, i.e. VBI capture has to be started first.
=item $proxy->channel_request($chn_prio [, $profile])
This function is used to request permission to switch channels or norm.
Since the VBI device can be shared with other proxy clients, clients should
wait for permission, so that the proxy daemon can fairly schedule channel
requests.
Scheduling differs at the 3 priority levels. For available priority levels
for I<$chn_prio> see constants C<VBI_CHN_PRIO_*>. At background level channel
changes are coordinated by introduction of a virtual token: only the
one client which holds the token is allowed to switch channels. The daemon
will wait for the token to be returned before it's granted to another
client. This way conflicting channel changes are avoided. At the upper
levels the latest request always wins. To avoid interference, the
application still might wait until it gets indicated that the token
has been returned to the daemon.
The token may be granted right away or at a later time, e.g. when it has
to be reclaimed from another client first, or if there are other clients
with higher priority. If a callback has been registered, the respective
function will be invoked when the token arrives; otherwise
I<$proxy-E<gt>has_channel_control()> can be used to poll for it.
To set the priority level to "background" only without requesting a channel,
omit the I<$profile> parameter. Else, this parameter must be a reference
to a hash with the following members: "sub_prio", "allow_suspend",
"min_duration" and "exp_duration".
=item $proxy->channel_notify($notify_flags [, $scanning])
Sends channel control request to proxy daemon. Parameter
I<$notify_flags> is an OR of one or more of the following constants:
=over 8
=item VBI_PROXY_CHN_RELEASE
Revoke a previous channel request and return the channel switch
token to the daemon.
=item VBI_PROXY_CHN_TOKEN
Return the channel token to the daemon without releasing the
channel; This should always be done when the channel switch has
been completed to allow faster scheduling in the daemon (i.e. the
daemon can grant the token to a different client without having
to reclaim it first.)
=item VBI_PROXY_CHN_FLUSH
Indicate that the channel was changed and VBI buffer queue
must be flushed; Should be called as fast as possible after
the channel and/or norm was changed. Note this affects other
clients' capturing too, so use with care. Other clients will
be informed about this change by a channel change indication.
=item VBI_PROXY_CHN_NORM
Indicate a norm change. The new norm should be supplied in
the scanning parameter in case the daemon is not able to
determine it from the device directly.
=item VBI_PROXY_CHN_FAIL
Indicate that the client failed to switch the channel because
the device was busy. Used to notify the channel scheduler that
the current time slice cannot be used by the client. If the
client isn't able to schedule periodic re-attempts it should
also return the token.
=back
=item $proxy->channel_suspend($cmd)
Request to temporarily suspend capturing (if I<$cmd> is
C<VBI_PROXY_SUSPEND_START>) or revoke a suspension (if I<$cmd>
equals C<VBI_PROXY_SUSPEND_STOP>.)
=item $proxy->device_ioctl($request, $arg)
This function allows to manipulate parameters of the underlying
VBI device. Not all ioctls are allowed here. It's mainly intended
to be used for channel enumeration and channel/norm changes.
The request codes and parameters are the same as for the actual device.
The caller has to query the driver API via I<$proxy-E<gt>get_driver_api()>
first and use the respective ioctl codes, same as if the device would
be used directly.
Parameters and results are equivalent to the called B<ioctl> operation,
i.e. I<$request> is an IO code and I<$arg> is a packed binary structure.
After the call I<$arg> may be modified for operations which return data.
You must make sure the result buffer is large enough for the returned data.
Use Perl's I<pack> to build the argument buffer. Example:
# get current config of the selected channel
$vchan = pack("ix32iLss", $channel, 0, 0, 0, $norm);
$proxy->device_ioctl(VIDIOCGCHAN, $vchan);
The result is 0 upon success, else and C<$!> set appropriately. The function
also will fail with error code C<EBUSY> if the client doesn't have permission
to control the channel.
=item $proxy->get_channel_desc()
Retrieve info sent by the proxy daemon in a channel change indication.
The function returns a tuple with two elements: scanning value (625
indicating PAL, or 525 indicating NTSC, or 0 if unknown) and a boolean
indicator if the change request was granted.
=item $proxy->has_channel_control()
Returns 1 if client is currently allowed to switch channels, else 0.
=back
=head1 Video::ZVBI::rawdec
The functions in this section allow converting raw VBI samples to
bits and bytes (i.e. analog to digital conversion - even though the
data in a raw VBI buffer is obviously already digital, it's just a
sampled image of the analog wave line.)
These functions are used internally by libzvbi if you use the slicer
functions of the capture object (e.g. I<pull_sliced>)
=over 4
=item $rd = Video::ZVBI::rawdec::new($ref)
Creates and initializes a new raw decoder context. Parameter I<$ref>
specifies the physical parameters of the raw VBI image, such as the
sampling rate, number of VBI lines etc. The parameter can be either
a reference to a capture context (L</Video::ZVBI::capture>)
or a reference to a hash. The contents for the hash are as returned
by method I<$cap-E<gt>parameters()> on capture contexts, i.e. they
describe the physical parameters of the source.
=item $services = Video::ZVBI::rawdec::parameters($href, $services, $scanning, $max_rate)
Calculate the sampling parameters required to receive and decode the
requested data services. This function can be used to initialize
hardware prior to calling I<$rd-E<gt>add_service()>. The returned sampling
format is fixed to C<VBI_PIXFMT_YUV420>, and C<$href-E<gt>{bytes_per_line}>
is set to a reasonable minimum.
Input parameters: I<$href> must be a reference to a hash which is filled
with sampling parameters on return (contents see
I<Video::ZVBI::capture::parameters()>.)
I<$services> is a set of C<VBI_SLICED_*> constants. Here (and only here)
you can add C<VBI_SLICED_VBI_625> or C<VBI_SLICED_VBI_525> to include all
VBI scan lines in the calculated sampling parameters.
If I<$scanning> is set to 525 only NTSC services are accepted; if set to
625 only PAL/SECAM services are accepted. When scanning is 0, the norm is
determined from the requested services; an ambiguous set will result in
undefined behavior.
The function returns a set of C<VBI_SLICED_*> constants describing the
data services covered by the calculated sampling parameters returned in
I<$href>. This excludes services the libzvbi raw decoder cannot decode
assuming the specified physical parameters.
On return parameter I<$max_rate> is set to the highest data bit rate
in B<Hz> of all services requested (The sampling rate should be at least
twice as high; C<$href-E<gt>{sampling_rate}> will be set by libzvbi to a more
reasonable value of 27 MHz derived from ITU-R Rec. 601.)
=item $rd->reset()
Reset a raw decoder context. This removes all previously added services
to be decoded (if any) but does not touch the sampling parameters. You
are free to change the sampling parameters after calling this.
=item $services = $rd->add_services($services, $strict)
After you initialized the sampling parameters in raw decoder context
(according to the abilities of your VBI device), this function adds one
or more data services to be decoded. The libzvbi raw VBI decoder can
decode up to eight data services in parallel. You can call this function
while already decoding, it does not change sampling parameters and you
must not change them either after calling this.
Input parameters: I<$services> is a set of C<VBI_SLICED_*> constants
(see also description of the I<parameters> function above.)
I<$strict> is value of 0, 1 or 2 and requests loose, reliable or strict
matching of sampling parameters respectively. For example if the data
service requires knowledge of line numbers while they are not known,
value 0 will accept the service (which may work if the scan lines are
populated in a non-confusing way) but values 1 or 2 will not. If the
data service may use more lines than are sampled, value 1 will still
accept but value 2 will not. If unsure, set to 1.
Returns a set of C<VBI_SLICED_*> constants describing the data services
that actually can be decoded. This excludes those services not decodable
given sampling parameters of the raw decoder context.
=item $services = $rd->check_services($services, $strict)
Check and return which of the given services can be decoded with
current physical parameters at a given strictness level.
See I<add_services> for details on parameter semantics.
=item $services = $rd->remove_services($services)
Removes one or more data services given in input parameter I<$services>
to be decoded from the raw decoder context. This function can be called
at any time and does not touch sampling parameters stored in the context.
Returns a set of C<VBI_SLICED_*> constants describing the remaining
data services that will be decoded.
=item $rd->resize($start_a, $count_a, $start_b, $count_b)
Grows or shrinks the internal state arrays for VBI geometry changes.
Returns C<undef>.
=item $n_lines = $rd->decode($ref, $buf)