438 Commits

Author SHA1 Message Date
Thilo Graf
593c903846 update to version 1.4.0
- removed azbox, tripledragon
- hisilcon fixes
2020-10-04 17:06:37 +02:00
max_10
f2551c4866 - TRIPLEDRAGON: libtriple deleted 2020-10-04 16:19:49 +02:00
max_10
5a44386b34 - AZBOX: libazbox deleted 2020-10-04 16:19:07 +02:00
BPanther
a3e139776f vuduo4kse added 2020-10-04 16:17:30 +02:00
TangoCash
f74c04e03e - HD61 has ci 2020-10-04 16:17:27 +02:00
TangoCash
4a98c127e2 supplemental to last commit 2020-10-04 16:17:18 +02:00
TangoCash
3e49c20f4c use new define 2020-10-04 16:17:07 +02:00
TangoCash
3084287bd1 fix HD60/HD61 2020-10-04 16:17:02 +02:00
TangoCash
f6cf97a321 fix HD60/HD61 playback 2020-10-04 16:16:57 +02:00
TangoCash
e1c1c07b0d save cover if available, report avfc to streaminfo2 2020-10-03 16:36:13 +02:00
svenhoefer
ecb34f1cd1 - introduce can_cpufreq to control the cpu frequency
Signed-off-by: Thilo Graf <dbt@novatux.de>
2020-09-01 16:58:33 +02:00
DboxOldie
65aee42473 enable limit macros 2020-09-01 16:54:12 +02:00
GetAway
87b90f25ff introduce caps.display_has_colon 2020-07-16 14:44:13 +02:00
Markus Volk
e21785e7d0 playback_hisilicon: add some dummy functions to fix the build 2020-07-11 10:04:54 +02:00
Jacek Jendrzej
2ec2c1f97c libarmbox/playback_libeplayer3.cpp: try to fix box freeze after pause->fastforward 2020-07-05 18:19:08 +02:00
TangoCash
2d58382cdf hdmi cec reduce cpu load 2020-07-01 09:21:24 +02:00
max_10
cf9f93f459 - fix build hd60 2020-07-01 09:20:11 +02:00
max_10
2fbfd158df - hdmi_cec: fix warning: invalid suffix on literal; C++11 requires a space between literal and string macro 2020-07-01 09:20:07 +02:00
TangoCash
801f496c2d hdmi cec optimize timings 2020-07-01 09:19:59 +02:00
svenhoefer
ba934dd995 - rework VUPLUS defines
Signed-off-by: Thilo Graf <dbt@novatux.de>
2020-07-01 09:19:45 +02:00
TangoCash
6137874561 use hdmi_cec device only for VU 2020-07-01 09:19:29 +02:00
TangoCash
162be459ac fix CEC for all arm boxes #2 2020-07-01 09:19:25 +02:00
TangoCash
349cb2dbd4 fix CEC for all arm boxes 2020-07-01 09:19:21 +02:00
svenhoefer
aec6e74897 Revert "- libarmbox: try to fix cec"
This reverts commit bede15daa62c8896d9e43d19c4492cf3e2c26bd2.

Signed-off-by: Thilo Graf <dbt@novatux.de>
2020-07-01 09:18:44 +02:00
Jacek Jendrzej
e52a31f89c libeplayer3/manager/ fix other possible segfault 2020-05-24 15:13:15 +02:00
Jacek Jendrzej
731ed1ea89 libeplayer3/manager/audio.c: fix possible segfault 2020-04-05 07:50:12 +02:00
Jacek Jendrzej
aaf845a711 libgeneric-pc: fix compil - add missing VIDEO_STD enums 2020-03-07 19:52:48 +01:00
Markus Volk
bfc3b5f9d0 libarmbox/video.cpp: fix aspect settings for osmio 2020-03-05 10:03:20 +01:00
Jacek Jendrzej
89bc44dc26 libarmbox/playback_libeplayer3.cpp enable use headers with ffmpeg_av_dict_set 2020-03-03 08:04:28 +01:00
Jacek Jendrzej
cdf663d6b9 libeplayer3: disable mjpeg format,because hardware does not support and this kills PTS (mp3 with attached picture) 2020-03-02 18:50:21 +01:00
Frankenstone
f971434ab3 libarmbox/playback_libeplayer3.cpp: fix segfault when start webstream at first, thx DboxOldie 2020-02-26 10:14:54 +01:00
max_10
55839b5f87 - add osmio4k / osmio4kplus not yet ready
Conflicts:
	acinclude.m4
	libarmbox/hardware_caps.c

Signed-off-by: Thilo Graf <dbt@novatux.de>

osmio4k only
2020-02-26 10:12:36 +01:00
DboxOldie
67110fb054 sh4 eplayer prevent segfaults caused audio rework 2020-02-18 18:54:56 +01:00
TangoCash
480d23dc30 fix init jump 2020-02-18 18:54:42 +01:00
DboxOldie
566ccea279 libeplayer3-sh4: select audio at start 2020-02-18 18:54:27 +01:00
Markus Volk
a5fe472896 unify boxmodel name 2020-02-18 13:55:33 +01:00
Thilo Graf
6b15c22726 update version to 1.3.0 mpx
osmioplus4k added
2020-02-16 11:13:25 +01:00
Markus Volk
f9bb987a43 add osmioplus4k stb 2020-02-16 08:40:39 +01:00
DboxOldie
8f53e0d2d9 reduce arm ifndef warning 2020-02-13 22:00:18 +01:00
Frankenstone
64d853f245 ca_ci.cpp: fix -fpermissive error on aarch64 only arm/mips hardware, thx flk ;-) 2020-02-13 22:00:01 +01:00
Frankenstone
d0c12909c9 Revert "ca_ci.cpp: fix -fpermissive error on aarch64" 2020-02-13 09:56:15 +01:00
BPanther
1b4c5dc1f8 vuplus_arm: fix dmx_source 2020-02-13 09:55:52 +01:00
Markus Volk
f4bc510536 libarmbox/video.cpp: add missing defines
VIDEO_GET_FRAME_RATE was dropped in 4.19 kernel
2020-02-10 14:13:09 +01:00
Markus Volk
7cab06c525 linuxdvb_mipsel.c: add missing define AUDIO_GET_PTS has been removed from kernel 4.8 2020-02-10 10:43:44 +01:00
Markus Volk
a9251b30d1 dmx_hal.h: add needed defines DMX_SET_SOURCE and dmx_source enum removed on 4.14 kernel 2020-02-10 10:43:38 +01:00
BPanther
e22c3033af sh4 fix mp3 (thx DBoxOldie) 2020-02-07 17:44:21 +01:00
BPanther
83437c3656 patch for sh4 and actual ffmpeg versions (thx DBoxOldie) 2020-02-07 17:44:15 +01:00
MarkusVolk
5e3736a0a8 ca_ci.cpp: supplement to 9a9372931a 2020-02-07 10:12:25 +01:00
Markus Volk
9a9372931a ca_ci.cpp: fix -fpermissive error on aarch64
2020-02-06 19:43:08 +01:00
Jacek Jendrzej
0e82fc5325 playback_libeplayer3.cpp: fix compil warning 2020-02-04 17:15:06 +01:00
Thilo Graf
3c2ccc6fee libgeneric-pc: fix possible compiler warning Wunused-parameter 2020-01-28 09:58:41 +01:00
BPanther
34fc6368c4 arm/mips: more zappingmode options 2020-01-28 09:33:08 +01:00
BPanther
b6fe299ee6 fix vuuno4k 2020-01-22 20:32:20 +01:00
DboxOldie
3d6077b3af fix build for no ci stb 2020-01-22 20:32:04 +01:00
BPanther
660c99317c vuplus: relevant pids routing - fix 2020-01-19 13:49:25 +01:00
BPanther
1db0ffb694 vuplus: relevant pids routing - fix 2020-01-19 13:49:16 +01:00
BPanther
0875e2c853 vuplus: relevant pids routing - fix 2020-01-19 13:49:08 +01:00
BPanther
f14212783b vuplus: relevant pids routing 2020-01-19 13:49:05 +01:00
svenhoefer
c14601465a - fix defines
Signed-off-by: Thilo Graf <dbt@novatux.de>
2020-01-19 13:48:51 +01:00
TangoCash
1920c37be5 - libarmbox: try to fix cec 2020-01-19 13:48:34 +01:00
DboxOldie
8658177951 small fix dvbci 2020-01-19 13:48:22 +01:00
BPanther
6eb082c12a vuplus: dvb wait delay for ci response 2020-01-19 13:48:08 +01:00
BPanther
a76f914d9b ci "extra_high" for vuplus 2020-01-19 13:47:46 +01:00
BPanther
32361d734e arm/mips: eplayer3 binary disabled 2020-01-14 12:31:58 +01:00
BPanther
fd8cc781dd dmx.cpp: fix debug 2020-01-14 12:31:56 +01:00
Thilo Graf
52213f9a21 fix pick error, remove wrong package name 2020-01-14 12:31:52 +01:00
svenhoefer
9c422e5713 - Revert first try to fix hdmi-cec
Signed-off-by: Thilo Graf <dbt@novatux.de>
2020-01-14 12:31:48 +01:00
Jacek Jendrzej
84ad5a2019 exteplayer.c:fix heap buffer overflow 2020-01-14 10:31:40 +01:00
Jacek Jendrzej
8ff9d03679 fix compiler warnings 2020-01-09 16:54:07 +01:00
Jacek Jendrzej
5791880e4c libgeneric-pc/clutterfb.cpp: sync keys with glfb.cpp 2020-01-06 13:34:41 +01:00
Thilo Graf
60f6a1f4be lib cleanup and sync for mips vu support 2020-01-05 21:11:50 +01:00
Thilo Graf
ed84d0ac6e libspark: fix pick error 2020-01-05 21:11:50 +01:00
Thilo Graf
92f912e541 libraspi: add missing links to generic-pc 2020-01-05 21:11:50 +01:00
vanhofen
5802a2ed1e - acinclude: resort 2020-01-05 21:11:50 +01:00
BPanther
7f329670fc some more devices for vu 2020-01-05 21:11:50 +01:00
svenhoefer
7a650421bf - libarmbox: align modification of /proc/stb/frontend/fbc/fcc to the proc_put calls above
Signed-off-by: Thilo Graf <dbt@novatux.de>
2020-01-05 21:11:50 +01:00
svenhoefer
fb8bb36cf7 - libarmbox: remove still picture while zapping
Conflicts:
	libarmbox/init.cpp

Signed-off-by: Thilo Graf <dbt@novatux.de>
2020-01-05 21:11:50 +01:00
svenhoefer
15ed156bd3 - vuplus: fix volume 0
Signed-off-by: Thilo Graf <dbt@novatux.de>
2020-01-05 21:11:50 +01:00
max_10
6e45d7affa - hardware_caps: bre2ze4k disable display has statusline 2020-01-05 21:11:50 +01:00
max_10
0f85aa4f60 - libeplayer3: fix __inline is not at beginning of declaration [-Wold-style-declaration] 2020-01-05 21:11:50 +01:00
svenhoefer
69a371a709 - vuplus: allow to control led brightness for zero4k and uno4k
maybe this is also usefull for the other vuplus4k boxes

 Conflicts:
	libarmbox/hardware_caps.c

Signed-off-by: Thilo Graf <dbt@novatux.de>

TODO: 	Maybe this commit makes behavior broken on boxes with line display eg. hd51.
	Observed in relation with simple_display.cpp, see neutrino source.
2020-01-05 20:59:46 +01:00
max_10
f26097e1fc - add h7
Conflicts:
	acinclude.m4
2020-01-05 20:42:27 +01:00
Thilo Graf
5979389a2c libgeneric-pc: fix possible linker error
undefined reference to symbol 'aio_error@@GLIBC_2.2.5'
.../x86_64-linux-gnu/librt.so: error adding symbols: DSO missing ...
2020-01-05 20:41:32 +01:00
Jacek Jendrzej
c4e474a48e libarmbox/video.cpp: image_to_mpeg2 fix memleak 2020-01-05 17:45:32 +01:00
Jacek Jendrzej
db244f0b8a libeplayer3-arm:playback.c reduce log errors 2020-01-03 21:54:48 +01:00
Jacek Jendrzej
c25f68eda1 av_dict_free avio_opts; fix memleak 2020-01-03 20:09:42 +01:00
Jacek Jendrzej
68fa79b83f libeplayer3-arm: malloc player once on neutrino start 2020-01-01 19:02:41 +01:00
Jacek Jendrzej
3b0bad6f54 libeplayer3-arm:playback.c: avoid use after free 2020-01-01 18:58:30 +01:00
Jacek Jendrzej
4d6eef9433 libarmbox/playback_libeplayer3: fix audio track select, broken pointer size 2019-12-29 19:59:39 +01:00
Jacek Jendrzej
f0f1a282bf libarmbox: stop player before free it 2019-12-29 11:48:50 +01:00
Jacek Jendrzej
603fba2500 playback arm: add option to play szSecondFile (audio) 2019-11-03 18:30:13 +01:00
Jacek Jendrzej
639762e1b3 subtitle: fix debug compil 2019-11-03 18:27:06 +01:00
Thilo Graf
2b32057d88 update version to 1.2.0 mpx
zgemma h7, vuduo4k, vuzero4k added
2019-10-27 11:28:15 +01:00
BPanther
643e31d127 fix vuzero4k 2019-10-27 11:28:14 +01:00
svenhoefer
89795e0ac9 - acinclude.m4: sort helpstrings and code (start with generic and end up with armbox and mipsbox)
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-10-27 11:28:12 +01:00
svenhoefer
08fcc53323 - acinclude.m4: add boxmodel generic (not really needed; just for better readability)
Signed-off-by: Thilo Graf <dbt@novatux.de>

Conflicts:
	acinclude.m4
2019-10-27 11:28:11 +01:00
TangoCash
ddfc274773 silence ffmpeg 2019-10-27 11:28:10 +01:00
TangoCash
f88e4e9451 fix segfaults on some HEVC/h265 files 2019-10-27 11:28:09 +01:00
max_10
4024d92c22 - vuduo4k added 2019-10-27 11:28:07 +01:00
max_10
64822e3f16 - vuzero4k added
Conflicts:
	configure.ac
2019-10-27 11:28:05 +01:00
svenhoefer
9821a03061 - fix SNDCTL_DSP_RESET handling for bre2ze4k and h7
Signed-off-by: GetAway <get-away@t-online.de>
2019-10-27 10:40:32 +01:00
GetAway
6e1b833522 supplement to commit f4ef056
- libarm clipplay-retry, thx DboxOldie
2019-10-23 22:43:12 +02:00
Markus Volk
a43f47cfff libstb hal add zgemma h7 stb models
Signed-off-by: Markus Volk <f_l_k@t-online.de>
Signed-off-by: GetAway <get-away@t-online.de>
2019-10-23 22:12:07 +02:00
Jacek Jendrzej
60106b3fb3 libarmbox: remove unnecessary while 2019-08-04 19:50:47 +02:00
Jacek Jendrzej
13e00bae72 fix chapter 2019-07-29 20:16:51 +02:00
Jacek Jendrzej
d4c09e2bb9 disable chapter, need fix 2019-07-29 20:00:23 +02:00
Jacek Jendrzej
011843ef91 libeplayer3-arm: fix chapter 2019-07-29 18:11:02 +02:00
Jacek Jendrzej
6b64c065d2 libeplayer3-arm: fix mem leak uri on open error 2019-07-29 11:05:36 +02:00
Jacek Jendrzej
e27822382d try to fix segfault on open/close 2019-07-22 19:48:51 +02:00
Jacek Jendrzej
42ac0f8229 enable abortRequested for http and isPlaying is 0, some dash urls hangs (ffmpeg timeouut is broken ?) 2019-07-19 18:00:02 +02:00
Jacek Jendrzej
119aefaf82 possible mem leak 2019-07-19 18:00:02 +02:00
Thilo Graf
a3f7195688 clutterfb.cpp: avoid possible memleak 2019-07-16 11:03:50 +02:00
Jacek Jendrzej
bc01e812e6 avoid segfault 2019-07-14 19:06:15 +02:00
Jacek Jendrzej
a22d54a164 avoid segfault 2019-07-14 19:05:11 +02:00
Jacek Jendrzej
d975c90d34 fix segfault on strdup 2019-07-14 19:04:24 +02:00
max_10
070cfa7223 - libgeneric-pc: fix build with --enable-clutter 2019-06-27 15:49:33 +02:00
Thilo Graf
5caaa055bd Revert "libgeneric: add missing header files, required with --enable-clutter"
This reverts commit 7fea151f3e.
2019-06-27 15:49:24 +02:00
Thilo Graf
7fea151f3e libgeneric: add missing header files, required with --enable-clutter 2019-06-25 19:59:46 +02:00
Jacek Jendrzej
809833f99a generic-pc: reduce warnings 2019-06-20 20:48:12 +02:00
Jacek Jendrzej
8992afc489 generic-pc: reduce ffmpeg warnings 2019-06-20 20:39:38 +02:00
GetAway
a7401f47ff flv2mpeg4_ffmpeg.c: fix warning unused parameter 2019-06-18 18:35:04 +02:00
GetAway
731505ddf2 ffmpeg: fix error duplicate ‘const’ declaration specifier 2019-06-18 18:24:25 +02:00
GetAway
c8eda96620 libstb_hal: Suppress implicit-fallthrough warnings from GCC 7 2019-06-14 21:03:10 +02:00
GetAway
9dc3e7b768 surpress sprintf() warning when compiling with newer gcc
and -Werror=format-overflow
2019-06-14 20:16:02 +02:00
max_10
6fc257e3ae - libdvbci: add CA_SET_PID, for kernels > 4.14 2019-05-26 21:53:37 +02:00
max_10
f9ff2988d0 - libdvbci: no define CA_SET_DESCR_DATA, read from linux/dvb/ca.h
Conflicts:
	libdvbci/descrambler.cpp
2019-05-26 21:53:36 +02:00
max_10
c8ef8405b1 - libgeneric-pc: reduce ffmpeg warnings 2019-05-26 21:53:35 +02:00
Jacek Jendrzej
84e2b58fdc generic-pc: avoid segfault 2019-05-11 19:43:39 +02:00
Jacek Jendrzej
f42c7d86af generic-pc: avoid segfault 2019-05-09 18:05:59 +02:00
BPanther
dfb48f114f vusolo4k enable fcc 2019-04-28 20:07:51 +02:00
svenhoefer
a90ec77f11 - fill COPYING file with GPLv2
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-04-28 20:07:49 +02:00
svenhoefer
6454033995 - add missing empty INSTALL file
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-04-28 20:07:48 +02:00
svenhoefer
170da9756e - configure.ac: add foreign switch to AM_INIT_AUTOMAKE macro
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-04-28 20:07:47 +02:00
svenhoefer
9018804c8a - configure.ac: autoupdate
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-04-28 20:07:46 +02:00
svenhoefer
e15b2580fb - Makefile.am: remove non-working pkginclude_HEADERS
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-04-28 20:07:43 +02:00
svenhoefer
302737c891 - configure.ac: remove AC_CONFIG_MACRO_DIR macro
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-04-28 20:07:42 +02:00
svenhoefer
26fc20ef70 - .gitignore: a bit more structure; inspired by https://github.com/github/gitignore
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-04-28 20:07:41 +02:00
svenhoefer
5940755332 - configure.ac: completion of "remove obsolete TUXBOX_APPS_DIRECTORY macro"
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-04-28 20:07:40 +02:00
svenhoefer
5a9c1974c2 - acinclude.m4: remove obsolete TUXBOX_APPS_DIRECTORY macro
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-04-28 20:07:38 +02:00
svenhoefer
351c377966 - acinclude.m4: align to neutrino's acinclude.m4; fix exec_prefix variable in cdk-mode too
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-04-28 20:07:37 +02:00
svenhoefer
1b89f9241f - fix indentation
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-04-28 20:07:36 +02:00
Jacek Jendrzej
973e8c3a7a try to fix unmap error,automatically unmapped don't work ? 2019-04-28 20:07:35 +02:00
Jacek Jendrzej
4c5b13c4a4 fix check mmap error, avoid possible segment fault 2019-04-28 20:07:33 +02:00
Jacek Jendrzej
005bcbdf01 libeplayer3-arm/container/container_ffmpeg.c fix possible segfault 2019-04-10 12:46:09 +02:00
max_10
265eaecd8a - bre2ze4k: fix hardware_caps
Signed-off-by: GetAway <get-away@t-online.de>
2019-03-26 09:42:54 +01:00
Frankenstone
5840f86e31 Not starting record or stream to pc, when watching live-tv via CI module and stream or record needs the module
Signed-off-by: GetAway <get-away@t-online.de>
2019-03-16 14:29:28 +01:00
FlatTV
c06a34faa8 ca_ci.cpp: No decoding using the same SID after switching to a FTA channel 2019-03-14 09:03:43 +01:00
Frankenstone
f4ef056089 - libarm clipplay-retry, thx DboxOldie 2019-03-13 08:42:47 +01:00
BPanther
453f61b8da small fix for vusolo4k 2019-03-13 08:42:37 +01:00
svenhoefer
7c17a9fa12 - libazbox/video.cpp: fix wrong brackets
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-03-13 08:40:42 +01:00
Frankenstone
d44e2b0419 libarm use ffmpeg log 2019-03-05 20:36:16 +01:00
Frankenstone
a618e70a3e armhardware reduce ffmpeg warnings part 2
- thx DbO

 Conflicts:
	libarmbox/video.cpp
2019-03-04 12:59:05 +01:00
Frankenstone
3dec38599a fix possible segfault arm hardware, thx DboxOldie 2019-03-01 22:22:30 +01:00
max_10
23ee0a2ae6 Revert "try to fix slowly close internet radio/music player"
This reverts commit 42dc38f7c9.
2019-03-01 21:39:40 +01:00
Frankenstone
84c333354e armhardware reduce ffmpeg warnings part 1
- thx DbO
2019-03-01 21:35:03 +01:00
Frankenstone
7559f1ab54 fix possible segfault, thx DboxOldie
-arm eplayer get writer segfault
2019-02-27 09:45:20 +01:00
TangoCash
519afb1035 add experimental hisilicon player for hd60 2019-02-27 09:45:20 +01:00
samsamsam
37c27cf695 Unify h263 and mpeg4 formatters 2019-02-27 09:45:20 +01:00
samsamsam
77cac9222f Add mapping of a stream type and bypass mode and try to set alternative one if main fail 2019-02-27 09:45:20 +01:00
max_10
cb7c9874e8 - fix-compiler-warnings 2019-02-27 09:45:20 +01:00
samsamsam
32bc62a65b Attempt to add MJPEG support 2019-02-27 09:45:20 +01:00
samsamsam
a3e9180edd Improve Zgemma H9S playback start with new drivers, deploy version v54 2019-02-27 09:45:20 +01:00
samsamsam
4e11cb9a92 Fix VP9 playback for the Octagon SF4008 2019-02-27 09:45:20 +01:00
samsamsam
c298f20a69 Improve playback of VP9 codec 2019-02-27 09:45:20 +01:00
redblue-pkt
0435571728 fix commit b750bbe3eb
Signed-off-by: Thilo Graf <dbt@novatux.de>

Commit was:
arm: finally fix play next file
adab40123e
2019-02-27 09:45:20 +01:00
max_10
d8b3a2d5b4 libeplayer3-arm: debug issue shortened 2019-02-27 09:45:20 +01:00
max_10
72367605fc mpeg4p2_ffmpeg: fix shadows a global declaration 2019-02-27 09:45:20 +01:00
samsamsam
0500967a2a Improve seeks on playback with multi AV context - when option 2019-02-27 09:45:20 +01:00
samsamsam
6ee43d0121 libavformat option was not set for the second context. 2019-02-27 09:45:20 +01:00
samsamsam
a7e749dc67 Fix compilation of the linuxdvb_fake.c 2019-02-27 09:45:20 +01:00
samsamsam
f58a34e220 Refactoring debug code
Conflicts:
	libeplayer3-arm/container/container_ffmpeg.c
2019-02-27 09:45:20 +01:00
Charles Duco
99844a02dd added webvtt support 2019-02-27 09:45:20 +01:00
redblue-pkt
5f71277215 armbox: eplayer3 add read-count 2019-02-27 09:45:20 +01:00
redblue-pkt
0b92f90ce2 fastforward: move VIDEO_CONTINUE from playback.c to linuxdvb_mipsel.c 2019-02-27 09:45:20 +01:00
redblue-pkt
89a891ddbb LinuxDvbAudioMute replace AUDIO_STOP, AUDIO_PLAY to AUDIO_SET_MUTE 2019-02-27 09:45:20 +01:00
GetAway
06f46400c2 arm: fix black screen in channel swiching
this fixes wrong commit e20d1913
2019-02-26 18:28:43 +01:00
Jacek Jendrzej
f5c1a7c9a3 try fix to call container_ffmpeg_stop on file EOF 2019-02-22 21:32:23 +01:00
Jacek Jendrzej
167c259649 fix memleak , free unused track.aacbuf 2019-02-22 15:23:26 +01:00
Jacek Jendrzej
e51ad20c46 workaround for double malloc if container_ffmpeg_stop is not called after file play to end 2019-02-21 19:46:27 +01:00
Markus Volk
e9c53684e3 fix commit: fix for build with openssl 1.1
1ce6f8c629

Signed-off-by: Markus Volk <f_l_k@t-online.de>
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-02-16 12:37:48 +01:00
Thilo Graf
1ce6f8c629 libdvbci: fix for build with openssl 1.1
error: invalid use of incomplete type 'DH' {aka 'struct dh_st'}
2019-02-15 21:40:15 +01:00
Jacek Jendrzej
97db720210 try to fix unmap error,automatically unmapped don't work ? 2019-01-14 10:44:13 +01:00
Jacek Jendrzej
cf1884f1fc fix check mmap error, avoid possible segment fault 2019-01-13 20:13:55 +01:00
Jacek Jendrzej
4730206966 fix generic build 2019-01-13 12:46:19 +01:00
GetAway
4f15222d9c ShowPicture: return boolean expression 2019-01-12 11:47:33 +01:00
Thilo Graf
0b6120d170 version_hal: simplify methodes
adopt method names similar to cs name convention
2019-01-02 17:24:10 +01:00
Thilo Graf
21561e233a configure: remove config from separat include dir
Not really needed
2019-01-02 17:19:56 +01:00
Thilo Graf
b693517e3c configure: add missing entry
build was broken
2019-01-01 20:38:43 +01:00
redblue-pkt
adab40123e arm: finally fix play next file 2019-01-01 15:51:04 +01:00
redblue-pkt
e20d19138e arm: add black screen in channel swiching 2019-01-01 15:50:59 +01:00
Thilo Graf
f07fcb26cd Makefile.am: fix generic build
wrong defined directory
2019-01-01 15:50:56 +01:00
svenhoefer
5f3fc84a2d - hal-debug: replace some more libtriple shortcuts
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:51 +01:00
Thilo Graf
d72d198740 cs_api.h: fix define of different macro
__CS_API_H__ is used as header guard-, build was broken
2019-01-01 15:50:47 +01:00
svenhoefer
038d2288cc - unify defines in header files
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:45 +01:00
svenhoefer
a7221f4d8c - includes: better error messages
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:41 +01:00
svenhoefer
77d5cafd32 - init: align init/exit function names
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:39 +01:00
svenhoefer
3da91b1463 - rename lt_debug => hal_debug; it's not only libtriple debugging
Signed-off-by: Thilo Graf <dbt@novatux.de>

- debuglevel fixed
2019-01-01 15:50:37 +01:00
svenhoefer
8d4a39566a - libarmbox: fix boxvendor VU+
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:33 +01:00
BPanther
1a5f51f80c vusolo4k tuner fix 2019-01-01 15:50:30 +01:00
svenhoefer
89000ffda3 - rename init_td.h => init.h
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:28 +01:00
svenhoefer
18f895ed6d - re-split ca.h/ca_ci.h for a better transparency
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:24 +01:00
svenhoefer
3921988f22 - remove some more obsolete compatibility headers
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:19 +01:00
svenhoefer
2ad621326b - align includes and Makefiles to directory changes
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:14 +01:00
svenhoefer
335dbdd2ea - move libeplayer3-sh4 code to libeplayer3-sh4 directory; ...
rename library to libeplayer3_sh4.la

Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:12 +01:00
svenhoefer
89e4134873 - Makefile.am: put commented libtest lines together
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:09 +01:00
svenhoefer
635ec1617b - move generic-pc code to libgeneric-pc directory
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:07 +01:00
svenhoefer
aba7114188 - move raspi code to libraspi directory
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:50:02 +01:00
svenhoefer
ec28791f79 - move azbox code to libazbox directory
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:49:59 +01:00
svenhoefer
72a8f6cf73 - fix last commit; generic/playback_lib.h was changed by mistake
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:49:56 +01:00
svenhoefer
871bbcc86f - unify handling of playback header
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:49:51 +01:00
svenhoefer
e478e35f0e - unify handling of ca header
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:49:02 +01:00
svenhoefer
e84e5c8647 - remove obsolete compatibility headers
Signed-off-by: Thilo Graf <dbt@novatux.de>
2019-01-01 15:48:18 +01:00
Thilo Graf
b87250108c version_hal.cpp/h: add methodes to get package data 2019-01-01 15:46:26 +01:00
Thilo Graf
71197a55d9 configure: add additional config header
config.h was not usable with neutrino.
2019-01-01 15:29:47 +01:00
Thilo Graf
90aabf766b .gitignore: ignore some unneeded config and local stuff 2019-01-01 15:29:43 +01:00
GetAway
2d90952e28 libarmbox: introduce has_button_vformat 2018-12-01 10:38:17 +01:00
TangoCash
d92f990091 add support for wwio bre2ze4k 2018-11-23 09:28:15 +01:00
TangoCash
736d4c6edc add first experimental support for ax hd60
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-11-01 20:44:49 +01:00
TangoCash
698585e1cb liabarmbox: hdmi_cec return volume in percent, correct msg length
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-20 14:18:58 +02:00
TangoCash
1a2fd80b53 libeplayer3-arm: fix h265 playback
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-16 08:45:03 +02:00
TangoCash
3057e3aa4d libarmbox: hdmi_cec add option to regulate audio systems volume via CEC, better log readability
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-14 13:51:07 +02:00
TangoCash
53f752a014 libarmbox: hdmi_cec switch debug log to INIT (not used by armbox elsewhere), to debug hdmi_cec separatly from video
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-11 09:50:19 +02:00
TangoCash
7c40bbf4f1 libarmbox: hdmi_cec fix device
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-11 09:34:03 +02:00
TangoCash
08984d1c35 libarmbox: hmdi_cec emit received keys, report power status
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-10 09:14:56 +02:00
TangoCash
b047bcdcf2 libarmbox: hdmi_cec typo
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-10 09:14:56 +02:00
TangoCash
ae74e313ef libarmbox: hdmi_cec fixx segfault on DDT, align log
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-10 09:14:56 +02:00
TangoCash
6427cf09a8 libarmbox: hdmi_cec better readability
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-10 09:14:56 +02:00
TangoCash
97ca22c7fa libarmbox: hdmi_cec add some more output
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-10 09:14:56 +02:00
TangoCash
d58558c82a libarmbox: fix hdmi_cec handling
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-10 09:14:56 +02:00
TangoCash
0621626119 libarmbox: move hdmi_cec to own class, add basic cec-remote support
cec-remote will print received commands in log for now

Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-10 09:14:56 +02:00
Frankenstone
2820170776 arm hardware: fast forward, mute audio when passthrough AC3 / DTS
-thx DboxOldie

Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-10 09:14:56 +02:00
TangoCash
c58e9b9eb7 arm another fix fastforward
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-10-06 20:44:38 +02:00
max_10
9e9d4ca39b Revert "update audio streamtype"
This reverts commit 803aa065fc6ff33f69a5cc9a6e420e7d80c5638c.
2018-10-06 20:33:00 +02:00
max_10
84fe2aa10c Revert "update video streamtype"
This reverts commit d6b32edaa7d0cd1eb035e3404a12dee2359037ea.
2018-10-06 20:32:38 +02:00
redblue-pkt
950f804f3f fix no sound after play video 2018-10-05 13:58:29 +02:00
redblue-pkt
dde77e1b5c add codec info 2018-10-05 13:58:25 +02:00
redblue-pkt
4806fe87b0 update SetColorFormat() 2018-10-05 13:58:22 +02:00
Thilo Graf
2a5d3d23f2 libarmbox/video.cpp: fix possible broken build
possible error:

"error: '0' flag ignored with precision and '%X' gnu_printf format [-Werror=format=]"
2018-10-05 13:58:11 +02:00
redblue-pkt
1e674880f3 update SetControl() 2018-10-04 23:39:48 +02:00
redblue-pkt
a6614a7cdd update video streamtype 2018-10-04 23:39:46 +02:00
redblue-pkt
18ee150d60 update audio streamtype 2018-10-04 23:39:44 +02:00
redblue-pkt
42dc38f7c9 try to fix slowly close internet radio/music player 2018-10-04 23:39:41 +02:00
redblue-pkt
5c733a1ac1 fix mute, sound volume 2018-10-04 23:39:39 +02:00
redblue-pkt
2cc698c3ec fix fastforward 2018-10-04 23:39:37 +02:00
redblue-pkt
e5724161b0 fix segfault in backward 2018-10-04 23:39:33 +02:00
BPanther
df7a030d06 update hwcaps for hl101 (thx sid8796)
Signed-off-by: Thilo Graf <dbt@novatux.de>

I tryed to reduce the mess of commits.
2018-10-04 23:38:43 +02:00
BPanther
ad385ab627 sh4 hwcaps update 2018-10-04 22:50:57 +02:00
BPanther
6cf28c8d10 fix vusolo4k 2018-10-04 22:50:51 +02:00
BPanther
0a6d33c327 fix vusolo4k 2018-10-04 22:50:48 +02:00
BPanther
e962d40349 vusolo4k: more tuner fix 2018-10-04 22:50:46 +02:00
BPanther
3a4cded5d8 vusolo4k: more tuner 2018-10-04 22:50:43 +02:00
Frankenstone
ccc243eafe workaround arm hardware, timshift time in vfd
- thx DBoxOldie
2018-10-04 22:50:35 +02:00
TangoCash
7a796b445b silence ! 2018-10-04 22:50:32 +02:00
TangoCash
d52aa714ce silent output 2018-10-04 22:50:30 +02:00
redblue-pkt
87ffb80f3d fix backward 2018-10-04 22:50:24 +02:00
max_10
ec76737c03 fix segfault subtitles selection - but not yet ready 2018-10-04 22:50:18 +02:00
max_10
cf45b80334 generic-pc: rework glfb (thx seife) 2018-10-04 22:49:59 +02:00
Stefan Seyfried
c8c7f0c45f generic-pc: add alternative clutter based framebuffer
Add a framebuffer implementation based on clutter instead of "raw"
OpenGL. The performance is slightly worse, but it might bring some
platform abstraction and other benefits for the future.
2018-10-04 22:49:56 +02:00
Stefan Seyfried
9a5bc535b4 generic-pc: don't crash in getAudioInfo if no codec is set 2018-10-04 22:49:51 +02:00
svenhoefer
8a87094b11 - generic-pc/audio.cpp: add default-section to c->codec_id switch ...
to avoid compiler warnings
2018-10-04 22:49:48 +02:00
Jacek Jendrzej
1d4329a505 fix audio video rate info 2018-10-04 22:49:43 +02:00
max_10
b7d195ecaa fix mutex revert 2018-10-04 22:49:39 +02:00
max_10
bdf8de2c42 Revert "add mutex and thread abstraction"
This reverts commit 78dd12e2dd.
2018-10-04 22:49:07 +02:00
max_10
b08367d83a Revert "add mutex and thread abstraction to common files"
This reverts commit 626c785081.
2018-10-04 22:49:02 +02:00
max_10
745b3054ba Revert "add changed files"
This reverts commit c37263f594.
2018-10-04 22:48:59 +02:00
max_10
bc7be9dd74 Revert "fix thread namespace"
This reverts commit 3ef2eeb8aa.
2018-10-04 22:48:54 +02:00
max_10
1aece863c1 Revert "move libthread to libstb-hal"
This reverts commit 95ee7f9e98.
2018-10-04 22:48:05 +02:00
max_10
10710b9b53 Revert "change libeplayer3 to own thread class"
This reverts commit 9ed0a0d244.
2018-10-04 22:33:16 +02:00
max_10
89ab7c86dc Revert "changed raspi to own thread class"
This reverts commit 467f6976f7.
2018-10-04 22:33:13 +02:00
max_10
b3d05f59bf Revert "fix missing compiler include"
This reverts commit 047d3158c5.
2018-10-04 22:33:09 +02:00
BPanther
04fd634c0d small fix 2018-10-04 22:32:26 +02:00
max_10
83f8661c7b [libarmbox] libeplayer3-arm code format 2018-10-04 22:29:43 +02:00
max_10
6886c61e10 [libarmbox] libeplayer3-arm code format 2018-10-04 22:29:40 +02:00
max_10
4dc1decaf4 [libarmbox] fix last commit 2018-10-04 22:29:37 +02:00
max_10
f8e5b9a4a0 [libarmbox] add libeplayer3-arm --enable-flv2mpeg4 2018-10-04 22:29:34 +02:00
max_10
9c5221298b [libarmbox] Change Makefile.am 2018-10-04 22:29:27 +02:00
max_10
5402933900 [libarmbox] playback_libeplayer3.cpp code format 2018-10-04 22:29:25 +02:00
TangoCash
477bbc064c add frontpanel xres for sh4 (thx dbo) 2018-10-04 22:27:43 +02:00
BPanther
360661992e vusolo4k: small fix - but not yet ready 2018-10-03 19:23:57 +02:00
Frankenstone
8e37565740 fix CEC TV ON after deepstandby
- init 4 / init 3
2018-10-03 19:23:28 +02:00
Jacek Jendrzej
1219df131d reset seek position at the end of playback 2018-09-01 12:59:15 +02:00
Jacek Jendrzej
eaca615348 fix possible segfault 2018-07-28 14:24:12 +02:00
Jacek Jendrzej
e77090de83 fix framerate 29970 signalisatiom (by bazi98) 2018-05-31 13:55:54 +02:00
Jacek Jendrzej
626ed6a31b fix signalisation bitrate 599940 (by bazi98) 2018-05-30 10:40:58 +02:00
Jacek Jendrzej
511f0a5011 fix getAspectRatio for movieplayer 2018-05-29 18:37:58 +02:00
Jacek Jendrzej
148a6298da fix framerate for movieplayer 2018-05-29 18:06:21 +02:00
Jacek Jendrzej
6739acbdd4 set av input on start 2018-05-29 16:32:47 +02:00
Jacek Jendrzej
1d7e6dc1dc fix CEC TV ON after deepstandby 2018-05-25 17:05:09 +02:00
Jacek Jendrzej
5a2865d01c use enum for setAVInput 2018-05-19 19:21:22 +02:00
Jacek Jendrzej
f182216d94 add av input switch in deep/standby 2018-05-19 18:34:26 +02:00
Jacek Jendrzej
cfbec0b292 use SetCECState in deepstandby 2018-05-18 12:50:12 +02:00
Jacek Jendrzej
8bd666f27e Revert "this break play video ->try to fix set blank video"
This reverts commit c1049db9c6.
2018-05-18 11:45:08 +02:00
Jacek Jendrzej
c1049db9c6 try to fix set blank video -> http://dbox2world.net/thread/12965-hdmi-ausgang-im-standby-richtig-abschalten/ 2018-05-17 18:51:02 +02:00
Thilo Graf
3cf039c72b update to version 1.0.4-mpx 2018-04-27 08:35:49 +02:00
GetAway
eaf3e5c4b0 fix possible segfault
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-04-27 08:16:36 +02:00
GetAway
c7e6effcdf fix HD51 mix-up letterbox<->panscan
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-04-27 08:16:34 +02:00
max_10
110ad775e6 fix-compiler-warnings 2018-04-20 20:21:01 +02:00
samsamsam
f9b108577c Fix typo
Signed-off-by: max_10 <max_10@gmx.de>
2018-04-20 20:20:13 +02:00
samsamsam
55ced53561 Fix typo
Signed-off-by: max_10 <max_10@gmx.de>
2018-04-20 20:19:57 +02:00
samsamsam
0783d816b0 Add buffering for SH4
Signed-off-by: max_10 <max_10@gmx.de>
2018-04-20 20:19:19 +02:00
max_10
b35e8af698 bugfix-last-commits 2018-04-12 02:26:59 +02:00
samsamsam
193a2d305c Fix wrong playback file name
Signed-off-by: max_10 <max_10@gmx.de>
2018-04-12 02:26:56 +02:00
samsamsam
f380103bfc Add possibility to provide moov atom data as separate file.
This will allow playback of MP4 files which are under download and
moov atom is located at the end of file.

Signed-off-by: max_10 <max_10@gmx.de>
2018-04-12 02:25:49 +02:00
Thilo Graf
449438e144 generic-pc/dmx.cpp: fix possible compile error
Unused variable
2018-04-10 22:55:07 +02:00
TangoCash
cc09186911 fix generic compile 2018-04-10 22:35:39 +02:00
max_10
704bcc5a21 libeplayer3-arm: insert original blank lines from exteplayer3.git, for better merge 2018-04-10 22:19:03 +02:00
samsamsam
d00c87b361 Improve STOP command in the buffering mode
Signed-off-by: max_10 <max_10@gmx.de>
2018-04-10 22:18:55 +02:00
samsamsam
923698bbe1 Linux DVB output - workaround for BUG? in the DVB drivers
Signed-off-by: max_10 <max_10@gmx.de>
2018-04-10 22:18:51 +02:00
samsamsam
98195bba11 Replace the AAC Main object type to the AAC LC in the ADTS header - workaround for no audio on some TS'streams
Signed-off-by: max_10 <max_10@gmx.de>
2018-04-10 22:18:47 +02:00
samsamsam
93f61a89f6 Linux DVB output for STBs based on Broadcom - replace active pooling by select (ready to write)
Signed-off-by: max_10 <max_10@gmx.de>
2018-04-10 22:18:38 +02:00
samsamsam
2878ec69bc Add buffering for Linux DVB outputs
Signed-off-by: max_10 <max_10@gmx.de>
2018-04-10 22:18:34 +02:00
samsamsam
b0e666e1cb Do not wait in the FFMPEG thread.
Signed-off-by: max_10 <max_10@gmx.de>
2018-04-10 22:18:28 +02:00
max_10
5ccc49af32 all: clean up pwrmngr header file 2018-03-23 10:06:05 +01:00
max_10
6a3abc86d8 all: clean up cDemux headers 2018-03-23 10:05:55 +01:00
max_10
f4ad480fc0 armbox: fix video policy again
Conflicts:
	libarmbox/video.cpp
2018-03-23 10:05:26 +01:00
Thilo Graf
1d210b8de7 libeplayer3-arm/container/container_ffmpeg.c: add missing code parts
fix some pick errors
2018-03-22 17:51:00 +01:00
Thilo Graf
19a166bf93 libeplayer3-arm/playback/playback.c: add missing parts for backward play 2018-03-22 17:50:53 +01:00
max_10
ad45a46137 container_ffmpeg: fix Write from incompatible pointer type 2018-03-22 17:50:47 +01:00
samsamsam
c150fe7bd6 Set discard flag to all not active streams, do not process packets from discarded streams
Conflicts:
	libeplayer3-arm/container/container_ffmpeg.c
2018-03-22 17:50:35 +01:00
Jacek Jendrzej
8aa8152d09 fix commit 06f9a1b694 2018-03-22 13:38:29 +01:00
Thilo Graf
06f9a1b694 libarmbox/video.cpp: fix possible compile error
error: unused variable 'r' [-Werror=unused-variable]
2018-03-14 10:02:14 +01:00
samsamsam
c5920200b6 h264 writer - Revert not intended test change 2018-03-13 22:10:28 +01:00
samsamsam
8267a8c76d h264 writer - do not inject prive codec data if the Sequence Parameter Set (SPS) and the Picture Parameter Set (PPS) are available in the bitstreamThis should fix playback of stream http://www.djing.com/tv/live.m3u8 2018-03-13 22:10:25 +01:00
svenhoefer
828b4b439a - introduce caps.has_button_timer
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-03-13 22:10:02 +01:00
BPanther
8095d83353 missing brightness added for ufs922, hdbox, octagon1008, mini2, av7500 2018-03-13 22:06:06 +01:00
max_10
cb275626b1 libeplayer3-arm: cleanup types, use Context_t in commands 2018-03-13 22:05:50 +01:00
max_10
71905680a6 libeplayer3-arm: reduce compiler warnings 2018-03-13 22:00:16 +01:00
Jacek Jendrzej
0285b4e898 add screenshot for hd51 2018-02-26 18:10:20 +01:00
Jacek Jendrzej
f43dc68b5c supplement to b232a8f225, fix segfault with only audio stream 2018-02-11 12:01:19 +01:00
Jacek Jendrzej
e570611a8d remove isContainerRunning, this break next file play aufter eof stop 2018-02-10 20:41:24 +01:00
Jacek Jendrzej
b232a8f225 fix OUTPUT_PLAY error handling 2018-02-10 20:34:01 +01:00
max_10
e5d24ce4ed libeplayer3-arm: reduce compiler warnings 2018-02-09 15:15:39 +01:00
Frankenstone
0bd3f48ff2 arm different tuner authorization (thx DboxOldie) 2018-02-02 18:17:24 +01:00
Thilo Graf
ac95d67e89 update to version 1.0.3-mpx 2018-01-21 15:25:59 +01:00
Thilo Graf
9395b18f89 libarmbox/video.cpp: add missing lines in setBlank()
Fix lost lines in pick 'add armbox'
2018-01-21 14:37:33 +01:00
Thilo Graf
a8c886d166 libarmbox/hardware_caps.c: add missing init for caps.display_can_deepstandby 2018-01-21 14:37:31 +01:00
Thilo Graf
4ecbe7733b libarmbox/playback_gst.cpp: minor format changes 2018-01-21 14:37:29 +01:00
Thilo Graf
0ad071c97b libarmbox/playback_gst.cpp: small format changes 2018-01-21 14:37:26 +01:00
Jacek Jendrzej
a28ebe6eae Revert "return false in decoder have no time"
This reverts commit 6f006f1ce9.
2018-01-21 01:03:06 +01:00
Jacek Jendrzej
0e1d7fe1b5 return false in decoder have no time 2018-01-21 01:03:05 +01:00
Jacek Jendrzej
c0963b38f0 fix null list 2018-01-21 01:03:03 +01:00
Jacek Jendrzej
e4d7f02317 fix get play position 2018-01-21 01:03:02 +01:00
Frankenstone
ee18fd5c8a libeplayer3-arm: fix fast forward (thx DboxOldie) 2018-01-21 01:03:01 +01:00
max_10
bfb3de420f Revert "libeplayer3: switch off the teletext sub"
This reverts commit 96bd1c5c9f631ceb272dd4afb4667e8a976c8620.
2018-01-21 01:02:58 +01:00
max_10
8fe7fd7a3c libeplayer3-arm: Code formatting 2018-01-21 01:02:57 +01:00
max_10
5ccdc663b2 libeplayer3-arm: eliminate some warnings 2018-01-21 01:02:46 +01:00
max_10
c5dc767b64 adding SLOWMOTION, FASTBACKWARD and FASTFORWARD are not working properly yet. 2018-01-21 01:02:44 +01:00
TangoCash
0290cefdee fix last commit 2018-01-21 01:02:42 +01:00
TangoCash
136306c6d5 generic gestreamer align to armbox 2018-01-21 01:02:39 +01:00
max_10
65a67f7919 test 2018-01-21 01:02:38 +01:00
max_10
233e756d04 Revert "Revert "libeplayer3: switch off the teletext sub""
This reverts commit a2fc1d51ee.
2018-01-21 01:02:37 +01:00
Jacek Jendrzej
d275525164 Revert "return false in decoder have no time"
This reverts commit 6f006f1ce9.
2018-01-21 01:02:35 +01:00
Jacek Jendrzej
5f230f4d38 return false in decoder have no time 2018-01-21 01:02:34 +01:00
max_10
f41378c492 libarmbox: fix resolution icon in infoviewer 2018-01-21 01:02:32 +01:00
max_10
8f242002a9 armbox: Cosmetics replace spaces with tabs and delete unnecessary tabs 2018-01-21 01:02:31 +01:00
max_10
15b4162b58 armbox eplayer: fix playing files with subtitles
Signed-off-by: Thilo Graf <dbt@novatux.de>

Conflicts:
	libeplayer3-arm/manager/subtitle.c

additional format fixes, solved conflicts and clean up
2018-01-20 22:55:34 +01:00
max_10
5930dca63f libeplayer3-arm: audio.c delete newline 2018-01-20 22:42:18 +01:00
max_10
4e1855eb75 generic-pc: switch to ffmpeg 3.0 API 2018-01-20 22:39:07 +01:00
max_10
fbad9e1bc4 libarmbox/video: Workaround Channel Change No Black Picture when Show Picture was active. 2018-01-20 22:38:32 +01:00
max_10
f793f03267 libeplayer3-arm: fixes segfault on internet streams (thx DboxOldie) 2018-01-20 22:36:06 +01:00
Frankenstone
fc5c510334 libeplayer3-arm: fix fast forward (thx DboxOldie)
Conflicts:
	libeplayer3-arm/playback/playback.c

Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-01-20 22:34:41 +01:00
TangoCash
3e166e6123 armbox eplayer: fix init jump 2018-01-11 19:51:05 +01:00
max_10
c8a4716085 fix ci arm auth (thx DboxOldie) 2018-01-11 19:50:39 +01:00
svenhoefer
32a693a51b - fix build for generic-pc
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-01-11 19:09:37 +01:00
max_10
1ac7e9202c libeplayer3-arm: update Makefile.am 2018-01-11 13:13:27 +01:00
max_10
32f64c474d libeplayer3-arm: eliminate some warnings 2018-01-11 13:03:18 +01:00
max_10
f72e8edc2e libeplayer3-arm: Code formatting 2018-01-11 13:02:22 +01:00
Frankenstone
0cdc859110 fix ci arm hardware (thx DboxOldie) 2018-01-07 19:30:17 +01:00
max_10
e6c29f2545 armbox eplayer: remove writeReverseData (unused) 2018-01-07 19:30:15 +01:00
Jacek Jendrzej
d2bb71dcab remove double AV_CODEC_ID_EAC3 2018-01-03 19:33:40 +01:00
max_10
db374e2225 armbox eplayer: noprobe for ts (thx DboxOldie) 2018-01-03 16:55:50 +01:00
max_10
6ae2a21f9c armbox eplayer: increase wait time (thx DboxOldie) 2018-01-03 16:55:44 +01:00
max_10
b5744e2728 armbox eplayer: eplayer3 Binary adaptation to the changed manager list (thx DboxOldie) 2018-01-03 16:55:37 +01:00
TangoCash
3b25b464c3 armbox eplayer: fix playing files with subtitles 2018-01-03 16:55:26 +01:00
svenhoefer
c88157d559 - add some missing members for ARM_HARDWARE; mostly dummy functions
Signed-off-by: Thilo Graf <dbt@novatux.de>
2018-01-02 14:01:01 +01:00
max_10
96bb5eb255 libeplayer3-arm: Code formatting 2017-12-28 19:53:18 +01:00
max_10
9b48c84176 libarmbox: Code formatting playback_libeplayer3 2017-12-28 19:53:05 +01:00
max_10
dfafcfa01c armbox eplayer: add eplayer3 bin 2017-12-28 19:52:48 +01:00
max_10
ac5aacd704 Code formatting 2017-12-28 19:52:39 +01:00
TangoCash
3d8987513d eplayer armbox: fix webtv (thx dbo) 2017-12-28 19:52:12 +01:00
Thilo Graf
ea00f01dcc update version 1.0.2-mpx
eplayer beta
2017-12-21 10:54:07 +01:00
TangoCash
ef4260b6b2 armbox eplayer: reactivate audio, subtitle and chapters 2017-12-21 10:43:24 +01:00
TangoCash
3d6689cfca armbox eplayer: add chapter.c 2017-12-21 10:43:19 +01:00
TangoCash
2a7f1bb1fa armbox eplayer: add chapters 2017-12-21 10:43:13 +01:00
TangoCash
f5c1ff725f armbox eplayer: align to last commits 2017-12-21 10:43:06 +01:00
TangoCash
c15484e01a armbox eplayer: use other tracklist 2017-12-21 10:42:54 +01:00
TangoCash
e5a50e7126 armbox eplayer: add metadata 2017-12-21 10:42:48 +01:00
TangoCash
6bc9d6a949 armbox eplayer: small fix TTX 2017-12-21 10:42:37 +01:00
max_10
3ca9c451a4 libeplayer3-arm: fix playback (thx DboxOldie) 2017-12-21 10:42:12 +01:00
max_10
011f009ece fix video policy 2017-12-21 10:41:26 +01:00
TangoCash
f9b1b8aa58 fix close files 2017-12-21 10:41:15 +01:00
svenhoefer
5d1406b93c - Makefile: disable libstb_hal_test stuff; this completes 188f10dd86
Signed-off-by: Thilo Graf <dbt@novatux.de>
2017-12-21 10:39:31 +01:00
TangoCash
09aa5e9ac5 generic gestreamer align to armbox 2017-12-21 10:38:34 +01:00
TangoCash
fea27b6160 gstreamer: increase seek accuracy 2017-12-21 10:36:54 +01:00
svenhoefer
228b58137c - generic-pc/audio: fix segfault in getAudioInfo() function
Signed-off-by: Thilo Graf <dbt@novatux.de>
2017-12-18 19:49:41 +01:00
TangoCash
c2a574aa4b fix compile 2017-12-18 19:47:21 +01:00
max_10
b75f8393c2 add libeplayer3-arm test 2017-12-18 19:47:06 +01:00
max_10
f28d013972 acinclude: some more minor format changes 2017-12-18 19:46:46 +01:00
max_10
7f081bee8c libeplayer3: code format 2017-12-18 19:46:34 +01:00
max_10
c0ef130e8e armbox: fix write value hex
Signed-off-by: Thilo Graf <dbt@novatux.de>

ax needs hex
2017-12-04 10:39:12 +01:00
Jacek Jendrzej
f5e07c5704 fix max apids 2017-11-23 09:29:40 +01:00
Jacek Jendrzej
188f10dd86 disable test 2017-11-23 08:56:38 +01:00
Jacek Jendrzej
3ac8fa2080 write m2v direct to device 2017-11-22 10:10:01 +01:00
TangoCash
8a3ba60e14 align gststreamer findallpids to eplayers logic 2017-11-21 09:52:58 +01:00
TangoCash
6af94cc719 porting av converter to sh4 2017-11-21 09:52:58 +01:00
Jacek Jendrzej
03446f4122 fix possible memleak 2017-11-17 16:20:42 +01:00
Jacek Jendrzej
6649d6250a convert pix fmt 2017-11-17 15:29:20 +01:00
Jacek Jendrzej
545fb415b2 fix logic and possible memleak 2017-11-17 06:34:13 +01:00
Jacek Jendrzej
e0effa50e2 fix last commit 2017-11-16 19:10:40 +01:00
Jacek Jendrzej
702b8d6085 check alloc AVFormatContext 2017-11-16 19:09:16 +01:00
Jacek Jendrzej
193fcf4ea1 fix close fp 2017-11-16 18:58:13 +01:00
Jacek Jendrzej
e86301004a convert jpg to m2v with libavcodec, need --enable-demuxer=image2 2017-11-16 18:51:01 +01:00
TangoCash
d016c7315e cleanup 2017-11-16 15:06:43 +01:00
TangoCash
afa6b14f46 cleanup 2017-11-16 15:06:43 +01:00
TangoCash
cde1e655f3 fix 0648 caid issue (dbo!!!) 2017-11-14 18:04:54 +01:00
Jacek Jendrzej
32a72a7357 sync with oher repo 2017-11-14 15:24:03 +01:00
Jacek Jendrzej
0b9575ff7f fix merge error 2017-11-14 15:13:13 +01:00
Jacek Jendrzej
5662d18602 fix last commit 2017-11-14 12:55:11 +01:00
Jacek Jendrzej
ceb1620bcd remove double keys 2017-11-14 11:33:38 +01:00
vanhofen
70cdad0db1 - add display_has_statusline member
Signed-off-by: Jacek Jendrzej <satbaby@kawaii.com>
2017-11-14 09:43:22 +01:00
vanhofen
6c0d55da96 - generic-pc: add our proven keymap to glfb 2017-11-14 09:41:02 +01:00
Jacek Jendrzej
64828627ac try to fix possible race condition 2017-11-13 09:44:47 +01:00
Jacek Jendrzej
fc5d505995 init mpegts 2017-11-12 08:58:18 +01:00
Jacek Jendrzej
dcce5347b1 Revert "return false in decoder have no time"
This reverts commit 6f006f1ce9.
2017-11-12 08:57:41 +01:00
Jacek Jendrzej
b67c8b39b5 fix last commit, broken check logic 2017-11-11 17:08:51 +01:00
Jacek Jendrzej
50904a1825 check if tag is gst list 2017-11-11 16:55:02 +01:00
Jacek Jendrzej
6f006f1ce9 return false in decoder have no time 2017-11-11 16:52:38 +01:00
Jacek Jendrzej
2864b81fe2 try to fix freeze with subtitle file , use gst_element_get_state only if need 2017-11-11 16:29:28 +01:00
TangoCash
bc4a9b3329 fix missing close fd (thx dbo) 2017-11-11 15:23:05 +01:00
Jacek Jendrzej
2bbb8a9044 move gchar * sourceName = gst_object_get_name(source); 2017-11-10 16:17:40 +01:00
Jacek Jendrzej
be5bf56314 check m_stream_tags if not NULL 2017-11-10 12:50:15 +01:00
Jacek Jendrzej
d9b7971e30 add check if children not NULL 2017-11-10 12:37:46 +01:00
Jacek Jendrzej
b75667176b fix memleak, init and compil 2017-11-10 12:25:58 +01:00
TangoCash
1e8e9bcc4d gstreamer playback: fix possible race condition 2017-11-10 12:20:28 +01:00
TangoCash
54341f0c48 gstreamer playback: fix possible segfault 2017-11-10 12:20:28 +01:00
TangoCash
31a73a2bd5 gstreamer playback: remove subtitles until fully supported 2017-11-08 10:18:15 +01:00
TangoCash
a811b733d4 gstreamer playback: fix possible segfaults 2017-11-08 10:18:15 +01:00
TangoCash
f170c38f10 CI: fix some caid issues (thx dboxoldie) 2017-11-08 10:18:15 +01:00
357 changed files with 43209 additions and 12933 deletions

63
.gitignore vendored
View File

@@ -1,21 +1,68 @@
/aclocal.m4
/autom4te.cache/
### http://www.gnu.org/software/automake
Makefile
Makefile.in
### http://www.gnu.org/software/autoconf
autom4te.cache
/autoscan.log
/autoscan-*.log
/aclocal.m4
/compile
/config.guess
/config.h.in
/config.log
/config.status
/config.sub
/configure
/configure.scan
/depcomp
/install-sh
/ltmain.sh
/m4/
/missing
*.*~
*.a
*.la
*.lai
/stamp-h*
### https://www.gnu.org/software/libtool/
/libtool
/ltmain.sh
### http://www.gnu.org/software/m4/
m4/libtool.m4
m4/ltoptions.m4
m4/ltsugar.m4
m4/ltversion.m4
m4/lt~obsolete.m4
### compiled objects and libs
.libs
*.lo
*.o
*.so
*.lai
*.la
*.a
### dependency files
.deps
*.Plo
*.Po
### diff and patch files
*.patch
*.diff
*.orig
*.rej
### system generated stuff
# dolphin
.directory
# kate
*-swp
.*.swp
### generally excluded files
*~
*.pc
git-*
go_*
### header files that fall out of the build
libstb-hal-config.h

339
COPYING
View File

@@ -0,0 +1,339 @@
GNU GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1989, 1991 Free Software Foundation, Inc.,
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. This
General Public License applies to most of the Free Software
Foundation's software and to any other program whose authors commit to
using it. (Some other Free Software Foundation software is covered by
the GNU Lesser General Public License instead.) You can apply it to
your programs, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must show them these terms so they know their
rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that redistributors of a free
program will individually obtain patent licenses, in effect making the
program proprietary. To prevent this, we have made it clear that any
patent must be licensed for everyone's free use or not licensed at all.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License applies to any program or other work which contains
a notice placed by the copyright holder saying it may be distributed
under the terms of this General Public License. The "Program", below,
refers to any such program or work, and a "work based on the Program"
means either the Program or any derivative work under copyright law:
that is to say, a work containing the Program or a portion of it,
either verbatim or with modifications and/or translated into another
language. (Hereinafter, translation is included without limitation in
the term "modification".) Each licensee is addressed as "you".
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running the Program is not restricted, and the output from the Program
is covered only if its contents constitute a work based on the
Program (independent of having been made by running the Program).
Whether that is true depends on what the Program does.
1. You may copy and distribute verbatim copies of the Program's
source code as you receive it, in any medium, provided that you
conspicuously and appropriately publish on each copy an appropriate
copyright notice and disclaimer of warranty; keep intact all the
notices that refer to this License and to the absence of any warranty;
and give any other recipients of the Program a copy of this License
along with the Program.
You may charge a fee for the physical act of transferring a copy, and
you may at your option offer warranty protection in exchange for a fee.
2. You may modify your copy or copies of the Program or any portion
of it, thus forming a work based on the Program, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) You must cause the modified files to carry prominent notices
stating that you changed the files and the date of any change.
b) You must cause any work that you distribute or publish, that in
whole or in part contains or is derived from the Program or any
part thereof, to be licensed as a whole at no charge to all third
parties under the terms of this License.
c) If the modified program normally reads commands interactively
when run, you must cause it, when started running for such
interactive use in the most ordinary way, to print or display an
announcement including an appropriate copyright notice and a
notice that there is no warranty (or else, saying that you provide
a warranty) and that users may redistribute the program under
these conditions, and telling the user how to view a copy of this
License. (Exception: if the Program itself is interactive but
does not normally print such an announcement, your work based on
the Program is not required to print an announcement.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Program,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Program, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Program.
In addition, mere aggregation of another work not based on the Program
with the Program (or with a work based on the Program) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may copy and distribute the Program (or a work based on it,
under Section 2) in object code or executable form under the terms of
Sections 1 and 2 above provided that you also do one of the following:
a) Accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of Sections
1 and 2 above on a medium customarily used for software interchange; or,
b) Accompany it with a written offer, valid for at least three
years, to give any third party, for a charge no more than your
cost of physically performing source distribution, a complete
machine-readable copy of the corresponding source code, to be
distributed under the terms of Sections 1 and 2 above on a medium
customarily used for software interchange; or,
c) Accompany it with the information you received as to the offer
to distribute corresponding source code. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form with such
an offer, in accord with Subsection b above.)
The source code for a work means the preferred form of the work for
making modifications to it. For an executable work, complete source
code means all the source code for all modules it contains, plus any
associated interface definition files, plus the scripts used to
control compilation and installation of the executable. However, as a
special exception, the source code distributed need not include
anything that is normally distributed (in either source or binary
form) with the major components (compiler, kernel, and so on) of the
operating system on which the executable runs, unless that component
itself accompanies the executable.
If distribution of executable or object code is made by offering
access to copy from a designated place, then offering equivalent
access to copy the source code from the same place counts as
distribution of the source code, even though third parties are not
compelled to copy the source along with the object code.
4. You may not copy, modify, sublicense, or distribute the Program
except as expressly provided under this License. Any attempt
otherwise to copy, modify, sublicense or distribute the Program is
void, and will automatically terminate your rights under this License.
However, parties who have received copies, or rights, from you under
this License will not have their licenses terminated so long as such
parties remain in full compliance.
5. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Program or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Program (or any work based on the
Program), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Program or works based on it.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the
original licensor to copy, distribute or modify the Program subject to
these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
7. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Program at all. For example, if a patent
license would not permit royalty-free redistribution of the Program by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Program.
If any portion of this section is held invalid or unenforceable under
any particular circumstance, the balance of the section is intended to
apply and the section as a whole is intended to apply in other
circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system, which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
8. If the distribution and/or use of the Program is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Program under this License
may add an explicit geographical distribution limitation excluding
those countries, so that distribution is permitted only in or among
countries not thus excluded. In such case, this License incorporates
the limitation as if written in the body of this License.
9. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of this License which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
this License, you may choose any version ever published by the Free Software
Foundation.
10. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to the public, the best way to achieve this is to make it
free software which everyone can redistribute and change under these terms.
To do so, attach the following notices to the program. It is safest
to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least
the "copyright" line and a pointer to where the full notice is found.
<one line to give the program's name and a brief idea of what it does.>
Copyright (C) <year> <name of author>
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.
You should have received a copy of the GNU General Public License along
with this program; if not, write to the Free Software Foundation, Inc.,
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
Also add information on how to contact you by electronic and paper mail.
If the program is interactive, make it output a short notice like this
when it starts in an interactive mode:
Gnomovision version 69, Copyright (C) year name of author
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the appropriate
parts of the General Public License. Of course, the commands you use may
be called something other than `show w' and `show c'; they could even be
mouse-clicks or menu items--whatever suits your program.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the program, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
`Gnomovision' (which makes passes at compilers) written by James Hacker.
<signature of Ty Coon>, 1 April 1989
Ty Coon, President of Vice
This General Public License does not permit incorporating your program into
proprietary programs. If your program is a subroutine library, you may
consider it more useful to permit linking proprietary applications with the
library. If this is what you want to do, use the GNU Lesser General
Public License instead of this License.

467
ChangeLog
View File

@@ -1,3 +1,470 @@
2018-01-12 GetAway1 <get-away@t-online.de>
ShowPicture: return boolean expression
2018-04-27 Thilo Graf <dbt@novatux.de>
update to version 1.0.4-mpx
2018-04-27 GetAway <get-away@t-online.de>
fix possible segfault
fix HD51 mix-up letterbox<->panscan
2018-04-20 max_10 <max_10@gmx.de>
fix-compiler-warnings
2018-04-20 samsamsam <samsamsam@o2.pl>
Fix typo
Fix typo
Add buffering for SH4
2018-04-12 max_10 <max_10@gmx.de>
bugfix-last-commits
2018-04-12 samsamsam <samsamsam@o2.pl>
Fix wrong playback file name
Add possibility to provide moov atom data as separate file.
This will allow playback of MP4 files which are under download and
moov atom is located at the end of file.
2018-04-10 Thilo Graf <dbt@novatux.de>
generic-pc/dmx.cpp: fix possible compile error
Unused variable
2018-04-10 TangoCash <eric@loxat.de>
fix generic compile
2018-04-10 max_10 <max_10@gmx.de>
libeplayer3-arm: insert original blank lines from exteplayer3.git, for better merge
2018-04-10 samsamsam <samsamsam@o2.pl>
Improve STOP command in the buffering mode
Linux DVB output - workaround for BUG? in the DVB drivers
Replace the AAC Main object type to the AAC LC in the ADTS header - workaround for no audio on some TS'streams
Linux DVB output for STBs based on Broadcom - replace active pooling by select (ready to write)
Add buffering for Linux DVB outputs
Do not wait in the FFMPEG thread.
2018-03-23 max_10 <max_10@gmx.de>
all: clean up pwrmngr header file
all: clean up cDemux headers
armbox: fix video policy again
Conflicts:
libarmbox/video.cpp
2018-03-22 Thilo Graf <dbt@novatux.de>
libeplayer3-arm/container/container_ffmpeg.c: add missing code parts
fix some pick errors
libeplayer3-arm/playback/playback.c: add missing parts for backward play
2018-03-22 max_10 <max_10@gmx.de>
container_ffmpeg: fix Write from incompatible pointer type
2018-03-22 samsamsam <samsamsam@o2.pl>
Set discard flag to all not active streams, do not process packets from discarded streams
Conflicts:
libeplayer3-arm/container/container_ffmpeg.c
2018-03-22 Jacek Jendrzej <satbaby@kawaii.com>
fix commit 06f9a1b694c1806a20d18b85b9affde146f0c9bb
2018-03-14 Thilo Graf <dbt@novatux.de>
libarmbox/video.cpp: fix possible compile error
error: unused variable 'r' [-Werror=unused-variable]
2018-03-13 samsamsam <samsamsam@o2.pl>
h264 writer - Revert not intended test change
h264 writer - do not inject prive codec data if the Sequence Parameter Set (SPS) and the Picture Parameter Set (PPS) are available in the bitstreamThis should fix playback of stream http://www.djing.com/tv/live.m3u8
2018-03-13 svenhoefer <svenhoefer@svenhoefer.com>
- introduce caps.has_button_timer
2018-03-13 BPanther <bpanther_ts@hotmail.com>
missing brightness added for ufs922, hdbox, octagon1008, mini2, av7500
2018-03-13 max_10 <max_10@gmx.de>
libeplayer3-arm: cleanup types, use Context_t in commands
libeplayer3-arm: reduce compiler warnings
2018-02-26 Jacek Jendrzej <satbaby@kawaii.com>
add screenshot for hd51
2018-02-11 Jacek Jendrzej <satbaby@kawaii.com>
supplement to b232a8f225056a80b4d732d4a7db3d01a050f288, fix segfault with only audio stream
2018-02-10 Jacek Jendrzej <satbaby@kawaii.com>
remove isContainerRunning, this break next file play aufter eof stop
fix OUTPUT_PLAY error handling
2018-02-09 max_10 <max_10@gmx.de>
libeplayer3-arm: reduce compiler warnings
2018-02-02 Frankenstone <dampf_acc@yahoo.com>
arm different tuner authorization (thx DboxOldie)
2018-01-21 Thilo Graf <dbt@novatux.de>
update to version 1.0.3-mpx
libarmbox/video.cpp: add missing lines in setBlank()
Fix lost lines in pick 'add armbox'
libarmbox/hardware_caps.c: add missing init for caps.display_can_deepstandby
libarmbox/playback_gst.cpp: minor format changes
libarmbox/playback_gst.cpp: small format changes
2018-01-21 Jacek Jendrzej <satbaby@kawaii.com>
Revert "return false in decoder have no time"
This reverts commit 6f006f1ce9026cccddfe87a88fb3ebaa1f6a9e98.
return false in decoder have no time
fix null list
fix get play position
2018-01-21 Frankenstone <dampf_acc@yahoo.com>
libeplayer3-arm: fix fast forward (thx DboxOldie)
2018-01-21 max_10 <max_10@gmx.de>
Revert "libeplayer3: switch off the teletext sub"
This reverts commit 96bd1c5c9f631ceb272dd4afb4667e8a976c8620.
libeplayer3-arm: Code formatting
libeplayer3-arm: eliminate some warnings
adding SLOWMOTION, FASTBACKWARD and FASTFORWARD are not working properly yet.
2018-01-21 TangoCash <eric@loxat.de>
fix last commit
generic gestreamer align to armbox
2018-01-21 max_10 <max_10@gmx.de>
test
Revert "Revert "libeplayer3: switch off the teletext sub""
This reverts commit a2fc1d51ee2bd5d66263aecdbf2936cf26e91f17.
2018-01-21 Jacek Jendrzej <satbaby@kawaii.com>
Revert "return false in decoder have no time"
This reverts commit 6f006f1ce9026cccddfe87a88fb3ebaa1f6a9e98.
return false in decoder have no time
2018-01-21 max_10 <max_10@gmx.de>
libarmbox: fix resolution icon in infoviewer
armbox: Cosmetics replace spaces with tabs and delete unnecessary tabs
2018-01-20 max_10 <max_10@gmx.de>
armbox eplayer: fix playing files with subtitles
Conflicts:
libeplayer3-arm/manager/subtitle.c
additional format fixes, solved conflicts and clean up
2018-01-20 max_10 <max_10@gmx.de>
libeplayer3-arm: audio.c delete newline
generic-pc: switch to ffmpeg 3.0 API
libarmbox/video: Workaround Channel Change No Black Picture when Show Picture was active.
libeplayer3-arm: fixes segfault on internet streams (thx DboxOldie)
2018-01-20 Frankenstone <dampf_acc@yahoo.com>
libeplayer3-arm: fix fast forward (thx DboxOldie)
Conflicts:
libeplayer3-arm/playback/playback.c
2018-01-11 TangoCash <eric@loxat.de>
armbox eplayer: fix init jump
2018-01-11 max_10 <max_10@gmx.de>
fix ci arm auth (thx DboxOldie)
2018-01-11 svenhoefer <svenhoefer@svenhoefer.com>
- fix build for generic-pc
2018-01-11 max_10 <max_10@gmx.de>
libeplayer3-arm: update Makefile.am
libeplayer3-arm: eliminate some warnings
libeplayer3-arm: Code formatting
2018-01-07 Frankenstone <dampf_acc@yahoo.com>
fix ci arm hardware (thx DboxOldie)
2018-01-07 max_10 <max_10@gmx.de>
armbox eplayer: remove writeReverseData (unused)
2018-01-03 Jacek Jendrzej <satbaby@kawaii.com>
remove double AV_CODEC_ID_EAC3
2018-01-03 max_10 <max_10@gmx.de>
armbox eplayer: noprobe for ts (thx DboxOldie)
armbox eplayer: increase wait time (thx DboxOldie)
armbox eplayer: eplayer3 Binary adaptation to the changed manager list (thx DboxOldie)
2018-01-03 TangoCash <eric@loxat.de>
armbox eplayer: fix playing files with subtitles
2018-01-02 svenhoefer <svenhoefer@svenhoefer.com>
- add some missing members for ARM_HARDWARE; mostly dummy functions
2017-12-28 max_10 <max_10@gmx.de>
libeplayer3-arm: Code formatting
libarmbox: Code formatting playback_libeplayer3
armbox eplayer: add eplayer3 bin
Code formatting
2017-12-28 TangoCash <eric@loxat.de>
eplayer armbox: fix webtv (thx dbo)
2017-12-21 Thilo Graf <dbt@novatux.de>
update version 1.0.2-mpx
eplayer beta
2017-12-21 TangoCash <eric@loxat.de>
armbox eplayer: reactivate audio, subtitle and chapters
armbox eplayer: add chapter.c
armbox eplayer: add chapters
armbox eplayer: align to last commits
armbox eplayer: use other tracklist
armbox eplayer: add metadata
armbox eplayer: small fix TTX
2017-12-21 max_10 <max_10@gmx.de>
libeplayer3-arm: fix playback (thx DboxOldie)
fix video policy
2017-12-21 TangoCash <eric@loxat.de>
fix close files
2017-12-21 svenhoefer <svenhoefer@svenhoefer.com>
- Makefile: disable libstb_hal_test stuff; this completes 188f10dd8644c30f64b04c99447c165193fb9790
2017-12-21 TangoCash <eric@loxat.de>
generic gestreamer align to armbox
gstreamer: increase seek accuracy
2017-12-18 svenhoefer <svenhoefer@svenhoefer.com>
- generic-pc/audio: fix segfault in getAudioInfo() function
2017-12-18 TangoCash <eric@loxat.de>
fix compile
2017-12-18 max_10 <max_10@gmx.de>
add libeplayer3-arm test
acinclude: some more minor format changes
libeplayer3: code format
2017-12-04 max_10 <max_10@gmx.de>
armbox: fix write value hex
ax needs hex
2017-11-23 Jacek Jendrzej <satbaby@kawaii.com>
fix max apids
disable test
2017-11-22 Jacek Jendrzej <satbaby@kawaii.com>
write m2v direct to device
2017-11-21 TangoCash <eric@loxat.de>
align gststreamer findallpids to eplayers logic
porting av converter to sh4
2017-11-17 Jacek Jendrzej <satbaby@kawaii.com>
fix possible memleak
convert pix fmt
fix logic and possible memleak
2017-11-16 Jacek Jendrzej <satbaby@kawaii.com>
fix last commit
check alloc AVFormatContext
fix close fp
convert jpg to m2v with libavcodec, need --enable-demuxer=image2
2017-11-16 TangoCash <eric@loxat.de>
cleanup
cleanup
2017-11-14 TangoCash <eric@loxat.de>
fix 0648 caid issue (dbo!!!)
2017-11-14 Jacek Jendrzej <satbaby@kawaii.com>
sync with oher repo
fix merge error
fix last commit
remove double keys
2017-11-14 vanhofen <vanhofen@gmx.de>
- add display_has_statusline member
- generic-pc: add our proven keymap to glfb
2017-11-13 Jacek Jendrzej <satbaby@kawaii.com>
try to fix possible race condition
2017-11-12 Jacek Jendrzej <satbaby@kawaii.com>
init mpegts
Revert "return false in decoder have no time"
This reverts commit 6f006f1ce9026cccddfe87a88fb3ebaa1f6a9e98.
2017-11-11 Jacek Jendrzej <satbaby@kawaii.com>
fix last commit, broken check logic
check if tag is gst list
return false in decoder have no time
try to fix freeze with subtitle file , use gst_element_get_state only if need
2017-11-11 TangoCash <eric@loxat.de>
fix missing close fd (thx dbo)
2017-11-10 Jacek Jendrzej <satbaby@kawaii.com>
move gchar * sourceName = gst_object_get_name(source);
check m_stream_tags if not NULL
add check if children not NULL
fix memleak, init and compil
2017-11-10 TangoCash <eric@loxat.de>
gstreamer playback: fix possible race condition
gstreamer playback: fix possible segfault
2017-11-08 TangoCash <eric@loxat.de>
gstreamer playback: remove subtitles until fully supported
gstreamer playback: fix possible segfaults
CI: fix some caid issues (thx dboxoldie)
2017-11-06 Thilo Graf <dbt@novatux.de>
Merge branch 'master' of https://github.com/TangoCash/libstb-hal-cst-next.git into mpx

0
INSTALL Normal file
View File

View File

@@ -2,60 +2,82 @@ ACLOCAL_AMFLAGS = -I m4
lib_LTLIBRARIES = libstb-hal.la
libstb_hal_la_SOURCES =
SUBDIRS = common tools libthread
bin_PROGRAMS = libstb-hal-test
SUBDIRS = common tools
libstb_hal_la_LIBADD = \
common/libcommon.la \
libthread/libthread.la
common/libcommon.la
AM_CPPFLAGS = \
-I$(top_srcdir)/include
libstb_hal_test_SOURCES = libtest.cpp
libstb_hal_test_LDADD = libstb-hal.la
#bin_PROGRAMS = libstb-hal-test
#libstb_hal_test_SOURCES = libtest.cpp
#libstb_hal_test_LDADD = libstb-hal.la
# there has to be a better way to do this...
if BOXTYPE_TRIPLE
SUBDIRS += libtriple
libstb_hal_la_LIBADD += \
libtriple/libtriple.la
endif
if BOXTYPE_AZBOX
SUBDIRS += azbox
libstb_hal_la_LIBADD += \
azbox/libazbox.la
endif
if BOXTYPE_GENERIC
if BOXMODEL_RASPI
SUBDIRS += raspi
SUBDIRS += libraspi
libstb_hal_la_LIBADD += \
raspi/libraspi.la
libraspi/libraspi.la
else
SUBDIRS += generic-pc
SUBDIRS += libgeneric-pc
libstb_hal_la_LIBADD += \
generic-pc/libgeneric.la
libgeneric-pc/libgeneric.la
endif
endif
if BOXTYPE_SPARK
libstb_hal_test_LDADD += -lasound
SUBDIRS += libspark libeplayer3
#libstb_hal_test_LDADD += -lasound
SUBDIRS += libspark libeplayer3-sh4
libstb_hal_la_LIBADD += \
libspark/libspark.la \
libeplayer3/libeplayer3.la
libeplayer3-sh4/libeplayer3_sh4.la
endif
if BOXTYPE_DUCKBOX
libstb_hal_test_LDADD += -lasound
SUBDIRS += libduckbox libeplayer3 libdvbci
#libstb_hal_test_LDADD += -lasound
SUBDIRS += libduckbox libeplayer3-sh4 libdvbci
libstb_hal_la_LIBADD += \
libduckbox/libduckbox.la \
libeplayer3/libeplayer3.la \
libeplayer3-sh4/libeplayer3_sh4.la \
libdvbci/libdvbci.la
endif
if BOXTYPE_ARMBOX
libstb_hal_test_LDADD += -lasound
if BOXMODEL_HD60
SUBDIRS += libarmbox
libstb_hal_la_LIBADD += \
libarmbox/libarmbox.la
else
if BOXMODEL_OSMIO4K
SUBDIRS += libarmbox
libstb_hal_la_LIBADD += \
libarmbox/libarmbox.la
else
if BOXMODEL_OSMIO4KPLUS
SUBDIRS += libarmbox
libstb_hal_la_LIBADD += \
libarmbox/libarmbox.la
else
#libstb_hal_test_LDADD += -lasound
SUBDIRS += libarmbox libdvbci
libstb_hal_la_LIBADD += \
libarmbox/libarmbox.la \
libdvbci/libdvbci.la
endif
endif
endif
if !ENABLE_GSTREAMER_10
SUBDIRS += libeplayer3
libstb_hal_la_LIBADD += \
libeplayer3/libeplayer3.la
endif
endif
if BOXTYPE_MIPSBOX
SUBDIRS += libmipsbox libdvbci
libstb_hal_la_LIBADD += \
libmipsbox/libmipsbox.la \
libdvbci/libdvbci.la
SUBDIRS += libeplayer3
libstb_hal_la_LIBADD += \
libeplayer3/libeplayer3.la
endif

View File

@@ -1,24 +1,27 @@
AC_DEFUN([TUXBOX_APPS],[
AC_DEFUN([TUXBOX_APPS], [
AM_CONFIG_HEADER(config.h)
AM_MAINTAINER_MODE
AC_SYS_LARGEFILE
AC_GNU_SOURCE
AC_ARG_WITH(target,
[ --with-target=TARGET target for compilation [[native,cdk]]],
[TARGET="$withval"],[TARGET="native"])
AS_HELP_STRING([--with-target=TARGET], [target for compilation [[native,cdk]]]),
[TARGET="$withval"],
[TARGET="native"])
AC_ARG_WITH(targetprefix,
[ --with-targetprefix=PATH prefix relative to target root (only applicable in cdk mode)],
[targetprefix="$withval"],[targetprefix="NONE"])
AS_HELP_STRING([--with-targetprefix=PATH], [prefix relative to target root (only applicable in cdk mode)]),
[TARGET_PREFIX="$withval"],
[TARGET_PREFIX=""])
AC_ARG_WITH(debug,
[ --without-debug disable debugging code],
[DEBUG="$withval"],[DEBUG="yes"])
AS_HELP_STRING([--without-debug], [disable debugging code @<:@default=no@:>@]),
[DEBUG="$withval"],
[DEBUG="yes"])
if test "$DEBUG" = "yes"; then
DEBUG_CFLAGS="-g3 -ggdb"
AC_DEFINE(DEBUG,1,[Enable debug messages])
AC_DEFINE(DEBUG, 1, [enable debugging code])
fi
AC_MSG_CHECKING(target)
@@ -34,284 +37,187 @@ if test "$TARGET" = "native"; then
prefix=/usr/local
fi
targetprefix=$prefix
TARGET_PREFIX=$prefix
AC_DEFINE_UNQUOTED(TARGET_PREFIX, "$TARGET_PREFIX", [The targets prefix])
elif test "$TARGET" = "cdk"; then
AC_MSG_RESULT(cdk)
if test "$prefix" = "NONE"; then
AC_MSG_ERROR(invalid prefix, you need to specify one in cdk mode)
if test "$CC" = "" -a "$CXX" = ""; then
AC_MSG_ERROR([you need to specify variables CC or CXX in cdk])
fi
if test "$targetprefix" = "NONE"; then
targetprefix=""
if test "$CFLAGS" = "" -o "$CXXFLAGS" = ""; then
AC_MSG_ERROR([you need to specify variables CFLAGS and CXXFLAGS in cdk])
fi
if test "$prefix" = "NONE"; then
AC_MSG_ERROR([invalid prefix, you need to specify one in cdk mode])
fi
if test "$TARGET_PREFIX" != "NONE"; then
AC_DEFINE_UNQUOTED(TARGET_PREFIX, "$TARGET_PREFIX", [The targets prefix])
fi
if test "$TARGET_PREFIX" = "NONE"; then
AC_MSG_ERROR([invalid targetprefix, you need to specify one in cdk mode])
TARGET_PREFIX=""
fi
else
AC_MSG_RESULT(none)
AC_MSG_ERROR([invalid target $TARGET, choose on from native,cdk]);
fi
AC_CANONICAL_BUILD
AC_CANONICAL_HOST
])
dnl expand nested ${foo}/bar
AC_DEFUN([TUXBOX_EXPAND_VARIABLE],[__$1="$2"
for __CNT in false false false false true; do dnl max 5 levels of indirection
$1=`eval echo "$__$1"`
echo ${$1} | grep -q '\$' || break # 'grep -q' is POSIX, exit if no $ in variable
__$1="${$1}"
done
$__CNT && AC_MSG_ERROR([can't expand variable $1=$2]) dnl bail out if we did not expand
])
AC_DEFUN([TUXBOX_APPS_DIRECTORY_ONE],[
AC_ARG_WITH($1,[ $6$7 [[PREFIX$4$5]]],[
_$2=$withval
if test "$TARGET" = "cdk"; then
$2=`eval echo "${targetprefix}$withval"` # no indirection possible IMNSHO
else
$2=$withval
fi
TARGET_$2=${$2}
],[
# RFC 1925: "you can always add another level of indirection..."
TUXBOX_EXPAND_VARIABLE($2,"${$3}$5")
if test "$TARGET" = "cdk"; then
TUXBOX_EXPAND_VARIABLE(_$2,"${target$3}$5")
else
_$2=${$2}
fi
TARGET_$2=$_$2
])
dnl AC_SUBST($2)
AC_DEFINE_UNQUOTED($2,"$_$2",$7)
AC_SUBST(TARGET_$2)
])
AC_DEFUN([TUXBOX_APPS_DIRECTORY],[
AC_REQUIRE([TUXBOX_APPS])
if test "$TARGET" = "cdk"; then
datadir="\${prefix}/share"
sysconfdir="\${prefix}/etc"
localstatedir="\${prefix}/var"
libdir="\${prefix}/lib"
targetdatadir="\${targetprefix}/share"
targetsysconfdir="\${targetprefix}/etc"
targetlocalstatedir="\${targetprefix}/var"
targetlibdir="\${targetprefix}/lib"
if test "$exec_prefix" = "NONE"; then
exec_prefix=$prefix
fi
TUXBOX_APPS_DIRECTORY_ONE(configdir,CONFIGDIR,localstatedir,/var,/tuxbox/config,
[--with-configdir=PATH ],[where to find the config files])
AC_CANONICAL_BUILD
AC_CANONICAL_HOST
AC_SYS_LARGEFILE
TUXBOX_APPS_DIRECTORY_ONE(datadir,DATADIR,datadir,/share,/tuxbox,
[--with-datadir=PATH ],[where to find data])
TUXBOX_APPS_DIRECTORY_ONE(fontdir,FONTDIR,datadir,/share,/fonts,
[--with-fontdir=PATH ],[where to find the fonts])
TUXBOX_APPS_DIRECTORY_ONE(gamesdir,GAMESDIR,localstatedir,/var,/tuxbox/games,
[--with-gamesdir=PATH ],[where games data is stored])
TUXBOX_APPS_DIRECTORY_ONE(libdir,LIBDIR,libdir,/lib,/tuxbox,
[--with-libdir=PATH ],[where to find the internal libs])
TUXBOX_APPS_DIRECTORY_ONE(plugindir,PLUGINDIR,libdir,/lib,/tuxbox/plugins,
[--with-plugindir=PATH ],[where to find the plugins])
TUXBOX_APPS_DIRECTORY_ONE(themesdir,THEMESDIR,datadir,/share,/tuxbox/neutrino/themes,
[--with-themesdir=PATH ],[where to find the themes (don't change)])
])
dnl automake <= 1.6 needs this specifications
AC_SUBST(CONFIGDIR)
AC_SUBST(DATADIR)
AC_SUBST(FONTDIR)
AC_SUBST(GAMESDIR)
AC_SUBST(LIBDIR)
AC_SUBST(PLUGINDIR)
AC_SUBST(THEMESDIR)
dnl end workaround
AC_DEFUN([TUXBOX_BOXTYPE],[
AC_DEFUN([TUXBOX_BOXTYPE], [
AC_ARG_WITH(boxtype,
[ --with-boxtype valid values: tripledragon,spark,azbox,generic,duckbox,spark7162,armbox],
AS_HELP_STRING([--with-boxtype], [valid values: generic, spark, duckbox, armbox, mipsbox]),
[case "${withval}" in
tripledragon|azbox|generic)
generic|spark|duckbox|armbox|mipsbox)
BOXTYPE="$withval"
;;
spark|spark7162)
BOXTYPE="spark"
BOXMODEL="$withval"
;;
dm*)
BOXTYPE="dreambox"
BOXMODEL="$withval"
;;
ufs*)
BOXTYPE="duckbox"
BOXMODEL="$withval"
;;
atevio*)
BOXTYPE="duckbox"
BOXMODEL="$withval"
;;
fortis*)
BOXTYPE="duckbox"
BOXMODEL="$withval"
;;
octagon*)
BOXTYPE="duckbox"
BOXMODEL="$withval"
;;
hs7*)
BOXTYPE="duckbox"
BOXMODEL="$withval"
;;
dp*)
BOXTYPE="duckbox"
BOXMODEL="$withval"
;;
cuberevo*)
BOXTYPE="duckbox"
BOXMODEL="$withval"
;;
ipbox*)
BOXTYPE="duckbox"
BOXMODEL="$withval"
;;
arivalink200)
BOXTYPE="duckbox"
BOXMODEL="$withval"
;;
tf*)
BOXTYPE="duckbox"
BOXMODEL="$withval"
;;
hl101)
BOXTYPE="duckbox"
BOXMODEL="$withval"
;;
hd51)
BOXTYPE="armbox"
BOXMODEL="$withval"
;;
vusolo4k)
BOXTYPE="armbox"
BOXMODEL="$withval"
;;
;;
*)
AC_MSG_ERROR([bad value $withval for --with-boxtype]) ;;
esac], [BOXTYPE="generic"])
AC_MSG_ERROR([bad value $withval for --with-boxtype])
;;
esac],
[BOXTYPE="generic"])
AC_ARG_WITH(boxmodel,
[ --with-boxmodel valid for generic: raspi
valid for duckbox: ufs910, ufs912, ufs913, ufs922, atevio7500, fortis_hdbox, octagon1008, hs7110, hs7810a, hs7119, hs7819, dp7000, cuberevo, cuberevo_mini, cuberevo_mini2, cuberevo_250hd, cuberevo_2000hd, cuberevo_3000hd, ipbox9900, ipbox99, ipbox55, arivalink200, tf7700, hl101
valid for spark: spark, spark7162
valid for armbox: hd51, vusolo4k],
AS_HELP_STRING([--with-boxmodel], [valid for generic: generic, raspi])
AS_HELP_STRING([], [valid for spark: spark, spark7162])
AS_HELP_STRING([], [valid for duckbox: ufs910, ufs912, ufs913, ufs922, atevio7500, fortis_hdbox, octagon1008, hs7110, hs7810a, hs7119, hs7819, dp7000, cuberevo, cuberevo_mini, cuberevo_mini2, cuberevo_250hd, cuberevo_2000hd, cuberevo_3000hd, ipbox9900, ipbox99, ipbox55, arivalink200, tf7700, hl101])
AS_HELP_STRING([], [valid for armbox: hd51, hd60, hd61, bre2ze4k, h7, osmio4k, osmio4kplus, vusolo4k, vuduo4k, vuduo4kse, vuultimo4k, vuuno4k, vuuno4kse, vuzero4k])
AS_HELP_STRING([], [valid for mipsbox: vuduo]),
[case "${withval}" in
ufs910|ufs912|ufs913|ufs922|atevio7500|fortis_hdbox|octagon1008|hs7110|hs7810a|hs7119|hs7819|dp7000|cuberevo|cuberevo_mini|cuberevo_mini2|cuberevo_250hd|cuberevo_2000hd|cuberevo_3000hd|ipbox9900|ipbox99|ipbox55|arivalink200|tf7700|hl101)
if test "$BOXTYPE" = "duckbox"; then
generic|raspi)
if test "$BOXTYPE" = "generic"; then
BOXMODEL="$withval"
else
AC_MSG_ERROR([unknown model $withval for boxtype $BOXTYPE])
fi
;;
;;
spark|spark7162)
if test "$BOXTYPE" = "spark"; then
BOXMODEL="$withval"
else
AC_MSG_ERROR([unknown model $withval for boxtype $BOXTYPE])
fi
;;
raspi)
if test "$BOXTYPE" = "generic"; then
;;
ufs910|ufs912|ufs913|ufs922|atevio7500|fortis_hdbox|octagon1008|hs7110|hs7810a|hs7119|hs7819|dp7000|cuberevo|cuberevo_mini|cuberevo_mini2|cuberevo_250hd|cuberevo_2000hd|cuberevo_3000hd|ipbox9900|ipbox99|ipbox55|arivalink200|tf7700|hl101)
if test "$BOXTYPE" = "duckbox"; then
BOXMODEL="$withval"
else
AC_MSG_ERROR([unknown model $withval for boxtype $BOXTYPE])
fi
;;
hd51)
;;
hd51|hd60|hd61|bre2ze4k|h7|osmio4k|osmio4kplus|vusolo4k|vuduo4k|vuduo4kse|vuultimo4k|vuuno4k|vuuno4kse|vuzero4k)
if test "$BOXTYPE" = "armbox"; then
BOXMODEL="$withval"
else
AC_MSG_ERROR([unknown model $withval for boxtype $BOXTYPE])
fi
;;
vusolo4k)
if test "$BOXTYPE" = "armbox"; then
;;
vuduo)
if test "$BOXTYPE" = "mipsbox"; then
BOXMODEL="$withval"
else
AC_MSG_ERROR([unknown model $withval for boxtype $BOXTYPE])
fi
;;
;;
*)
AC_MSG_ERROR([unsupported value $withval for --with-boxmodel])
;;
esac])
;;
esac],
[BOXMODEL="generic"])
AC_SUBST(BOXTYPE)
AC_SUBST(BOXMODEL)
AM_CONDITIONAL(BOXTYPE_AZBOX, test "$BOXTYPE" = "azbox")
AM_CONDITIONAL(BOXTYPE_TRIPLE, test "$BOXTYPE" = "tripledragon")
AM_CONDITIONAL(BOXTYPE_SPARK, test "$BOXTYPE" = "spark")
AM_CONDITIONAL(BOXTYPE_GENERIC, test "$BOXTYPE" = "generic")
AM_CONDITIONAL(BOXTYPE_SPARK, test "$BOXTYPE" = "spark")
AM_CONDITIONAL(BOXTYPE_DUCKBOX, test "$BOXTYPE" = "duckbox")
AM_CONDITIONAL(BOXTYPE_ARMBOX, test "$BOXTYPE" = "armbox")
AM_CONDITIONAL(BOXTYPE_MIPSBOX, test "$BOXTYPE" = "mipsbox")
AM_CONDITIONAL(BOXMODEL_UFS910,test "$BOXMODEL" = "ufs910")
AM_CONDITIONAL(BOXMODEL_UFS912,test "$BOXMODEL" = "ufs912")
AM_CONDITIONAL(BOXMODEL_UFS913,test "$BOXMODEL" = "ufs913")
AM_CONDITIONAL(BOXMODEL_UFS922,test "$BOXMODEL" = "ufs922")
AM_CONDITIONAL(BOXMODEL_SPARK,test "$BOXMODEL" = "spark")
AM_CONDITIONAL(BOXMODEL_SPARK7162,test "$BOXMODEL" = "spark7162")
AM_CONDITIONAL(BOXMODEL_ATEVIO7500,test "$BOXMODEL" = "atevio7500")
AM_CONDITIONAL(BOXMODEL_FORTIS_HDBOX,test "$BOXMODEL" = "fortis_hdbox")
AM_CONDITIONAL(BOXMODEL_OCTAGON1008,test "$BOXMODEL" = "octagon1008")
AM_CONDITIONAL(BOXMODEL_HS7110,test "$BOXMODEL" = "hs7110")
AM_CONDITIONAL(BOXMODEL_HS7810A,test "$BOXMODEL" = "hs7810a")
AM_CONDITIONAL(BOXMODEL_HS7119,test "$BOXMODEL" = "hs7119")
AM_CONDITIONAL(BOXMODEL_HS7819,test "$BOXMODEL" = "hs7819")
AM_CONDITIONAL(BOXMODEL_DP7000,test "$BOXMODEL" = "dp7000")
AM_CONDITIONAL(BOXMODEL_CUBEREVO,test "$BOXMODEL" = "cuberevo")
AM_CONDITIONAL(BOXMODEL_CUBEREVO_MINI,test "$BOXMODEL" = "cuberevo_mini")
AM_CONDITIONAL(BOXMODEL_CUBEREVO_MINI2,test "$BOXMODEL" = "cuberevo_mini2")
AM_CONDITIONAL(BOXMODEL_CUBEREVO_250HD,test "$BOXMODEL" = "cuberevo_250hd")
AM_CONDITIONAL(BOXMODEL_CUBEREVO_2000HD,test "$BOXMODEL" = "cuberevo_2000hd")
AM_CONDITIONAL(BOXMODEL_CUBEREVO_3000HD,test "$BOXMODEL" = "cuberevo_3000hd")
AM_CONDITIONAL(BOXMODEL_IPBOX9900,test "$BOXMODEL" = "ipbox9900")
AM_CONDITIONAL(BOXMODEL_IPBOX99,test "$BOXMODEL" = "ipbox99")
AM_CONDITIONAL(BOXMODEL_IPBOX55,test "$BOXMODEL" = "ipbox55")
AM_CONDITIONAL(BOXMODEL_ARIVALINK200,test "$BOXMODEL" = "arivalink200")
AM_CONDITIONAL(BOXMODEL_TF7700,test "$BOXMODEL" = "tf7700")
AM_CONDITIONAL(BOXMODEL_HL101,test "$BOXMODEL" = "hl101")
# generic
AM_CONDITIONAL(BOXMODEL_GENERIC, test "$BOXMODEL" = "generic")
AM_CONDITIONAL(BOXMODEL_RASPI, test "$BOXMODEL" = "raspi")
AM_CONDITIONAL(BOXMODEL_HD51,test "$BOXMODEL" = "hd51")
AM_CONDITIONAL(BOXMODEL_VUSOLO4K,test "$BOXMODEL" = "vusolo4k")
# spark
AM_CONDITIONAL(BOXMODEL_SPARK, test "$BOXMODEL" = "spark")
AM_CONDITIONAL(BOXMODEL_SPARK7162, test "$BOXMODEL" = "spark7162")
AM_CONDITIONAL(BOXMODEL_RASPI,test "$BOXMODEL" = "raspi")
# duckbox
AM_CONDITIONAL(BOXMODEL_UFS910, test "$BOXMODEL" = "ufs910")
AM_CONDITIONAL(BOXMODEL_UFS912, test "$BOXMODEL" = "ufs912")
AM_CONDITIONAL(BOXMODEL_UFS913, test "$BOXMODEL" = "ufs913")
AM_CONDITIONAL(BOXMODEL_UFS922, test "$BOXMODEL" = "ufs922")
AM_CONDITIONAL(BOXMODEL_SPARK, test "$BOXMODEL" = "spark")
AM_CONDITIONAL(BOXMODEL_SPARK7162, test "$BOXMODEL" = "spark7162")
AM_CONDITIONAL(BOXMODEL_ATEVIO7500, test "$BOXMODEL" = "atevio7500")
AM_CONDITIONAL(BOXMODEL_FORTIS_HDBOX, test "$BOXMODEL" = "fortis_hdbox")
AM_CONDITIONAL(BOXMODEL_OCTAGON1008, test "$BOXMODEL" = "octagon1008")
AM_CONDITIONAL(BOXMODEL_HS7110, test "$BOXMODEL" = "hs7110")
AM_CONDITIONAL(BOXMODEL_HS7810A, test "$BOXMODEL" = "hs7810a")
AM_CONDITIONAL(BOXMODEL_HS7119, test "$BOXMODEL" = "hs7119")
AM_CONDITIONAL(BOXMODEL_HS7819, test "$BOXMODEL" = "hs7819")
AM_CONDITIONAL(BOXMODEL_DP7000, test "$BOXMODEL" = "dp7000")
if test "$BOXTYPE" = "azbox"; then
AC_DEFINE(HAVE_AZBOX_HARDWARE, 1, [building for an azbox])
elif test "$BOXTYPE" = "tripledragon"; then
AC_DEFINE(HAVE_TRIPLEDRAGON, 1, [building for a tripledragon])
AM_CONDITIONAL(BOXMODEL_CUBEREVO, test "$BOXMODEL" = "cuberevo")
AM_CONDITIONAL(BOXMODEL_CUBEREVO_MINI, test "$BOXMODEL" = "cuberevo_mini")
AM_CONDITIONAL(BOXMODEL_CUBEREVO_MINI2, test "$BOXMODEL" = "cuberevo_mini2")
AM_CONDITIONAL(BOXMODEL_CUBEREVO_250HD, test "$BOXMODEL" = "cuberevo_250hd")
AM_CONDITIONAL(BOXMODEL_CUBEREVO_2000HD, test "$BOXMODEL" = "cuberevo_2000hd")
AM_CONDITIONAL(BOXMODEL_CUBEREVO_3000HD, test "$BOXMODEL" = "cuberevo_3000hd")
AM_CONDITIONAL(BOXMODEL_IPBOX9900, test "$BOXMODEL" = "ipbox9900")
AM_CONDITIONAL(BOXMODEL_IPBOX99, test "$BOXMODEL" = "ipbox99")
AM_CONDITIONAL(BOXMODEL_IPBOX55, test "$BOXMODEL" = "ipbox55")
AM_CONDITIONAL(BOXMODEL_ARIVALINK200, test "$BOXMODEL" = "arivalink200")
AM_CONDITIONAL(BOXMODEL_TF7700, test "$BOXMODEL" = "tf7700")
AM_CONDITIONAL(BOXMODEL_HL101, test "$BOXMODEL" = "hl101")
# armbox
AM_CONDITIONAL(BOXMODEL_HD51, test "$BOXMODEL" = "hd51")
AM_CONDITIONAL(BOXMODEL_HD60, test "$BOXMODEL" = "hd60")
AM_CONDITIONAL(BOXMODEL_HD61, test "$BOXMODEL" = "hd61")
AM_CONDITIONAL(BOXMODEL_BRE2ZE4K, test "$BOXMODEL" = "bre2ze4k")
AM_CONDITIONAL(BOXMODEL_H7, test "$BOXMODEL" = "h7")
AM_CONDITIONAL(BOXMODEL_OSMIO4K, test "$BOXMODEL" = "osmio4k")
AM_CONDITIONAL(BOXMODEL_OSMIO4KPLUS, test "$BOXMODEL" = "osmio4kplus")
AM_CONDITIONAL(BOXMODEL_VUSOLO4K, test "$BOXMODEL" = "vusolo4k")
AM_CONDITIONAL(BOXMODEL_VUDUO4K, test "$BOXMODEL" = "vuduo4k")
AM_CONDITIONAL(BOXMODEL_VUDUO4KSE, test "$BOXMODEL" = "vuduo4kse")
AM_CONDITIONAL(BOXMODEL_VUULTIMO4K, test "$BOXMODEL" = "vuultimo4k")
AM_CONDITIONAL(BOXMODEL_VUUNO4K, test "$BOXMODEL" = "vuuno4k")
AM_CONDITIONAL(BOXMODEL_VUUNO4KSE, test "$BOXMODEL" = "vuuno4kse")
AM_CONDITIONAL(BOXMODEL_VUZERO4K, test "$BOXMODEL" = "vuzero4k")
# mipsbox
AM_CONDITIONAL(BOXMODEL_VUDUO, test "$BOXMODEL" = "vuduo")
if test "$BOXTYPE" = "generic"; then
AC_DEFINE(HAVE_GENERIC_HARDWARE, 1, [building for a generic device like a standard PC])
elif test "$BOXTYPE" = "spark"; then
AC_DEFINE(HAVE_SPARK_HARDWARE, 1, [building for a goldenmedia 990 or edision pingulux])
elif test "$BOXTYPE" = "generic"; then
AC_DEFINE(HAVE_GENERIC_HARDWARE, 1, [building for a generic device like a standard PC])
AC_DEFINE(HAVE_SH4_HARDWARE, 1, [building for a sh4 box])
elif test "$BOXTYPE" = "duckbox"; then
AC_DEFINE(HAVE_DUCKBOX_HARDWARE, 1, [building for a duckbox])
AC_DEFINE(HAVE_SH4_HARDWARE, 1, [building for a sh4 box])
elif test "$BOXTYPE" = "armbox"; then
AC_DEFINE(HAVE_ARM_HARDWARE, 1, [building for an armbox])
elif test "$BOXTYPE" = "mipsbox"; then
AC_DEFINE(HAVE_MIPS_HARDWARE, 1, [building for an mipsbox])
fi
# TODO: do we need more defines?
if test "$BOXMODEL" = "raspi"; then
AC_DEFINE(BOXMODEL_RASPI, 1, [Raspberry pi])
if test "$BOXMODEL" = "generic"; then
AC_DEFINE(BOXMODEL_GENERIC, 1, [generic pc])
elif test "$BOXMODEL" = "raspi"; then
AC_DEFINE(BOXMODEL_RASPI, 1, [raspberry pi])
elif test "$BOXMODEL" = "ufs910"; then
AC_DEFINE(BOXMODEL_UFS910, 1, [ufs910])
elif test "$BOXMODEL" = "ufs912"; then
@@ -365,31 +271,107 @@ elif test "$BOXMODEL" = "tf7700"; then
elif test "$BOXMODEL" = "hl101"; then
AC_DEFINE(BOXMODEL_HL101, 1, [hl101])
elif test "$BOXMODEL" = "hd51"; then
AC_DEFINE(BOXMODEL_HD51, 1, [HD51 / AX51])
AC_DEFINE(BOXMODEL_HD51, 1, [hd51])
elif test "$BOXMODEL" = "hd60"; then
AC_DEFINE(BOXMODEL_HD60, 1, [hd60])
elif test "$BOXMODEL" = "hd61"; then
AC_DEFINE(BOXMODEL_HD61, 1, [hd61])
elif test "$BOXMODEL" = "bre2ze4k"; then
AC_DEFINE(BOXMODEL_BRE2ZE4K, 1, [bre2ze4k])
elif test "$BOXMODEL" = "h7"; then
AC_DEFINE(BOXMODEL_H7, 1, [h7])
elif test "$BOXMODEL" = "osmio4k"; then
AC_DEFINE(BOXMODEL_OSMIO4K, 1, [osmio4k])
elif test "$BOXMODEL" = "osmio4kplus"; then
AC_DEFINE(BOXMODEL_OSMIO4KPLUS, 1, [osmio4kplus])
elif test "$BOXMODEL" = "vusolo4k"; then
AC_DEFINE(BOXMODEL_VUSOLO4K, 1, [vusolo4k])
elif test "$BOXMODEL" = "vuduo4k"; then
AC_DEFINE(BOXMODEL_VUDUO4K, 1, [vuduo4k])
elif test "$BOXMODEL" = "vuduo4kse"; then
AC_DEFINE(BOXMODEL_VUDUO4KSE, 1, [vuduo4kse])
elif test "$BOXMODEL" = "vuultimo4k"; then
AC_DEFINE(BOXMODEL_VUULTIMO4K, 1, [vuultimo4k])
elif test "$BOXMODEL" = "vuuno4k"; then
AC_DEFINE(BOXMODEL_VUUNO4K, 1, [vuuno4k])
elif test "$BOXMODEL" = "vuuno4kse"; then
AC_DEFINE(BOXMODEL_VUUNO4KSE, 1, [vuuno4kse])
elif test "$BOXMODEL" = "vuzero4k"; then
AC_DEFINE(BOXMODEL_VUZERO4K, 1, [vuzero4k])
elif test "$BOXMODEL" = "vuduo"; then
AC_DEFINE(BOXMODEL_VUDUO, 1, [vuduo])
fi
# all vuplus BOXMODELs
case "$BOXMODEL" in
vusolo4k|vuduo4k|vuduo4kse|vuultimo4k|vuuno4k|vuuno4kse|vuzero4k|vuduo)
AC_DEFINE(BOXMODEL_VUPLUS_ALL, 1, [vuplus_all])
vuplus_all=true
;;
*)
vuplus_all=false
;;
esac
AM_CONDITIONAL(BOXMODEL_VUPLUS_ALL, test "$vuplus_all" = "true")
# all vuplus arm BOXMODELs
case "$BOXMODEL" in
vusolo4k|vuduo4k|vuduo4kse|vuultimo4k|vuuno4k|vuuno4kse|vuzero4k)
AC_DEFINE(BOXMODEL_VUPLUS_ARM, 1, [vuplus_arm])
vuplus_arm=true
;;
*)
vuplus_arm=false
;;
esac
AM_CONDITIONAL(BOXMODEL_VUPLUS_ARM, test "$vuplus_arm" = "true")
# all vuplus mips BOXMODELs
case "$BOXMODEL" in
vuduo)
AC_DEFINE(BOXMODEL_VUPLUS_MIPS, 1, [vuplus_mips])
vuplus_mips=true
;;
*)
vuplus_mips=false
;;
esac
AM_CONDITIONAL(BOXMODEL_VUPLUS_MIPS, test "$vuplus_mips" = "true")
# all hisilicon BOXMODELs
case "$BOXMODEL" in
hd60|hd61)
AC_DEFINE(BOXMODEL_HISILICON, 1, [hisilicon])
hisilicon=true
;;
*)
hisilicon=false
;;
esac
AM_CONDITIONAL(BOXMODEL_HISILICON, test "$hisilicon" = "true")
])
dnl backward compatiblity
AC_DEFUN([AC_GNU_SOURCE],
[AH_VERBATIM([_GNU_SOURCE],
[/* Enable GNU extensions on systems that have them. */
AC_DEFUN([AC_GNU_SOURCE], [
AH_VERBATIM([_GNU_SOURCE], [
/* Enable GNU extensions on systems that have them. */
#ifndef _GNU_SOURCE
# undef _GNU_SOURCE
#endif])dnl
#endif
])dnl
AC_BEFORE([$0], [AC_COMPILE_IFELSE])dnl
AC_BEFORE([$0], [AC_RUN_IFELSE])dnl
AC_DEFINE([_GNU_SOURCE])
])
AC_DEFUN([AC_PROG_EGREP],
[AC_CACHE_CHECK([for egrep], [ac_cv_prog_egrep],
[if echo a | (grep -E '(a|b)') >/dev/null 2>&1
then ac_cv_prog_egrep='grep -E'
else ac_cv_prog_egrep='egrep'
fi])
EGREP=$ac_cv_prog_egrep
AC_SUBST([EGREP])
AC_DEFUN([AC_PROG_EGREP], [
AC_CACHE_CHECK([for egrep], [ac_cv_prog_egrep], [
if echo a | (grep -E '(a|b)') >/dev/null 2>&1; then
ac_cv_prog_egrep='grep -E'
else
ac_cv_prog_egrep='egrep'
fi
])
EGREP=$ac_cv_prog_egrep
AC_SUBST([EGREP])
])

View File

@@ -1,8 +1,15 @@
#!/bin/bash
#!/bin/sh
package="libstb-hal"
srcdir=`dirname $0`
test -z "$srcdir" && srcdir=.
cd "$srcdir"
echo "Generating configuration files for $package, please wait ..."
cd $(dirname $0)
aclocal --force
libtoolize --force
autoconf --force
autoheader --force
automake --add-missing --force-missing --foreign
automake --add-missing --force-missing

View File

@@ -1,18 +0,0 @@
noinst_LTLIBRARIES = libazbox.la
AM_CPPFLAGS = \
-I$(top_srcdir)/common
AM_CXXFLAGS = -fno-rtti -fno-exceptions -fno-strict-aliasing
AM_LDFLAGS = -lpthread
libazbox_la_SOURCES = \
hardware_caps.c \
dmx.cpp \
video.cpp \
audio.cpp \
init.cpp \
playback.cpp \
pwrmngr.cpp \
record.cpp

View File

@@ -1,398 +0,0 @@
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <sys/fcntl.h>
#include <sys/ioctl.h>
#include <unistd.h>
#include <linux/dvb/audio.h>
#include <proc_tools.h>
#include "audio_lib.h"
#include "lt_debug.h"
#define AUDIO_DEVICE "/dev/dvb/adapter0/audio0"
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_AUDIO, this, args)
#define lt_info(args...) _lt_info(TRIPLE_DEBUG_AUDIO, this, args)
#include <linux/soundcard.h>
cAudio * audioDecoder = NULL;
cAudio::cAudio(void *, void *, void *)
{
fd = -1;
clipfd = -1;
mixer_fd = -1;
openDevice();
Muted = false;
}
cAudio::~cAudio(void)
{
closeDevice();
}
void cAudio::openDevice(void)
{
lt_debug("%s\n", __func__);
if (fd < 0)
{
if ((fd = open(AUDIO_DEVICE, O_RDONLY|O_CLOEXEC)) < 0)
lt_info("openDevice: open failed (%m)\n");
do_mute(true, false);
}
else
lt_info("openDevice: already open (fd = %d)\n", fd);
}
void cAudio::closeDevice(void)
{
lt_debug("%s\n", __func__);
ioctl(fd, AUDIO_CONTINUE); /* enigma2 also does CONTINUE before close... */
if (fd >= 0)
close(fd);
fd = -1;
if (clipfd >= 0)
close(clipfd);
clipfd = -1;
if (mixer_fd >= 0)
close(mixer_fd);
mixer_fd = -1;
}
int cAudio::do_mute(bool enable, bool remember)
{
lt_debug("%s(%d, %d)\n", __func__, enable, remember);
if (remember)
Muted = enable;
#if 0
/* does not work? */
if (ioctl(fd, AUDIO_SET_MUTE, enable) < 0 )
lt_info("%s: AUDIO_SET_MUTE failed (%m)\n", __func__);
#else
char s[2] = { 0, 0 };
s[0] = '0' + (int)enable;
proc_put("/proc/stb/audio/j1_mute", s, 2);
#endif
return 0;
}
int map_volume(const int volume)
{
unsigned char vol = volume;
if (vol > 100)
vol = 100;
vol = 63 - vol * 63 / 100;
return vol;
}
int cAudio::setVolume(unsigned int left, unsigned int right)
{
lt_debug("%s(%d, %d)\n", __func__, left, right);
volume = (left + right) / 2;
if (clipfd != -1 && mixer_fd != -1) {
int tmp = 0;
/* not sure if left / right is correct here, but it is always the same anyways ;-) */
if (! Muted)
tmp = left << 8 | right;
int ret = ioctl(mixer_fd, MIXER_WRITE(mixer_num), &tmp);
if (ret == -1)
lt_info("%s: MIXER_WRITE(%d),%04x: %m\n", __func__, mixer_num, tmp);
return ret;
}
audio_mixer_t mixer;
mixer.volume_left = map_volume(left);
mixer.volume_right = map_volume(right);
if (ioctl(fd, AUDIO_SET_MIXER, &mixer) < 0)
lt_info("%s: AUDIO_SET_MIXER failed (%m)\n", __func__);
return 0;
}
int cAudio::Start(void)
{
lt_debug("%s\n", __func__);
int ret;
ioctl(fd, AUDIO_CONTINUE);
ret = ioctl(fd, AUDIO_PLAY);
return ret;
}
int cAudio::Stop(void)
{
lt_debug("%s\n", __func__);
ioctl(fd, AUDIO_STOP);
ioctl(fd, AUDIO_CONTINUE); /* no idea why we have to stop and then continue => enigma2 does it, too */
return 0;
}
bool cAudio::Pause(bool /*Pcm*/)
{
return true;
};
void cAudio::SetSyncMode(AVSYNC_TYPE Mode)
{
lt_debug("%s %d\n", __func__, Mode);
ioctl(fd, AUDIO_SET_AV_SYNC, Mode);
};
//AUDIO_ENCODING_AC3
#define AUDIO_STREAMTYPE_AC3 0
//AUDIO_ENCODING_MPEG2
#define AUDIO_STREAMTYPE_MPEG 1
//AUDIO_ENCODING_DTS
#define AUDIO_STREAMTYPE_DTS 2
#define AUDIO_ENCODING_LPCM 2
#define AUDIO_ENCODING_LPCMA 11
void cAudio::SetStreamType(AUDIO_FORMAT type)
{
int bypass = AUDIO_STREAMTYPE_MPEG;
lt_debug("%s %d\n", __func__, type);
StreamType = type;
switch (type)
{
case AUDIO_FMT_DOLBY_DIGITAL:
bypass = AUDIO_STREAMTYPE_AC3;
break;
case AUDIO_FMT_DTS:
bypass = AUDIO_STREAMTYPE_DTS;
break;
case AUDIO_FMT_MPEG:
default:
break;
}
// Normaly the encoding should be set using AUDIO_SET_ENCODING
// But as we implemented the behavior to bypass (cause of e2) this is correct here
if (ioctl(fd, AUDIO_SET_BYPASS_MODE, bypass) < 0)
lt_info("%s: AUDIO_SET_BYPASS_MODE failed (%m)\n", __func__);
};
int cAudio::setChannel(int channel)
{
return 0;
};
int cAudio::PrepareClipPlay(int ch, int srate, int bits, int little_endian)
{
int fmt;
unsigned int devmask, stereo, usable;
const char *dsp_dev = getenv("DSP_DEVICE");
const char *mix_dev = getenv("MIX_DEVICE");
lt_debug("%s ch %d srate %d bits %d le %d\n", __FUNCTION__, ch, srate, bits, little_endian);
if (clipfd >= 0) {
lt_info("%s: clipfd already opened (%d)\n", __FUNCTION__, clipfd);
return -1;
}
mixer_num = -1;
mixer_fd = -1;
/* a different DSP device can be given with DSP_DEVICE and MIX_DEVICE
* if this device cannot be opened, we fall back to the internal OSS device
* Example:
* modprobe snd-usb-audio
* export DSP_DEVICE=/dev/sound/dsp2
* export MIX_DEVICE=/dev/sound/mixer2
* neutrino
*/
if ((!dsp_dev) || (access(dsp_dev, W_OK))) {
if (dsp_dev)
lt_info("%s: DSP_DEVICE is set (%s) but cannot be opened,"
" fall back to /dev/dsp1\n", __func__, dsp_dev);
dsp_dev = "/dev/dsp1";
}
lt_info("%s: dsp_dev %s mix_dev %s\n", __func__, dsp_dev, mix_dev); /* NULL mix_dev is ok */
/* the tdoss dsp driver seems to work only on the second open(). really. */
clipfd = open(dsp_dev, O_WRONLY|O_CLOEXEC);
if (clipfd < 0) {
lt_info("%s open %s: %m\n", dsp_dev, __FUNCTION__);
return -1;
}
/* no idea if we ever get little_endian == 0 */
if (little_endian)
fmt = AFMT_S16_BE;
else
fmt = AFMT_S16_LE;
if (ioctl(clipfd, SNDCTL_DSP_SETFMT, &fmt))
perror("SNDCTL_DSP_SETFMT");
if (ioctl(clipfd, SNDCTL_DSP_CHANNELS, &ch))
perror("SNDCTL_DSP_CHANNELS");
if (ioctl(clipfd, SNDCTL_DSP_SPEED, &srate))
perror("SNDCTL_DSP_SPEED");
if (ioctl(clipfd, SNDCTL_DSP_RESET))
perror("SNDCTL_DSP_RESET");
if (!mix_dev)
return 0;
mixer_fd = open(mix_dev, O_RDWR|O_CLOEXEC);
if (mixer_fd < 0) {
lt_info("%s: open mixer %s failed (%m)\n", __func__, mix_dev);
/* not a real error */
return 0;
}
if (ioctl(mixer_fd, SOUND_MIXER_READ_DEVMASK, &devmask) == -1) {
lt_info("%s: SOUND_MIXER_READ_DEVMASK %m\n", __func__);
devmask = 0;
}
if (ioctl(mixer_fd, SOUND_MIXER_READ_STEREODEVS, &stereo) == -1) {
lt_info("%s: SOUND_MIXER_READ_STEREODEVS %m\n", __func__);
stereo = 0;
}
usable = devmask & stereo;
if (usable == 0) {
lt_info("%s: devmask: %08x stereo: %08x, no usable dev :-(\n",
__func__, devmask, stereo);
close(mixer_fd);
mixer_fd = -1;
return 0; /* TODO: should we treat this as error? */
}
/* __builtin_popcount needs GCC, it counts the set bits... */
if (__builtin_popcount (usable) != 1) {
/* TODO: this code is not yet tested as I have only single-mixer devices... */
lt_info("%s: more than one mixer control: devmask %08x stereo %08x\n"
"%s: querying MIX_NUMBER environment variable...\n",
__func__, devmask, stereo, __func__);
const char *tmp = getenv("MIX_NUMBER");
if (tmp)
mixer_num = atoi(tmp);
lt_info("%s: mixer_num is %d -> device %08x\n",
__func__, mixer_num, (mixer_num >= 0) ? (1 << mixer_num) : 0);
/* no error checking, you'd better know what you are doing... */
} else {
mixer_num = 0;
while (!(usable & 0x01)) {
mixer_num++;
usable >>= 1;
}
}
setVolume(volume, volume);
return 0;
};
int cAudio::WriteClip(unsigned char *buffer, int size)
{
int ret;
// lt_debug("cAudio::%s\n", __FUNCTION__);
if (clipfd <= 0) {
lt_info("%s: clipfd not yet opened\n", __FUNCTION__);
return -1;
}
ret = write(clipfd, buffer, size);
if (ret < 0)
lt_info("%s: write error (%m)\n", __FUNCTION__);
return ret;
};
int cAudio::StopClip()
{
lt_debug("%s\n", __FUNCTION__);
if (clipfd <= 0) {
lt_info("%s: clipfd not yet opened\n", __FUNCTION__);
return -1;
}
close(clipfd);
clipfd = -1;
if (mixer_fd >= 0)
close(mixer_fd);
mixer_fd = -1;
setVolume(volume, volume);
return 0;
};
void cAudio::getAudioInfo(int &type, int &layer, int &freq, int &bitrate, int &mode)
{
lt_debug("%s\n", __FUNCTION__);
type = 0;
layer = 0;
freq = 0;
bitrate = 0;
mode = 0;
#if 0
unsigned int atype;
static const int freq_mpg[] = {44100, 48000, 32000, 0};
static const int freq_ac3[] = {48000, 44100, 32000, 0};
scratchl2 i;
if (ioctl(fd, MPEG_AUD_GET_DECTYP, &atype) < 0)
perror("cAudio::getAudioInfo MPEG_AUD_GET_DECTYP");
if (ioctl(fd, MPEG_AUD_GET_STATUS, &i) < 0)
perror("cAudio::getAudioInfo MPEG_AUD_GET_STATUS");
type = atype;
#if 0
/* this does not work, some of the values are negative?? */
AMPEGStatus A;
memcpy(&A, &i.word00, sizeof(i.word00));
layer = A.audio_mpeg_layer;
mode = A.audio_mpeg_mode;
bitrate = A.audio_mpeg_bitrate;
switch(A.audio_mpeg_frequency)
#endif
/* layer and bitrate are not used anyway... */
layer = 0; //(i.word00 >> 17) & 3;
bitrate = 0; //(i.word00 >> 12) & 3;
switch (type)
{
case 0: /* MPEG */
mode = (i.word00 >> 6) & 3;
freq = freq_mpg[(i.word00 >> 10) & 3];
break;
case 1: /* AC3 */
mode = (i.word00 >> 28) & 7;
freq = freq_ac3[(i.word00 >> 16) & 3];
break;
default:
mode = 0;
freq = 0;
}
//fprintf(stderr, "type: %d layer: %d freq: %d bitrate: %d mode: %d\n", type, layer, freq, bitrate, mode);
#endif
};
void cAudio::SetSRS(int /*iq_enable*/, int /*nmgr_enable*/, int /*iq_mode*/, int /*iq_level*/)
{
lt_debug("%s\n", __FUNCTION__);
};
void cAudio::SetHdmiDD(bool enable)
{
lt_debug("%s %d\n", __func__, enable);
};
void cAudio::SetSpdifDD(bool enable)
{
lt_debug("%s %d\n", __func__, enable);
setBypassMode(!enable);
};
void cAudio::ScheduleMute(bool On)
{
lt_debug("%s %d\n", __FUNCTION__, On);
};
void cAudio::EnableAnalogOut(bool enable)
{
lt_debug("%s %d\n", __FUNCTION__, enable);
};
#define AUDIO_BYPASS_ON 0
#define AUDIO_BYPASS_OFF 1
void cAudio::setBypassMode(bool disable)
{
lt_debug("%s %d\n", __func__, disable);
int mode = disable ? AUDIO_BYPASS_OFF : AUDIO_BYPASS_ON;
if (ioctl(fd, AUDIO_SET_BYPASS_MODE, mode) < 0)
lt_info("%s AUDIO_SET_BYPASS_MODE %d: %m\n", __func__, mode);
return;
}

View File

@@ -1,98 +0,0 @@
/* public header file */
#ifndef _AUDIO_LIB_H_
#define _AUDIO_LIB_H_
#include "../common/cs_types.h"
typedef enum
{
AUDIO_SYNC_WITH_PTS,
AUDIO_NO_SYNC,
AUDIO_SYNC_AUDIO_MASTER
} AUDIO_SYNC_MODE;
typedef enum {
HDMI_ENCODED_OFF,
HDMI_ENCODED_AUTO,
HDMI_ENCODED_FORCED
} HDMI_ENCODED_MODE;
typedef enum
{
AUDIO_FMT_AUTO = 0,
AUDIO_FMT_MPEG,
AUDIO_FMT_MP3,
AUDIO_FMT_DOLBY_DIGITAL,
AUDIO_FMT_BASIC = AUDIO_FMT_DOLBY_DIGITAL,
AUDIO_FMT_AAC,
AUDIO_FMT_AAC_PLUS,
AUDIO_FMT_DD_PLUS,
AUDIO_FMT_DTS,
AUDIO_FMT_AVS,
AUDIO_FMT_MLP,
AUDIO_FMT_WMA,
AUDIO_FMT_MPG1, // TD only. For Movieplayer / cPlayback
AUDIO_FMT_ADVANCED = AUDIO_FMT_MLP
} AUDIO_FORMAT;
class cAudio
{
friend class cPlayback;
private:
int fd;
bool Muted;
int clipfd; /* for pcm playback */
int mixer_fd; /* if we are using the OSS mixer */
int mixer_num; /* oss mixer to use, if any */
AUDIO_FORMAT StreamType;
AUDIO_SYNC_MODE SyncMode;
bool started;
int volume;
void openDevice(void);
void closeDevice(void);
int do_mute(bool enable, bool remember);
void setBypassMode(bool disable);
public:
/* construct & destruct */
cAudio(void *, void *, void *);
~cAudio(void);
void *GetHandle() { return NULL; };
/* shut up */
int mute(bool remember = true) { return do_mute(true, remember); };
int unmute(bool remember = true) { return do_mute(false, remember); };
/* volume, min = 0, max = 255 */
int setVolume(unsigned int left, unsigned int right);
int getVolume(void) { return volume;}
bool getMuteStatus(void) { return Muted; };
/* start and stop audio */
int Start(void);
int Stop(void);
bool Pause(bool Pcm = true);
void SetStreamType(AUDIO_FORMAT type);
void SetSyncMode(AVSYNC_TYPE Mode);
/* select channels */
int setChannel(int channel);
int PrepareClipPlay(int uNoOfChannels, int uSampleRate, int uBitsPerSample, int bLittleEndian);
int WriteClip(unsigned char * buffer, int size);
int StopClip();
void getAudioInfo(int &type, int &layer, int& freq, int &bitrate, int &mode);
void SetSRS(int iq_enable, int nmgr_enable, int iq_mode, int iq_level);
bool IsHdmiDDSupported();
void SetHdmiDD(bool enable);
void SetSpdifDD(bool enable);
void ScheduleMute(bool On);
void EnableAnalogOut(bool enable);
};
#endif

View File

@@ -1 +0,0 @@
../libspark/cs_api.h

View File

@@ -1,523 +0,0 @@
/*
* cDemux implementation for azbox receivers (tested on azbox me and minime)
*
* derived from libtriple/dmx_td.cpp
*
* (C) 2010-2013 Stefan Seyfried
*
* 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.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include "config.h"
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <poll.h>
#include <errno.h>
#include <inttypes.h>
#include <cstring>
#include <cstdio>
#include <string>
#include "dmx_lib.h"
#include "lt_debug.h"
/* Ugh... see comment in destructor for details... */
#include "video_lib.h"
extern cVideo *videoDecoder;
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_DEMUX, this, args)
#define lt_info(args...) _lt_info(TRIPLE_DEBUG_DEMUX, this, args)
#define lt_info_c(args...) _lt_info(TRIPLE_DEBUG_DEMUX, NULL, args)
#define dmx_err(_errfmt, _errstr, _revents) do { \
uint16_t _pid = (uint16_t)-1; uint16_t _f = 0;\
if (dmx_type == DMX_PSI_CHANNEL) { \
_pid = s_flt.pid; _f = s_flt.filter.filter[0]; \
} else { \
_pid = p_flt.pid; \
}; \
lt_info("%s " _errfmt " fd:%d, ev:0x%x %s pid:0x%04hx flt:0x%02hx\n", \
__func__, _errstr, fd, _revents, DMX_T[dmx_type], _pid, _f); \
} while(0);
cDemux *videoDemux = NULL;
cDemux *audioDemux = NULL;
//cDemux *pcrDemux = NULL;
static const char *DMX_T[] = {
"DMX_INVALID",
"DMX_VIDEO",
"DMX_AUDIO",
"DMX_PES",
"DMX_PSI",
"DMX_PIP",
"DMX_TP",
"DMX_PCR"
};
/* map the device numbers. for now only demux0 is used */
static const char *devname[] = {
"/dev/dvb/adapter0/demux0",
"/dev/dvb/adapter0/demux0",
"/dev/dvb/adapter0/demux0"
};
/* uuuugly */
static int dmx_tp_count = 0;
#define MAX_TS_COUNT 8
cDemux::cDemux(int n)
{
if (n < 0 || n > 2)
{
lt_info("%s ERROR: n invalid (%d)\n", __FUNCTION__, n);
num = 0;
}
else
num = n;
fd = -1;
measure = false;
last_measure = 0;
last_data = 0;
}
cDemux::~cDemux()
{
lt_debug("%s #%d fd: %d\n", __FUNCTION__, num, fd);
Close();
/* in zapit.cpp, videoDemux is deleted after videoDecoder
* in the video watchdog, we access videoDecoder
* the thread still runs after videoDecoder has been deleted
* => set videoDecoder to NULL here to make the check in the
* watchdog thread pick this up.
* This is ugly, but it saves me from changing neutrino
*
* if the delete order in neutrino will ever be changed, this
* will blow up badly :-(
*/
if (dmx_type == DMX_VIDEO_CHANNEL)
videoDecoder = NULL;
}
bool cDemux::Open(DMX_CHANNEL_TYPE pes_type, void * /*hVideoBuffer*/, int uBufferSize)
{
int devnum = num;
int flags = O_RDWR|O_CLOEXEC;
if (fd > -1)
lt_info("%s FD ALREADY OPENED? fd = %d\n", __FUNCTION__, fd);
if (pes_type != DMX_PSI_CHANNEL)
flags |= O_NONBLOCK;
fd = open(devname[devnum], flags);
if (fd < 0)
{
lt_info("%s %s: %m\n", __FUNCTION__, devname[devnum]);
return false;
}
lt_debug("%s #%d pes_type: %s(%d), uBufferSize: %d fd: %d\n", __func__,
num, DMX_T[pes_type], pes_type, uBufferSize, fd);
dmx_type = pes_type;
#if 0
if (!pesfds.empty())
{
lt_info("%s ERROR! pesfds not empty!\n", __FUNCTION__); /* TODO: error handling */
return false;
}
int n = DMX_SOURCE_FRONT0;
if (ioctl(fd, DMX_SET_SOURCE, &n) < 0)
lt_info("%s DMX_SET_SOURCE failed!\n", __func__);
#endif
if (uBufferSize > 0)
{
/* probably uBufferSize == 0 means "use default size". TODO: find a reasonable default */
if (ioctl(fd, DMX_SET_BUFFER_SIZE, uBufferSize) < 0)
lt_info("%s DMX_SET_BUFFER_SIZE failed (%m)\n", __func__);
}
buffersize = uBufferSize;
return true;
}
void cDemux::Close(void)
{
lt_debug("%s #%d, fd = %d\n", __FUNCTION__, num, fd);
if (fd < 0)
{
lt_info("%s #%d: not open!\n", __FUNCTION__, num);
return;
}
pesfds.clear();
ioctl(fd, DMX_STOP);
close(fd);
fd = -1;
if (measure)
return;
if (dmx_type == DMX_TP_CHANNEL)
{
dmx_tp_count--;
if (dmx_tp_count < 0)
{
lt_info("%s dmx_tp_count < 0!!\n", __func__);
dmx_tp_count = 0;
}
}
}
bool cDemux::Start(bool)
{
lt_debug("%s #%d fd: %d type: %s\n", __func__, num, fd, DMX_T[dmx_type]);
if (fd < 0)
{
lt_info("%s #%d: not open!\n", __FUNCTION__, num);
return false;
}
ioctl(fd, DMX_START);
return true;
}
bool cDemux::Stop(void)
{
lt_debug("%s #%d fd: %d type: %s\n", __func__, num, fd, DMX_T[dmx_type]);
if (fd < 0)
{
lt_info("%s #%d: not open!\n", __FUNCTION__, num);
return false;
}
ioctl(fd, DMX_STOP);
return true;
}
int cDemux::Read(unsigned char *buff, int len, int timeout)
{
#if 0
if (len != 4095 && timeout != 100)
fprintf(stderr, "cDemux::%s #%d fd: %d type: %s len: %d timeout: %d\n",
__FUNCTION__, num, fd, DMX_T[dmx_type], len, timeout);
#endif
int rc;
int to = timeout;
/* using a one-dimensional array seems to avoid strange segfaults / memory corruption?? */
struct pollfd ufds[1];
ufds[0].fd = fd;
ufds[0].events = POLLIN|POLLPRI|POLLERR;
ufds[0].revents = 0;
/* hack: if the frontend loses and regains lock, the demuxer often will not
* return from read(), so as a "emergency exit" for e.g. NIT scan, set a (long)
* timeout here */
if (dmx_type == DMX_PSI_CHANNEL && timeout <= 0)
to = 60 * 1000;
if (to > 0)
{
retry:
rc = ::poll(ufds, 1, to);
if (!rc)
{
if (timeout == 0) /* we took the emergency exit */
{
dmx_err("timed out for timeout=0!, %s", "", 0);
return -1; /* this timeout is an error */
}
return 0; // timeout
}
else if (rc < 0)
{
dmx_err("poll: %s,", strerror(errno), 0)
//lt_info("%s poll: %m\n", __FUNCTION__);
/* happens, when running under gdb... */
if (errno == EINTR)
goto retry;
return -1;
}
#if 0
if (ufds.revents & POLLERR) /* POLLERR means buffer error, i.e. buffer overflow */
{
dmx_err("received %s,", "POLLERR", ufds.revents);
/* this seems to happen sometimes at recording start, without bad effects */
return 0;
}
#endif
if (ufds[0].revents & POLLHUP) /* we get POLLHUP if e.g. a too big DMX_BUFFER_SIZE was set */
{
dmx_err("received %s,", "POLLHUP", ufds[0].revents);
return -1;
}
if (!(ufds[0].revents & POLLIN)) /* we requested POLLIN but did not get it? */
{
dmx_err("received %s, please report!", "POLLIN", ufds[0].revents);
return 0;
}
}
rc = ::read(fd, buff, len);
//fprintf(stderr, "fd %d ret: %d\n", fd, rc);
if (rc < 0)
dmx_err("read: %s", strerror(errno), 0);
return rc;
}
bool cDemux::sectionFilter(unsigned short pid, const unsigned char * const filter,
const unsigned char * const mask, int len, int timeout,
const unsigned char * const negmask)
{
memset(&s_flt, 0, sizeof(s_flt));
if (len > DMX_FILTER_SIZE)
{
lt_info("%s #%d: len too long: %d, DMX_FILTER_SIZE %d\n", __func__, num, len, DMX_FILTER_SIZE);
len = DMX_FILTER_SIZE;
}
s_flt.pid = pid;
s_flt.timeout = timeout;
memcpy(s_flt.filter.filter, filter, len);
memcpy(s_flt.filter.mask, mask, len);
if (negmask != NULL)
memcpy(s_flt.filter.mode, negmask, len);
s_flt.flags = DMX_IMMEDIATE_START|DMX_CHECK_CRC;
int to = 0;
switch (filter[0]) {
case 0x00: /* program_association_section */
to = 2000;
break;
case 0x01: /* conditional_access_section */
to = 6000;
break;
case 0x02: /* program_map_section */
to = 1500;
break;
case 0x03: /* transport_stream_description_section */
to = 10000;
break;
/* 0x04 - 0x3F: reserved */
case 0x40: /* network_information_section - actual_network */
to = 10000;
break;
case 0x41: /* network_information_section - other_network */
to = 15000;
break;
case 0x42: /* service_description_section - actual_transport_stream */
to = 10000;
break;
/* 0x43 - 0x45: reserved for future use */
case 0x46: /* service_description_section - other_transport_stream */
to = 10000;
break;
/* 0x47 - 0x49: reserved for future use */
case 0x4A: /* bouquet_association_section */
to = 11000;
break;
/* 0x4B - 0x4D: reserved for future use */
case 0x4E: /* event_information_section - actual_transport_stream, present/following */
to = 2000;
break;
case 0x4F: /* event_information_section - other_transport_stream, present/following */
to = 10000;
break;
/* 0x50 - 0x5F: event_information_section - actual_transport_stream, schedule */
/* 0x60 - 0x6F: event_information_section - other_transport_stream, schedule */
case 0x70: /* time_date_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
s_flt.flags |= DMX_ONESHOT;
//s_flt.pid = 0x0014;
to = 30000;
break;
case 0x71: /* running_status_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
to = 0;
break;
case 0x72: /* stuffing_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
to = 0;
break;
case 0x73: /* time_offset_section */
s_flt.flags |= DMX_ONESHOT;
//s_flt.pid = 0x0014;
to = 30000;
break;
/* 0x74 - 0x7D: reserved for future use */
case 0x7E: /* discontinuity_information_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
to = 0;
break;
case 0x7F: /* selection_information_section */
to = 0;
break;
/* 0x80 - 0x8F: ca_message_section */
/* 0x90 - 0xFE: user defined */
/* 0xFF: reserved */
default:
break;
// return -1;
}
/* the negmask == NULL is a hack: the users of negmask are PMT-update
* and sectionsd EIT-Version change. And they really want no timeout
* if timeout == 0 instead of "default timeout" */
if (timeout == 0 && negmask == NULL)
s_flt.timeout = to;
lt_debug("%s #%d pid:0x%04hx fd:%d type:%s len:%d to:%d flags:%x flt[0]:%02x\n", __func__, num,
pid, fd, DMX_T[dmx_type], len, s_flt.timeout,s_flt.flags, s_flt.filter.filter[0]);
#if 0
fprintf(stderr,"filt: ");for(int i=0;i<DMX_FILTER_SIZE;i++)fprintf(stderr,"%02hhx ",s_flt.filter.filter[i]);fprintf(stderr,"\n");
fprintf(stderr,"mask: ");for(int i=0;i<DMX_FILTER_SIZE;i++)fprintf(stderr,"%02hhx ",s_flt.filter.mask [i]);fprintf(stderr,"\n");
fprintf(stderr,"mode: ");for(int i=0;i<DMX_FILTER_SIZE;i++)fprintf(stderr,"%02hhx ",s_flt.filter.mode [i]);fprintf(stderr,"\n");
#endif
ioctl (fd, DMX_STOP);
if (ioctl(fd, DMX_SET_FILTER, &s_flt) < 0)
return false;
ioctl(fd, DMX_START);
return true;
}
bool cDemux::pesFilter(const unsigned short pid)
{
/* allow PID 0 for web streaming e.g.
* this check originally is from tuxbox cvs but I'm not sure
* what it is good for...
if (pid <= 0x0001 && dmx_type != DMX_PCR_ONLY_CHANNEL)
return false;
*/
if ((pid >= 0x0002 && pid <= 0x000f) || pid >= 0x1fff)
return false;
lt_debug("%s #%d pid: 0x%04hx fd: %d type: %s\n", __FUNCTION__, num, pid, fd, DMX_T[dmx_type]);
memset(&p_flt, 0, sizeof(p_flt));
p_flt.pid = pid;
p_flt.output = DMX_OUT_DECODER;
p_flt.input = DMX_IN_FRONTEND;
switch (dmx_type) {
case DMX_PCR_ONLY_CHANNEL:
p_flt.pes_type = DMX_PES_PCR;
break;
case DMX_AUDIO_CHANNEL:
p_flt.pes_type = DMX_PES_AUDIO;
break;
case DMX_VIDEO_CHANNEL:
p_flt.pes_type = DMX_PES_VIDEO;
break;
case DMX_PES_CHANNEL:
p_flt.pes_type = DMX_PES_OTHER;
p_flt.output = DMX_OUT_TAP;
break;
case DMX_TP_CHANNEL:
p_flt.pes_type = DMX_PES_OTHER;
p_flt.output = DMX_OUT_TSDEMUX_TAP;
break;
default:
lt_info("%s #%d invalid dmx_type %d!\n", __func__, num, dmx_type);
return false;
}
return (ioctl(fd, DMX_SET_PES_FILTER, &p_flt) >= 0);
}
void cDemux::SetSyncMode(AVSYNC_TYPE /*mode*/)
{
lt_debug("%s #%d\n", __FUNCTION__, num);
}
void *cDemux::getBuffer()
{
lt_debug("%s #%d\n", __FUNCTION__, num);
return NULL;
}
void *cDemux::getChannel()
{
lt_debug("%s #%d\n", __FUNCTION__, num);
return NULL;
}
bool cDemux::addPid(unsigned short Pid)
{
lt_debug("%s: pid 0x%04hx\n", __func__, Pid);
pes_pids pfd;
int ret;
if (dmx_type != DMX_TP_CHANNEL)
{
lt_info("%s pes_type %s not implemented yet! pid=%hx\n", __FUNCTION__, DMX_T[dmx_type], Pid);
return false;
}
if (fd == -1)
lt_info("%s bucketfd not yet opened? pid=%hx\n", __FUNCTION__, Pid);
pfd.fd = fd; /* dummy */
pfd.pid = Pid;
pesfds.push_back(pfd);
ret = (ioctl(fd, DMX_ADD_PID, &Pid));
if (ret < 0)
lt_info("%s: DMX_ADD_PID (%m)\n", __func__);
return (ret != -1);
}
void cDemux::removePid(unsigned short Pid)
{
if (dmx_type != DMX_TP_CHANNEL)
{
lt_info("%s pes_type %s not implemented yet! pid=%hx\n", __FUNCTION__, DMX_T[dmx_type], Pid);
return;
}
for (std::vector<pes_pids>::iterator i = pesfds.begin(); i != pesfds.end(); ++i)
{
if ((*i).pid == Pid) {
lt_debug("removePid: removing demux fd %d pid 0x%04x\n", fd, Pid);
if (ioctl(fd, DMX_REMOVE_PID, Pid) < 0)
lt_info("%s: (DMX_REMOVE_PID, 0x%04hx): %m\n", __func__, Pid);
pesfds.erase(i);
return; /* TODO: what if the same PID is there multiple times */
}
}
lt_info("%s pid 0x%04x not found\n", __FUNCTION__, Pid);
}
void cDemux::getSTC(int64_t * STC)
{
/* apparently I can only get the PTS of the video decoder,
* but that's good enough for dvbsub */
lt_debug("%s #%d\n", __func__, num);
int64_t pts = 0;
if (videoDecoder)
pts = videoDecoder->GetPTS();
*STC = pts;
}
int cDemux::getUnit(void)
{
lt_debug("%s #%d\n", __FUNCTION__, num);
/* just guessed that this is the right thing to do.
right now this is only used by the CA code which is stubbed out
anyway */
return num;
}
bool cDemux::SetSource(int unit, int source)
{
lt_info_c("%s(%d, %d): not implemented yet\n", __func__, unit, source);
return true;
}
int cDemux::GetSource(int unit)
{
lt_info_c("%s(%d): not implemented yet\n", __func__, unit);
return 0;
}

View File

@@ -1 +0,0 @@
#include "dmx_lib.h"

View File

@@ -1,83 +0,0 @@
//Additional Azbox
enum key_command {
KEY_COMMAND_QUIT_ALL = 100,
KEY_COMMAND_QUIT,
KEY_COMMAND_PLAY,
KEY_COMMAND_PAUSE,
KEY_COMMAND_RESUME,
KEY_COMMAND_STOP,
KEY_COMMAND_SEEK_TO_TIME,
KEY_COMMAND_SEEK_TO_PERCENT,
KEY_COMMAND_NEXT_PICT,
KEY_COMMAND_FAST_FWD_ALL_FRAMES,
KEY_COMMAND_SLOW_FWD_ALL_FRAMES,
KEY_COMMAND_IFRAMES_FWD,
KEY_COMMAND_IFRAMES_BWD,
KEY_COMMAND_SILENT_FWD,
KEY_COMMAND_SILENT_BWD,
KEY_COMMAND_SWITCH_VIDEO,
KEY_COMMAND_SWITCH_AUDIO,
KEY_COMMAND_SWITCH_PROGRAM,
KEY_COMMAND_SWITCH_SUBS,
KEY_COMMAND_SWITCH_MULTICAST,
KEY_COMMAND_APPLY_AV_DELAY,
KEY_COMMAND_SUBS_CHANGE_DELAY,
KEY_COMMAND_SUBS_INCREASE_FONT_SIZE,
KEY_COMMAND_SUBS_DECREASE_FONT_SIZE,
KEY_COMMAND_SUBS_INCREASE_POS_Y,
KEY_COMMAND_SUBS_DECREASE_POS_Y,
KEY_COMMAND_SUBS_SWITCH_ENCODING,
KEY_COMMAND_SUBS_RESET_ALL,
KEY_COMMAND_SUBS_CHANGE_COLOR,
KEY_COMMAND_DEBUG,
KEY_COMMAND_PRINT_INFO,
KEY_COMMAND_FULL_SCREEN,
KEY_COMMAND_HALF_SCREEN,
KEY_COMMAND_INCREASE_SIZE,
KEY_COMMAND_DECREASE_SIZE,
KEY_COMMAND_MOVE_LEFT,
KEY_COMMAND_MOVE_RIGHT,
KEY_COMMAND_MOVE_TOP,
KEY_COMMAND_MOVE_BOTTOM,
KEY_COMMAND_NONLINEAR_WIDTH,
KEY_COMMAND_NONLINEAR_LEVEL,
KEY_COMMAND_SWITCH_SCALER,
KEY_COMMAND_HELP,
KEY_COMMAND_FAST_FWD_WITH_AUDIO,
KEY_COMMAND_SLOW_FWD_WITH_AUDIO,
KEY_COMMAND_PRINT_TXT,
SPECIAL_KEY_COMMAND_IFRAMES_FWD,
SPECIAL_KEY_COMMAND_IFRAMES_BWD,
SPECIAL_KEY_COMMAND_NEXT_AUDIO,
SPECIAL_KEY_COMMAND_NEXT_SUBS,
};
enum custom_command {
CUSTOM_COMMAND_GETLENGTH = 200,
CUSTOM_COMMAND_GETPOSITION,
CUSTOM_COMMAND_AUDIOGETPOSITION,
CUSTOM_COMMAND_SEEK_RELATIVE_FWD,
CUSTOM_COMMAND_SEEK_RELATIVE_BWD,
CUSTOM_COMMAND_SUBS_COUNT,
CUSTOM_COMMAND_GET_SUB_BY_ID,
CUSTOM_COMMAND_AUDIO_COUNT,
CUSTOM_COMMAND_GET_AUDIO_BY_ID,
CUSTOM_COMMAND_AUDIO_CUR_STREAM,
CUSTOM_COMMAND_SUBS_CUR_STREAM,
CUSTOM_COMMAND_TRICK_SEEK,
CUSTOM_COMMAND_SET_SUB_SIZE,
CUSTOM_COMMAND_SET_SUB_ENCODING,
CUSTOM_COMMAND_SET_SUB_POS,
};
enum event_msg {
EVENT_MSG_FDOPEN = 300,
EVENT_MSG_PLAYBACK_STARTED,
EVENT_MSG_STOPPED,
EVENT_MSG_PAUSED,
EVENT_MSG_BUFFERING,
EVENT_MSG_EOS,
EVENT_MSG_SUB_CHANGED,
};
//int fd_cmd, fd_in, fd_out, fd_event, msg;

View File

@@ -1,21 +0,0 @@
#include <unistd.h>
#include "init_lib.h"
#include "lt_debug.h"
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_INIT, NULL, args)
#define lt_info(args...) _lt_info(TRIPLE_DEBUG_INIT, NULL, args)
static bool initialized = false;
void init_td_api()
{
if (!initialized)
lt_debug_init();
lt_info("%s begin, initialized=%d, debug=0x%02x\n", __func__, (int)initialized, debuglevel);
initialized = true;
}
void shutdown_td_api()
{
lt_info("%s, initialized = %d\n", __func__, (int)initialized);
initialized = false;
}

View File

@@ -1,5 +0,0 @@
#ifndef __INIT_TD_H
#define __INIT_TD_H
void init_td_api();
void shutdown_td_api();
#endif

View File

@@ -1,521 +0,0 @@
/*
* cPlayback implementation for azbox
* this is actually just a wrapper around rmfp_player which does
* all the heavy listing
*
* based on the original aztrino implementation, but almost
* completely rewritten since then
*
* some of the methods and constants were found by stracing the
* AZPlay enigma2 plugin...
*
* (C) 2012 Stefan Seyfried
*
* 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.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <fcntl.h>
#include <sstream>
#include <pty.h>
#include <sys/poll.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <sys/wait.h>
#include "lt_debug.h"
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_PLAYBACK, this, args)
#define lt_info(args...) _lt_info(TRIPLE_DEBUG_PLAYBACK, this, args)
#define lt_info_c(args...) _lt_info(TRIPLE_DEBUG_PLAYBACK, NULL, args)
#include <proc_tools.h>
/* the file-based commands work better than the FIFOs... */
#define CMD_FILE "/tmp/rmfp.cmd2"
#define IN_FILE "/tmp/rmfp.in2"
#define OUT_FILE "/tmp/rmfp.out2"
#include "playback.h"
extern "C"{
#include "e2mruainclude.h"
}
#if 0
/* useful for debugging */
static time_t monotonic_ms(void)
{
struct timespec t;
time_t ret;
if (clock_gettime(CLOCK_MONOTONIC, &t))
{
perror("monotonic_ms clock_gettime");
return -1;
}
ret = ((t.tv_sec + 604800)& 0x01FFFFF) * 1000; /* avoid overflow */
ret += t.tv_nsec / 1000000;
return ret;
}
#endif
/* the mutex makes sure that commands are not interspersed */
bool cPlayback::rmfp_command(int cmd, int param, bool has_param, char *buf, int buflen)
{
lt_info("%s: %d %d %d %d\n", __func__, cmd, param, has_param, buflen);
bool ret = true;
int fd;
if (cmd == 222)
{
if (pthread_mutex_trylock(&rmfp_cmd_mutex))
return false;
}
else
pthread_mutex_lock(&rmfp_cmd_mutex);
unlink(OUT_FILE);
if (has_param)
{
fd = open(IN_FILE, O_WRONLY|O_CREAT|O_TRUNC, 0666);
dprintf(fd, "%i", param);
close(fd);
}
fd = open(CMD_FILE, O_WRONLY|O_CREAT|O_TRUNC, 0666);
dprintf(fd, "%i", cmd);
close(fd);
int n = 0, m = 0;
if (buflen > 0)
{
while ((fd = open(OUT_FILE, O_RDONLY)) == -1) {
if (++m > 500) { /* don't wait more than 5 seconds */
lt_info("%s: timed out waiting for %s (cmd %d par %d buflen %d\n",
__func__, OUT_FILE, cmd, param, buflen);
ret = false;
goto out;
}
usleep(10000);
}
unlink(OUT_FILE);
n = read(fd, buf, buflen);
close(fd);
/* some commands (CUSTOM_COMMAND_GET_AUDIO_BY_ID for example) actually
* return the answer in two successive writes, as we are not using the
* FIFO, we need to make sure that the file is deleted immediately, because
* rmfp_player will not overwrite it if it exists */
while ((fd = open(OUT_FILE, O_RDONLY)) == -1) {
if (++m > 10)
break;
usleep(1000);
}
if (fd > -1)
{
read(fd, buf + n, buflen - n);
unlink(OUT_FILE);
close(fd);
}
buf[buflen - 1] = '0';
}
out:
pthread_mutex_unlock(&rmfp_cmd_mutex);
if (cmd != 222) /* called tooo often :-) */
lt_info("%s: reply: '%s' ret: %d m:%d\n", __func__, buf?buf:"(none)", ret, m);
return ret;
}
/*
* runs the rmfp_player in a terminal
* just doing popen() or similar does not work because then
* the output will be buffered after starting up and we will only
* see "Playback has started..." after the player exits
*/
void cPlayback::run_rmfp()
{
lt_debug("%s: starting\n", __func__);
thread_started = true;
//Watch for the space at the end
std::string base = "rmfp_player -dram 1 -ve 1 -waitexit ";
std::string filename(mfilename);
std::string file = '"' + filename + '"';
std::string final = base + file;
if (playMode == PLAYMODE_TS && mduration != 0)
{
std::stringstream duration;
duration << (mduration /** 60000LL*/);
final = base + "-duration " + duration.str() + " " + file;
}
pid_t pid = 0;
int master;
pid = forkpty(&master, NULL, NULL, NULL);
if (! pid) {
execl("/bin/sh", "sh", "-c", final.c_str(), (char *)0);
lt_info("%s: execl returned: %m\n", __func__);
exit(0);
}
if (pid > 0) {
char *output=NULL;
size_t n = 0;
ssize_t len;
FILE *f = fdopen(master, "r");
while ((len = getline(&output, &n, f)) != -1)
{
while (len > 0)
{
len--;
if (!isspace(output[len]))
break;
output[len] = '\0';
}
lt_info("%s out: '%s'\n", __func__, output);
if (strstr(output, "Playback has started..."))
{
playing = 1;
lt_info("%s: ===================> playing = true\n", __func__);
}
else if (strstr(output, "End of file..."))
{
playing = 1; /* this can happen without "Playback has started..." */
eof_reached = true;
lt_info("%s: ===================> eof_reached = true\n", __func__);
}
}
fclose(f);
int s;
while (waitpid(pid, &s, WNOHANG) > 0) {};
if (output)
free(output);
}
lt_info("%s: terminating\n", __func__);
if (playing == 0) /* playback did not start */
playing = 2;
else
playing = 0;
eof_reached = true;
pthread_exit(NULL);
}
/* helper function to call the cpp thread loop */
void *execute_rua_thread(void *c)
{
cPlayback *obj = (cPlayback *)c;
lt_info_c("%s\n", __func__);
obj->run_rmfp();
/* free(obj); // this is most likely wrong */
return NULL;
}
//Used by Fileplay
bool cPlayback::Open(playmode_t PlayMode)
{
static const char *aPLAYMODE[] = {
"PLAYMODE_TS",
"PLAYMODE_FILE"
};
playMode = PlayMode;
if (playMode > 1)
{
lt_info("%s: PlayMode %d out of range!\n", __func__, PlayMode);
playMode = PLAYMODE_FILE;
}
lt_info("%s: mode %d (%s)\n", __func__, PlayMode, aPLAYMODE[PlayMode]);
#if 0
while (access("/tmp/continue", R_OK))
sleep(1);
#endif
char c[2] = "0";
int i = 0;
for(;;)
{
proc_get("/proc/player", c, 2);
if (c[0] != '0')
break;
i++;
if (i > 10)
{
lt_info("%s: ERROR - player is not idle after 10 seconds!\n", __func__);
open_success = false;
return false;
}
sleep(1);
}
proc_put("/proc/player", "2", 2);
lt_info("%s: /proc/player switched to '2'\n", __func__);
unlink(CMD_FILE);
unlink(IN_FILE);
unlink(OUT_FILE);
open_success = true;
return 0;
}
//Used by Fileplay
bool cPlayback::Start(char *filename, unsigned short vpid, int vtype, unsigned short _apid,
int ac3, unsigned int duration)
{
bool ret = true;
lt_info("%s: filename=%s\n", __func__, filename);
lt_info("%s: vpid=%u vtype=%d apid=%u ac3=%d duration=%i open_success=%d\n",
__func__, vpid, vtype, _apid, ac3, duration, open_success);
if (!open_success)
return false;
eof_reached = false;
//create playback path
apid = 0;
subpid = 0;
mfilename = filename;
mduration = duration;
if (pthread_create(&thread, 0, execute_rua_thread, this) != 0)
{
lt_info("%s: error creating rmfp_player thread! (out of memory?)\n", __func__);
ret = false;
}
while (! playing)
sleep(1);
if (playing == 2)
playing = 0;
return ret;
}
void cPlayback::Close(void)
{
lt_info("%s: playing %d thread_started %d\n", __func__, playing, thread_started);
if (thread_started)
{
rmfp_command(KEY_COMMAND_QUIT_ALL, 0, false, NULL, 0);
if (pthread_join(thread, NULL))
lt_info("%s: error joining rmfp thread (%m)\n", __func__);
playing = 0;
thread_started = false;
}
else
lt_info("%s: Warning: thread_started == false!\n", __func__);
if (open_success)
{
proc_put("/proc/player", "1", 2);
open_success = false;
lt_info("%s: /proc/player switched to '1'\n", __func__);
usleep(1000000);
}
}
bool cPlayback::SetAPid(unsigned short pid, int /*ac3*/)
{
lt_info("%s: pid %i\n", __func__, pid);
if (pid != apid) {
rmfp_command(KEY_COMMAND_SWITCH_AUDIO, pid, true, NULL, 0);
apid = pid;
}
return true;
}
bool cPlayback::SelectSubtitles(int pid)
{
lt_info("%s: pid %i\n", __func__, pid);
if (pid != subpid)
{
rmfp_command(KEY_COMMAND_SWITCH_SUBS, pid, true, NULL, 0);
subpid = pid;
}
return true;
}
bool cPlayback::SetSpeed(int speed)
{
lt_info("%s: playing %d speed %d\n", __func__, playing, speed);
if (!playing)
return false;
playback_speed = speed;
if (speed > 1 || speed < 0)
rmfp_command(CUSTOM_COMMAND_TRICK_SEEK, speed, true, NULL, 0);
else if (speed == 0)
rmfp_command(KEY_COMMAND_PAUSE, 0, false, NULL, 0);
else
rmfp_command(KEY_COMMAND_PLAY, 0, false, NULL, 0);
return true;
}
bool cPlayback::GetSpeed(int &/*speed*/) const
{
#if 0
lt_info("%s:\n", __func__);
speed = playback_speed;
#endif
return true;
}
// in milliseconds
bool cPlayback::GetPosition(int &position, int &duration)
{
lt_debug("%s: playing %d\n", __func__, playing);
if (eof_reached)
{
position = mduration;
duration = mduration;
return true;
}
if (!playing)
return false;
char buf[32];
/* custom command 222 returns "12345\n1234\n",
* first line is duration, second line is position */
if (! rmfp_command(222, 0, false, buf, 32))
return false;
duration = atoi(buf);
char *p = strchr(buf, '\n');
if (!p)
return false;
position = atoi(++p);
/* some mpegs return length 0... which would lead to "eof" after 10 seconds */
if (duration == 0)
duration = position + 1000;
if (playMode == PLAYMODE_TS)
{
if (position > mduration)
mduration = position + 1000;
duration = mduration;
return true;
}
return true;
}
bool cPlayback::SetPosition(int position, bool absolute)
{
lt_info("%s: pos %d abs %d playing %d\n", __func__, position, absolute, playing);
if (!playing)
return false;
int seconds = position / 1000;;
if (absolute)
{
rmfp_command(KEY_COMMAND_SEEK_TO_TIME, seconds, true, NULL, 0);
return true;
}
if (position > 0)
rmfp_command(CUSTOM_COMMAND_SEEK_RELATIVE_FWD, seconds, true, NULL, 0);
else if (position < 0)
rmfp_command(CUSTOM_COMMAND_SEEK_RELATIVE_BWD, seconds, true, NULL, 0);
return true;
}
void cPlayback::FindAllPids(uint16_t *apids, unsigned short *ac3flags, uint16_t *numpida, std::string *language)
{
lt_info("%s\n", __func__);
char buf[32];
rmfp_command(CUSTOM_COMMAND_AUDIO_COUNT, 0, false, buf, 3);
unsigned int audio_count = atoi(buf);
*numpida = audio_count;
if (audio_count > 0)
{
for (unsigned int aid = 0; aid < audio_count; aid++)
{
char streamidstring[11];
char audio_lang[21];
memset(buf, 0, sizeof(buf));
rmfp_command(CUSTOM_COMMAND_GET_AUDIO_BY_ID, aid, true, buf, 32);
memcpy(streamidstring, buf, 10);
streamidstring[10] = '\0';
memcpy(audio_lang, buf + 10, 20);
audio_lang[20] = '\0';
apids[aid] = atoi(streamidstring);
ac3flags[aid] = 0;
language[aid] = audio_lang;
lt_info("%s: #%d apid:%d lang: %s\n", __func__, aid, apids[aid], audio_lang);
}
}
}
void cPlayback::FindAllSubs(uint16_t *spids, unsigned short *supported, uint16_t *numpids, std::string *language)
{
lt_info("%s\n", __func__);
char buf[32];
rmfp_command(CUSTOM_COMMAND_SUBS_COUNT, 0, false, buf, 3);
unsigned int spu_count = atoi(buf);
*numpids = spu_count;
if (spu_count > 0)
{
for (unsigned int sid = 0; sid < spu_count; sid++)
{
char streamidstring[11];
char spu_lang[21];
memset(buf, 0, sizeof(buf));
rmfp_command(CUSTOM_COMMAND_GET_SUB_BY_ID, sid, true, buf, 32);
memcpy(streamidstring, buf, 10);
streamidstring[10] = '\0';
memcpy(spu_lang, buf + 10, 20);
spu_lang[20] = '\0';
spids[sid] = atoi(streamidstring);
language[sid] = spu_lang;
supported[sid] = 1;
lt_info("%s: #%d apid:%d lang: %s\n", __func__, sid, spids[sid], spu_lang);
}
}
//Add streamid -1 to be able to disable subtitles
*numpids = spu_count + 1;
spids[spu_count] = -1;
language[spu_count] = "Disable";
}
/* DVD support is not yet ready... */
void cPlayback::GetChapters(std::vector<int> &positions, std::vector<std::string> &titles)
{
positions.clear();
titles.clear();
}
cPlayback::cPlayback(int /*num*/)
{
lt_info("%s: constructor\n", __func__);
playing = 0;
thread_started = false;
eof_reached = false;
open_success = false;
pthread_mutex_init(&rmfp_cmd_mutex, NULL);
}
cPlayback::~cPlayback()
{
lt_info("%s\n", __func__);
pthread_mutex_destroy(&rmfp_cmd_mutex);
}

View File

@@ -1,62 +0,0 @@
#ifndef __PLAYBACK_H
#define __PLAYBACK_H
#include <string>
#include <stdint.h>
#include <vector>
typedef enum {
PLAYMODE_TS = 0,
PLAYMODE_FILE,
} playmode_t;
class cPlayback
{
private:
pthread_mutex_t rmfp_cmd_mutex;
int playing;
bool eof_reached;
int playback_speed;
playmode_t playMode;
bool open_success;
uint16_t apid;
uint16_t subpid;
char *mfilename;
int mduration;
pthread_t thread;
bool thread_started;
/* private functions */
bool rmfp_command(int cmd, int param, bool has_param, char *buf, int buflen);
public:
cPlayback(int num = 0);
~cPlayback();
void run_rmfp();
bool Open(playmode_t PlayMode);
void Close(void);
bool Start(char *filename, unsigned short vpid, int vtype, unsigned short apid,
int ac3, unsigned int duration);
bool SetAPid(unsigned short pid, int ac3);
bool SetSpeed(int speed);
bool GetSpeed(int &speed) const;
bool GetPosition(int &position, int &duration); /* pos: current time in ms, dur: file length in ms */
bool SetPosition(int position, bool absolute = false); /* position: jump in ms */
void FindAllPids(uint16_t *apids, unsigned short *ac3flags, uint16_t *numpida, std::string *language);
void FindAllSubs(uint16_t *pids, unsigned short *supported, uint16_t *numpida, std::string *language);
bool SelectSubtitles(int pid);
void GetChapters(std::vector<int> &positions, std::vector<std::string> &titles);
#if 0
// Functions that are not used by movieplayer.cpp:
bool Stop(void);
bool GetOffset(off64_t &offset);
bool IsPlaying(void) const { return playing; }
bool IsEnabled(void) const { return enabled; }
void * GetHandle(void);
void * GetDmHandle(void);
int GetCurrPlaybackSpeed(void) const { return nPlaybackSpeed; }
void PlaybackNotify (int Event, void *pData, void *pTag);
void DMNotify(int Event, void *pTsBuf, void *Tag);
#endif
};
#endif

View File

@@ -1 +0,0 @@
../libspark/pwrmngr.cpp

View File

@@ -1 +0,0 @@
../libspark/pwrmngr.h

View File

@@ -1,635 +0,0 @@
/*
* (C) 2002-2003 Andreas Oberritter <obi@tuxbox.org>
* (C) 2010-2012 Stefan Seyfried
*
* 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.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, 51 Franklin Street, Suite 500 Boston, MA 02110-1335 USA
*/
#include <fcntl.h>
#include <sys/ioctl.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <utime.h>
#include <errno.h>
#include <ctype.h>
#include <cstring>
#include <cstdio>
#include <cstdlib>
#include <pthread.h>
#include <linux/types.h>
#include <linux/dvb/video.h>
#include <proc_tools.h>
#include "video_lib.h"
#define VIDEO_DEVICE "/dev/dvb/adapter0/video0"
#include "lt_debug.h"
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_VIDEO, this, args)
#define lt_info(args...) _lt_info(TRIPLE_DEBUG_VIDEO, this, args)
#define lt_debug_c(args...) _lt_debug(TRIPLE_DEBUG_VIDEO, NULL, args)
#define lt_info_c(args...) _lt_info(TRIPLE_DEBUG_VIDEO, NULL, args)
#define fop(cmd, args...) ({ \
int _r; \
if (fd >= 0) { \
if ((_r = ::cmd(fd, args)) < 0) \
lt_info(#cmd"(fd, "#args")\n"); \
else \
lt_debug(#cmd"(fd, "#args")\n");\
} \
else { _r = fd; } \
_r; \
})
cVideo * videoDecoder = NULL;
int system_rev = 0;
static bool stillpicture = false;
static unsigned char *blank_data;
static ssize_t blank_size;
static pthread_mutex_t stillp_mutex = PTHREAD_MUTEX_INITIALIZER;
/* prototype */
static void show_iframe(int fd, unsigned char *iframe, size_t st_size);
#define VIDEO_STREAMTYPE_MPEG2 0
#define VIDEO_STREAMTYPE_MPEG4_H264 1
#define VIDEO_STREAMTYPE_VC1 3
#define VIDEO_STREAMTYPE_MPEG4_Part2 4
#define VIDEO_STREAMTYPE_VC1_SM 5
#define VIDEO_STREAMTYPE_MPEG1 6
cVideo::cVideo(int, void *, void *, unsigned int)
{
lt_debug("%s\n", __FUNCTION__);
//croppingMode = VID_DISPMODE_NORM;
//outputformat = VID_OUTFMT_RGBC_SVIDEO;
scartvoltage = -1;
video_standby = 0;
fd = -1;
const char *blankname = "/share/tuxbox/blank_576.mpg";
int blankfd;
struct stat st;
blank_data = NULL; /* initialize */
blank_size = 0;
blankfd = open(blankname, O_RDONLY|O_CLOEXEC);
if (blankfd < 0)
lt_info("%s cannot open %s: %m", __func__, blankname);
else
{
if (fstat(blankfd, &st) != -1 && st.st_size > 0)
{
blank_size = st.st_size;
blank_data = (unsigned char *)malloc(blank_size);
if (! blank_data)
lt_info("%s malloc failed (%m)\n", __func__);
else if (read(blankfd, blank_data, blank_size) != blank_size)
{
lt_info("%s short read (%m)\n", __func__);
free(blank_data); /* don't leak... */
blank_data = NULL;
}
}
close(blankfd);
}
openDevice();
Pig(-1, -1, -1, -1);
}
cVideo::~cVideo(void)
{
closeDevice();
if (blank_data)
free(blank_data);
}
void cVideo::openDevice(void)
{
int n = 0;
lt_debug("%s\n", __func__);
/* todo: this fd checking is racy, should be protected by a lock */
if (fd != -1) /* already open */
return;
retry:
if ((fd = open(VIDEO_DEVICE, O_RDWR|O_CLOEXEC)) < 0)
{
if (errno == EBUSY)
{
/* sometimes we get busy quickly after close() */
usleep(50000);
if (++n < 10)
goto retry;
}
lt_info("%s cannot open %s: %m, retries %d\n", __func__, VIDEO_DEVICE, n);
}
playstate = VIDEO_STOPPED;
}
void cVideo::closeDevice(void)
{
lt_debug("%s\n", __func__);
if (fd >= 0)
close(fd);
fd = -1;
playstate = VIDEO_STOPPED;
}
int cVideo::setAspectRatio(int aspect, int mode)
{
static const char *a[] = { "n/a", "4:3", "14:9", "16:9" };
/* { "panscan", "letterbox", "fullscreen", "14:9", "(unset)" } */
static const char *m[] = { "1", "2", "0", "1", "(unset)" };
int n;
lt_debug("%s: a:%d m:%d %s\n", __func__, aspect, mode, m[(mode < 0||mode > 3) ? 4 : mode]);
if (aspect > 3 || aspect == 0)
lt_info("%s: invalid aspect: %d\n", __func__, aspect);
else if (aspect > 0) /* -1 == don't set */
{
lt_debug("%s: /proc/stb/video/aspect -> %s\n", __func__, a[aspect]);
n = proc_put("/proc/stb/video/aspect", a[aspect], strlen(a[aspect]));
if (n < 0)
lt_info("%s: proc_put /proc/stb/video/aspect (%m)\n", __func__);
}
if (mode == -1)
return 0;
lt_debug("%s: /proc/scalingmode -> %s\n", __func__, m[mode]);
n = proc_put("/proc/scalingmode", m[mode], strlen(m[mode]));
if (n < 0)
return 1;
return 0;
}
int cVideo::getAspectRatio(void)
{
video_size_t s;
if (fd == -1)
{
/* in movieplayer mode, fd is not opened -> fall back to procfs */
int n = proc_get_hex("/proc/stb/vmpeg/0/aspect");
return n * 2 + 1;
}
if (fop(ioctl, VIDEO_GET_SIZE, &s) < 0)
{
lt_info("%s: VIDEO_GET_SIZE %m\n", __func__);
return -1;
}
lt_debug("%s: %d\n", __func__, s.aspect_ratio);
return s.aspect_ratio * 2 + 1;
}
int cVideo::setCroppingMode(int /*vidDispMode_t format*/)
{
return 0;
#if 0
croppingMode = format;
const char *format_string[] = { "norm", "letterbox", "unknown", "mode_1_2", "mode_1_4", "mode_2x", "scale", "disexp" };
const char *f;
if (format >= VID_DISPMODE_NORM && format <= VID_DISPMODE_DISEXP)
f = format_string[format];
else
f = "ILLEGAL format!";
lt_debug("%s(%d) => %s\n", __FUNCTION__, format, f);
return fop(ioctl, MPEG_VID_SET_DISPMODE, format);
#endif
}
int cVideo::Start(void * /*PcrChannel*/, unsigned short /*PcrPid*/, unsigned short /*VideoPid*/, void * /*hChannel*/)
{
lt_debug("%s playstate=%d\n", __FUNCTION__, playstate);
#if 0
if (playstate == VIDEO_PLAYING)
return 0;
if (playstate == VIDEO_FREEZED) /* in theory better, but not in practice :-) */
fop(ioctl, MPEG_VID_CONTINUE);
#endif
playstate = VIDEO_PLAYING;
return fop(ioctl, VIDEO_PLAY);
}
int cVideo::Stop(bool blank)
{
lt_debug("%s(%d)\n", __FUNCTION__, blank);
if (stillpicture)
{
lt_debug("%s: stillpicture == true\n", __func__);
return -1;
}
/* blank parameter seems to not work on VIDEO_STOP */
if (blank)
setBlank(1);
playstate = blank ? VIDEO_STOPPED : VIDEO_FREEZED;
return fop(ioctl, VIDEO_STOP, blank ? 1 : 0);
}
int cVideo::setBlank(int)
{
pthread_mutex_lock(&stillp_mutex);
if (blank_data)
show_iframe(fd, blank_data, blank_size);
pthread_mutex_unlock(&stillp_mutex);
return 1;
}
int cVideo::SetVideoSystem(int video_system, bool remember)
{
lt_debug("%s(%d, %d)\n", __func__, video_system, remember);
char current[32];
static const char *modes[] = {
"480i", // VIDEO_STD_NTSC
"576i", // VIDEO_STD_SECAM
"576i", // VIDEO_STD_PAL
"480p", // VIDEO_STD_480P
"576p", // VIDEO_STD_576P
"720p60", // VIDEO_STD_720P60
"1080i60", // VIDEO_STD_1080I60
"720p50", // VIDEO_STD_720P50
"1080i50", // VIDEO_STD_1080I50
"1080p30", // VIDEO_STD_1080P30
"1080p24", // VIDEO_STD_1080P24
"1080p25", // VIDEO_STD_1080P25
"720p50", // VIDEO_STD_AUTO -> not implemented
"1080p50" // VIDEO_STD_1080P50 -> SPARK only
};
if (video_system > VIDEO_STD_MAX)
{
lt_info("%s: video_system (%d) > VIDEO_STD_MAX (%d)\n", __func__, video_system, VIDEO_STD_MAX);
return -1;
}
int ret = proc_get("/proc/stb/video/videomode", current, 32);
if (strcmp(current, modes[video_system]) == 0)
{
lt_info("%s: video_system %d (%s) already set, skipping\n", __func__, video_system, current);
return 0;
}
lt_info("%s: old: '%s' new: '%s'\n", __func__, current, modes[video_system]);
ret = proc_put("/proc/stb/video/videomode", modes[video_system],strlen(modes[video_system]));
return ret;
}
int cVideo::getPlayState(void)
{
return playstate;
}
void cVideo::SetVideoMode(analog_mode_t mode)
{
lt_debug("%s(%d)\n", __func__, mode);
if (!(mode & ANALOG_SCART_MASK))
{
lt_debug("%s: non-SCART mode ignored\n", __func__);
return;
}
const char *m;
switch(mode)
{
case ANALOG_SD_YPRPB_SCART:
m = "yuv";
break;
case ANALOG_SD_RGB_SCART:
m = "rgb";
break;
default:
lt_info("%s unknown mode %d\n", __func__, mode);
m = "rgb";
break; /* default to rgb */
}
proc_put("/proc/stb/avs/0/colorformat", m, strlen(m));
}
void cVideo::ShowPicture(const char * fname)
{
lt_debug("%s(%s)\n", __func__, fname);
char destname[512];
char cmd[512];
char *p;
int mfd;
unsigned char *iframe;
struct stat st, st2;
if (video_standby)
{
/* does not work and the driver does not seem to like it */
lt_info("%s: video_standby == true\n", __func__);
return;
}
if (fd < 0)
{
lt_info("%s: decoder not opened?\n", __func__);
return;
}
strcpy(destname, "/var/cache");
if (stat(fname, &st2))
{
lt_info("%s: could not stat %s (%m)\n", __func__, fname);
return;
}
mkdir(destname, 0755);
/* the cache filename is (example for /share/tuxbox/neutrino/icons/radiomode.jpg):
/var/cache/share.tuxbox.neutrino.icons.radiomode.jpg.m2v
build that filename first...
TODO: this could cause name clashes, use a hashing function instead... */
strcat(destname, fname);
p = &destname[strlen("/var/cache/")];
while ((p = strchr(p, '/')) != NULL)
*p = '.';
strcat(destname, ".m2v");
/* ...then check if it exists already... */
if (stat(destname, &st) || (st.st_mtime != st2.st_mtime) || (st.st_size == 0))
{
struct utimbuf u;
u.actime = time(NULL);
u.modtime = st2.st_mtime;
/* it does not exist or has a different date, so call ffmpeg... */
sprintf(cmd, "ffmpeg -y -f mjpeg -i '%s' -s 1280x720 '%s' </dev/null",
fname, destname);
system(cmd); /* TODO: use libavcodec to directly convert it */
utime(destname, &u);
}
/* the mutex is a workaround: setBlank is apparently called from
a differnt thread and takes slightly longer, so that the decoder
was blanked immediately after displaying the image, which is not
what we want. the mutex ensures proper ordering. */
pthread_mutex_lock(&stillp_mutex);
mfd = open(destname, O_RDONLY|O_CLOEXEC);
if (mfd < 0)
{
lt_info("%s cannot open %s: %m", __func__, destname);
goto out;
}
fstat(mfd, &st);
stillpicture = true;
iframe = (unsigned char *)malloc(st.st_size);
if (! iframe)
{
lt_info("%s: malloc failed (%m)\n", __func__);
goto out;
}
read(mfd, iframe, st.st_size);
show_iframe(fd, iframe, st.st_size);
free(iframe);
out:
close(mfd);
pthread_mutex_unlock(&stillp_mutex);
return;
}
void cVideo::StopPicture()
{
lt_debug("%s\n", __func__);
stillpicture = false;
}
void cVideo::Standby(unsigned int bOn)
{
lt_debug("%s(%d)\n", __func__, bOn);
if (bOn)
{
closeDevice();
proc_put("/proc/stb/avs/0/input", "aux", 4);
}
else
{
proc_put("/proc/stb/avs/0/input", "encoder", 8);
openDevice();
}
video_standby = bOn;
}
int cVideo::getBlank(void)
{
int ret = proc_get_hex("/proc/stb/vmpeg/0/xres");
lt_debug("%s => %d\n", __func__, !ret);
return !ret;
}
/* this function is regularly called, checks if video parameters
changed and triggers appropriate actions */
void cVideo::VideoParamWatchdog(void)
{
#if 0
static unsigned int _v_info = (unsigned int) -1;
unsigned int v_info;
if (fd == -1)
return;
ioctl(fd, MPEG_VID_GET_V_INFO_RAW, &v_info);
if (_v_info != v_info)
{
lt_debug("%s params changed. old: %08x new: %08x\n", __FUNCTION__, _v_info, v_info);
setAspectRatio(-1, -1);
}
_v_info = v_info;
#endif
}
void cVideo::Pig(int x, int y, int w, int h, int osd_w, int osd_h)
{
char buffer[64];
int _x, _y, _w, _h;
/* the target "coordinates" seem to be in a PAL sized plane
* TODO: check this in the driver sources */
int xres = 720; /* proc_get_hex("/proc/stb/vmpeg/0/xres") */
int yres = 576; /* proc_get_hex("/proc/stb/vmpeg/0/yres") */
lt_debug("%s: x:%d y:%d w:%d h:%d ow:%d oh:%d\n", __func__, x, y, w, h, osd_w, osd_h);
if (x == -1 && y == -1 && w == -1 && h == -1)
{
_w = xres;
_h = yres;
_x = 0;
_y = 0;
}
else
{
_x = x * xres / osd_w;
_w = w * xres / osd_w;
_y = y * yres / osd_h;
_h = h * yres / osd_h;
}
lt_debug("%s: x:%d y:%d w:%d h:%d xr:%d yr:%d\n", __func__, _x, _y, _w, _h, xres, yres);
sprintf(buffer, "%x", _x);
proc_put("/proc/stb/vmpeg/0/dst_left", buffer, strlen(buffer));
sprintf(buffer, "%x", _y);
proc_put("/proc/stb/vmpeg/0/dst_top", buffer, strlen(buffer));
sprintf(buffer, "%x", _w);
proc_put("/proc/stb/vmpeg/0/dst_width", buffer, strlen(buffer));
sprintf(buffer, "%x", _h);
proc_put("/proc/stb/vmpeg/0/dst_height", buffer, strlen(buffer));
}
static inline int rate2csapi(int rate)
{
switch (rate)
{
/* no idea how the float values are represented by the driver */
case 23976:
return 0;
case 24:
return 1;
case 25:
return 2;
case 29976:
return 3;
case 30:
return 4;
case 50:
return 5;
case 50940:
return 6;
case 60:
return 7;
default:
break;
}
return -1;
}
void cVideo::getPictureInfo(int &width, int &height, int &rate)
{
video_size_t s;
int r;
if (fd == -1)
{
/* in movieplayer mode, fd is not opened -> fall back to procfs */
r = proc_get_hex("/proc/stb/vmpeg/0/framerate");
width = proc_get_hex("/proc/stb/vmpeg/0/xres");
height = proc_get_hex("/proc/stb/vmpeg/0/yres");
rate = rate2csapi(r);
return;
}
ioctl(fd, VIDEO_GET_SIZE, &s);
ioctl(fd, VIDEO_GET_FRAME_RATE, &r);
rate = rate2csapi(r);
height = s.h;
width = s.w;
lt_debug("%s: rate: %d, width: %d height: %d\n", __func__, rate, width, height);
}
void cVideo::SetSyncMode(AVSYNC_TYPE mode)
{
lt_debug("%s %d\n", __func__, mode);
/*
* { 0, LOCALE_OPTIONS_OFF },
* { 1, LOCALE_OPTIONS_ON },
* { 2, LOCALE_AUDIOMENU_AVSYNC_AM }
*/
#if 0
switch(Mode)
{
case 0:
ioctl(fd, MPEG_VID_SYNC_OFF);
break;
case 1:
ioctl(fd, MPEG_VID_SYNC_ON, VID_SYNC_VID);
break;
default:
ioctl(fd, MPEG_VID_SYNC_ON, VID_SYNC_AUD);
break;
}
#endif
};
int cVideo::SetStreamType(VIDEO_FORMAT type)
{
static const char *VF[] = {
"VIDEO_FORMAT_MPEG2",
"VIDEO_FORMAT_MPEG4",
"VIDEO_FORMAT_VC1",
"VIDEO_FORMAT_JPEG",
"VIDEO_FORMAT_GIF",
"VIDEO_FORMAT_PNG"
};
int t;
lt_debug("%s type=%s\n", __FUNCTION__, VF[type]);
switch (type)
{
case VIDEO_FORMAT_MPEG4:
t = VIDEO_STREAMTYPE_MPEG4_H264;
break;
case VIDEO_FORMAT_VC1:
t = VIDEO_STREAMTYPE_VC1;
break;
case VIDEO_FORMAT_MPEG2:
default:
t = VIDEO_STREAMTYPE_MPEG2;
break;
}
if (ioctl(fd, VIDEO_SET_STREAMTYPE, t) < 0)
lt_info("%s VIDEO_SET_STREAMTYPE(%d) failed: %m\n", __func__, t);
return 0;
}
int64_t cVideo::GetPTS(void)
{
int64_t pts = 0;
if (ioctl(fd, VIDEO_GET_PTS, &pts) < 0)
lt_info("%s: GET_PTS failed (%m)\n", __func__);
return pts;
}
static void show_iframe(int fd, unsigned char *iframe, size_t st_size)
{
static const unsigned char pes_header[] = { 0, 0, 1, 0xE0, 0, 0, 0x80, 0x80, 5, 0x21, 0, 1, 0, 1};
static const unsigned char seq_end[] = { 0x00, 0x00, 0x01, 0xB7 };
unsigned char stuffing[128];
bool seq_end_avail = false;
size_t pos = 0;
int count = 7;
if (ioctl(fd, VIDEO_SET_FORMAT, VIDEO_FORMAT_16_9) < 0)
lt_info_c("%s: VIDEO_SET_FORMAT failed (%m)\n", __func__);
ioctl(fd, VIDEO_SET_STREAMTYPE, VIDEO_FORMAT_MPEG2);
ioctl(fd, VIDEO_SELECT_SOURCE, VIDEO_SOURCE_MEMORY);
ioctl(fd, VIDEO_PLAY);
ioctl(fd, VIDEO_CONTINUE);
ioctl(fd, VIDEO_CLEAR_BUFFER);
while (pos <= (st_size-4) && !(seq_end_avail = (!iframe[pos] && !iframe[pos+1] && iframe[pos+2] == 1 && iframe[pos+3] == 0xB7)))
++pos;
while (count--)
{
if ((iframe[3] >> 4) != 0xE) // no pes header
write(fd, pes_header, sizeof(pes_header));
else
iframe[4] = iframe[5] = 0x00;
write(fd, iframe, st_size);
usleep(8000);
}
if (!seq_end_avail)
write(fd, seq_end, sizeof(seq_end));
memset(stuffing, 0, sizeof(stuffing));
for (count = 0; count < 8192 / (int)sizeof(stuffing); count++)
write(fd, stuffing, sizeof(stuffing));
ioctl(fd, VIDEO_STOP, 0);
ioctl(fd, VIDEO_SELECT_SOURCE, VIDEO_SOURCE_DEMUX);
}
void cVideo::SetDemux(cDemux *)
{
lt_debug("%s: not implemented yet\n", __func__);
}

View File

@@ -1,196 +0,0 @@
#ifndef _VIDEO_TD_H
#define _VIDEO_TD_H
#include <linux/dvb/video.h>
#include "../common/cs_types.h"
#include "dmx_lib.h"
typedef enum {
ANALOG_SD_RGB_CINCH = 0x00,
ANALOG_SD_YPRPB_CINCH,
ANALOG_HD_RGB_CINCH,
ANALOG_HD_YPRPB_CINCH,
ANALOG_SD_RGB_SCART = 0x10,
ANALOG_SD_YPRPB_SCART,
ANALOG_HD_RGB_SCART,
ANALOG_HD_YPRPB_SCART,
ANALOG_SCART_MASK = 0x10
} analog_mode_t;
typedef enum {
VIDEO_FORMAT_MPEG2 = 0,
VIDEO_FORMAT_MPEG4,
VIDEO_FORMAT_VC1,
VIDEO_FORMAT_JPEG,
VIDEO_FORMAT_GIF,
VIDEO_FORMAT_PNG
} VIDEO_FORMAT;
typedef enum {
VIDEO_SD = 0,
VIDEO_HD,
VIDEO_120x60i,
VIDEO_320x240i,
VIDEO_1440x800i,
VIDEO_360x288i
} VIDEO_DEFINITION;
typedef enum {
VIDEO_FRAME_RATE_23_976 = 0,
VIDEO_FRAME_RATE_24,
VIDEO_FRAME_RATE_25,
VIDEO_FRAME_RATE_29_97,
VIDEO_FRAME_RATE_30,
VIDEO_FRAME_RATE_50,
VIDEO_FRAME_RATE_59_94,
VIDEO_FRAME_RATE_60
} VIDEO_FRAME_RATE;
typedef enum {
DISPLAY_AR_1_1,
DISPLAY_AR_4_3,
DISPLAY_AR_14_9,
DISPLAY_AR_16_9,
DISPLAY_AR_20_9,
DISPLAY_AR_RAW,
} DISPLAY_AR;
typedef enum {
DISPLAY_AR_MODE_PANSCAN = 0,
DISPLAY_AR_MODE_LETTERBOX,
DISPLAY_AR_MODE_NONE,
DISPLAY_AR_MODE_PANSCAN2
} DISPLAY_AR_MODE;
typedef enum {
VIDEO_DB_DR_NEITHER = 0,
VIDEO_DB_ON,
VIDEO_DB_DR_BOTH
} VIDEO_DB_DR;
typedef enum {
VIDEO_PLAY_STILL = 0,
VIDEO_PLAY_CLIP,
VIDEO_PLAY_TRICK,
VIDEO_PLAY_MOTION,
VIDEO_PLAY_MOTION_NO_SYNC
} VIDEO_PLAY_MODE;
typedef enum {
VIDEO_STD_NTSC,
VIDEO_STD_SECAM,
VIDEO_STD_PAL,
VIDEO_STD_480P,
VIDEO_STD_576P,
VIDEO_STD_720P60,
VIDEO_STD_1080I60,
VIDEO_STD_720P50,
VIDEO_STD_1080I50,
VIDEO_STD_1080P30,
VIDEO_STD_1080P24,
VIDEO_STD_1080P25,
VIDEO_STD_AUTO,
VIDEO_STD_1080P50, /* SPARK only */
VIDEO_STD_MAX
} VIDEO_STD;
/* not used, for dummy functions */
typedef enum {
VIDEO_HDMI_CEC_MODE_OFF = 0,
VIDEO_HDMI_CEC_MODE_TUNER,
VIDEO_HDMI_CEC_MODE_RECORDER
} VIDEO_HDMI_CEC_MODE;
typedef enum
{
VIDEO_CONTROL_BRIGHTNESS = 0,
VIDEO_CONTROL_CONTRAST,
VIDEO_CONTROL_SATURATION,
VIDEO_CONTROL_HUE,
VIDEO_CONTROL_SHARPNESS,
VIDEO_CONTROL_MAX = VIDEO_CONTROL_SHARPNESS
} VIDEO_CONTROL;
class cVideo
{
friend class cDemux;
friend class cPlayback;
private:
/* video device */
int fd;
/* apparently we cannot query the driver's state
=> remember it */
video_play_state_t playstate;
int /*vidDispMode_t*/ croppingMode;
int /*vidOutFmt_t*/ outputformat;
int scartvoltage;
VIDEO_FORMAT StreamType;
VIDEO_DEFINITION VideoDefinition;
DISPLAY_AR DisplayAR;
VIDEO_PLAY_MODE SyncMode;
DISPLAY_AR_MODE ARMode;
VIDEO_DB_DR eDbDr;
DISPLAY_AR PictureAR;
VIDEO_FRAME_RATE FrameRate;
int video_standby;
int64_t GetPTS(void);
void openDevice(void);
void closeDevice(void);
public:
/* constructor & destructor */
cVideo(int mode, void *, void *, unsigned int unit = 0);
~cVideo(void);
void * GetTVEnc() { return NULL; };
void * GetTVEncSD() { return NULL; };
/* aspect ratio */
int getAspectRatio(void);
void getPictureInfo(int &width, int &height, int &rate);
int setAspectRatio(int aspect, int mode);
/* cropping mode */
int setCroppingMode(int x = 0 /*vidDispMode_t x = VID_DISPMODE_NORM*/);
/* get play state */
int getPlayState(void);
/* blank on freeze */
int getBlank(void);
int setBlank(int enable);
/* change video play state. Parameters are all unused. */
int Start(void *PcrChannel = NULL, unsigned short PcrPid = 0, unsigned short VideoPid = 0, void *x = NULL);
int Stop(bool blank = true);
bool Pause(void);
/* set video_system */
int SetVideoSystem(int video_system, bool remember = true);
int SetStreamType(VIDEO_FORMAT type);
void SetSyncMode(AVSYNC_TYPE mode);
bool SetCECMode(VIDEO_HDMI_CEC_MODE) { return true; };
void SetCECAutoView(bool) { return; };
void SetCECAutoStandby(bool) { return; };
void ShowPicture(const char * fname);
void StopPicture();
void Standby(unsigned int bOn);
void Pig(int x, int y, int w, int h, int osd_w = 1064, int osd_h = 600);
void SetControl(int, int) { return; };
void VideoParamWatchdog(void);
void setContrast(int val);
void SetVideoMode(analog_mode_t mode);
void SetDBDR(int) { return; };
void SetAudioHandle(void *) { return; };
void SetAutoModes(int [VIDEO_STD_MAX]) { return; };
int OpenVBI(int) { return 0; };
int CloseVBI(void) { return 0; };
int StartVBI(unsigned short) { return 0; };
int StopVBI(void) { return 0; };
void SetDemux(cDemux *dmx);
};
#endif

View File

@@ -1,33 +1,62 @@
noinst_LTLIBRARIES = libcommon.la
AM_CXXFLAGS = -fno-rtti -fno-exceptions -fno-strict-aliasing
AM_CXXFLAGS += \
-I $(top_srcdir)/include
AM_LDFLAGS = -lpthread
if BOXTYPE_DUCKBOX
AM_CXXFLAGS += \
-I $(top_srcdir)/include \
-I $(top_srcdir)/libdvbci
endif
if BOXTYPE_ARMBOX
AM_CXXFLAGS += \
-I $(top_srcdir)/include \
-I $(top_srcdir)/libdvbci
endif
if BOXTYPE_MIPSBOX
AM_CXXFLAGS += \
-I $(top_srcdir)/libdvbci
endif
if BOXTYPE_MIPSBOX
libcommon_la_SOURCES = \
ca_ci.cpp
else
if BOXTYPE_DUCKBOX
libcommon_la_SOURCES = \
ca_ci.cpp
else
if BOXTYPE_ARMBOX
if BOXMODEL_HD60
libcommon_la_SOURCES = \
ca.cpp
else
if BOXMODEL_OSMIO4K
libcommon_la_SOURCES = \
ca.cpp
else
if BOXMODEL_OSMIO4KPLUS
libcommon_la_SOURCES = \
ca.cpp
else
libcommon_la_SOURCES = \
ca_ci.cpp
endif
endif
endif
else
libcommon_la_SOURCES = \
ca.cpp
endif
endif
endif
libcommon_la_SOURCES += \
lt_debug.cpp \
proc_tools.c
hal_debug.cpp \
proc_tools.c \
pwrmngr.cpp \
version_hal.cpp

View File

@@ -1,8 +1,8 @@
#include <stdio.h>
#include "ca.h"
#include "lt_debug.h"
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_CA, this, args)
#include "ca_hal.h"
#include "hal_debug.h"
#define hal_debug(args...) _hal_debug(HAL_DEBUG_CA, this, args)
static cCA *inst = NULL;
@@ -10,17 +10,17 @@ static cCA *inst = NULL;
/* those are all dummies for now.. */
cCA::cCA(void)
{
lt_debug("%s\n", __FUNCTION__);
hal_debug("%s\n", __FUNCTION__);
}
cCA::~cCA()
{
lt_debug("%s\n", __FUNCTION__);
hal_debug("%s\n", __FUNCTION__);
}
cCA *cCA::GetInstance()
{
_lt_debug(TRIPLE_DEBUG_CA, NULL, "%s\n", __FUNCTION__);
_hal_debug(HAL_DEBUG_CA, NULL, "%s\n", __FUNCTION__);
if (inst == NULL)
inst = new cCA();
@@ -29,82 +29,82 @@ cCA *cCA::GetInstance()
void cCA::MenuEnter(enum CA_SLOT_TYPE, uint32_t p)
{
lt_debug("%s param:%d\n", __FUNCTION__, (int)p);
hal_debug("%s param:%d\n", __FUNCTION__, (int)p);
}
void cCA::MenuAnswer(enum CA_SLOT_TYPE, uint32_t p, uint32_t /*choice*/)
{
lt_debug("%s param:%d\n", __FUNCTION__, (int)p);
hal_debug("%s param:%d\n", __FUNCTION__, (int)p);
}
void cCA::InputAnswer(enum CA_SLOT_TYPE, uint32_t p, uint8_t * /*Data*/, int /*Len*/)
{
lt_debug("%s param:%d\n", __FUNCTION__, (int)p);
hal_debug("%s param:%d\n", __FUNCTION__, (int)p);
}
void cCA::MenuClose(enum CA_SLOT_TYPE, uint32_t p)
{
lt_debug("%s param:%d\n", __FUNCTION__, (int)p);
hal_debug("%s param:%d\n", __FUNCTION__, (int)p);
}
uint32_t cCA::GetNumberCISlots(void)
{
lt_debug("%s\n", __FUNCTION__);
hal_debug("%s\n", __FUNCTION__);
return 0;
}
uint32_t cCA::GetNumberSmartCardSlots(void)
{
lt_debug("%s\n", __FUNCTION__);
hal_debug("%s\n", __FUNCTION__);
return 0;
}
void cCA::ModuleName(enum CA_SLOT_TYPE, uint32_t p, char * /*Name*/)
{
/* TODO: waht to do with *Name? */
lt_debug("%s param:%d\n", __FUNCTION__, (int)p);
hal_debug("%s param:%d\n", __FUNCTION__, (int)p);
}
bool cCA::ModulePresent(enum CA_SLOT_TYPE, uint32_t p)
{
lt_debug("%s param:%d\n", __FUNCTION__, (int)p);
hal_debug("%s param:%d\n", __FUNCTION__, (int)p);
return false;
}
void cCA::ModuleReset(enum CA_SLOT_TYPE, uint32_t p)
{
lt_debug("%s param:%d\n", __FUNCTION__, (int)p);
hal_debug("%s param:%d\n", __FUNCTION__, (int)p);
}
bool cCA::SendPMT(int, unsigned char *, int, CA_SLOT_TYPE)
{
lt_debug("%s\n", __FUNCTION__);
hal_debug("%s\n", __FUNCTION__);
return true;
}
bool cCA::SendMessage(const CA_MESSAGE *)
{
lt_debug("%s\n", __FUNCTION__);
hal_debug("%s\n", __FUNCTION__);
return true;
}
bool cCA::Start(void)
{
lt_debug("%s\n", __FUNCTION__);
hal_debug("%s\n", __FUNCTION__);
return true;
}
void cCA::Stop(void)
{
lt_debug("%s\n", __FUNCTION__);
hal_debug("%s\n", __FUNCTION__);
}
void cCA::Ready(bool p)
{
lt_debug("%s param:%d\n", __FUNCTION__, (int)p);
hal_debug("%s param:%d\n", __FUNCTION__, (int)p);
}
void cCA::SetInitMask(enum CA_INIT_MASK p)
{
lt_debug("%s param:%d\n", __FUNCTION__, (int)p);
hal_debug("%s param:%d\n", __FUNCTION__, (int)p);
}

View File

@@ -17,7 +17,7 @@
#include <queue>
#include "ca_ci.h"
#include "lt_debug.h"
#include "hal_debug.h"
#include <cs_api.h>
#include <hardware_caps.h>
@@ -34,15 +34,16 @@
#define tsb_debug 0
#define wd_debug 0
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_CA, this, args)
#define hal_debug(args...) _hal_debug(HAL_DEBUG_CA, this, args)
static const char * FILENAME = "[ca_ci]";
#if HAVE_DUCKBOX_HARDWARE
const char ci_path[] = "/dev/dvb/adapter0/ci%d";
ca_slot_info_t info;
#endif
#if HAVE_ARM_HARDWARE
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
const char ci_path[] = "/dev/ci%d";
static int last_source = -1;
#endif
static bool checkLiveSlot = false;
static bool CertChecked = false;
@@ -55,7 +56,11 @@ static cCA* pcCAInstance = NULL;
/* nur diese Message wird vom CI aus neutrinoMessages.h benutzt */
/* für den CamMsgHandler, darum hier einfach mal definiert */
/* die Feinheiten werden ja in CA_MESSAGE verpackt */
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
uintptr_t EVT_CA_MESSAGE = 0x80000000 + 60;
#else
uint32_t EVT_CA_MESSAGE = 0x80000000 + 60;
#endif
static cs_messenger cam_messenger = NULL;
@@ -190,7 +195,7 @@ eData waitData(int fd, unsigned char* buffer, int* len)
else if (retval == 0)
{
#if wd_debug
//printf("**** wd DataTimeout\n");
printf("**** wd DataTimeout\n");
#endif
return eDataTimeout;
}
@@ -214,7 +219,7 @@ eData waitData(int fd, unsigned char* buffer, int* len)
else if (fds.revents & POLLOUT)
{
#if wd_debug
//printf("**** wd DataWrite\n");
printf("**** wd DataWrite\n");
#endif
return eDataWrite;
}
@@ -233,7 +238,7 @@ static bool transmitData(eDVBCISlot* slot, unsigned char* d, int len)
{
printf("%s -> %s len(%d)\n", FILENAME, __func__, len);
#if BOXMODEL_VUSOLO4K
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUDUO4KSE || BOXMODEL_VUULTIMO4K || BOXMODEL_VUZERO4K
#if y_debug
for (int i = 0; i < len; i++)
printf("%02x ", d[i]);
@@ -262,7 +267,7 @@ static bool transmitData(eDVBCISlot* slot, unsigned char* d, int len)
//send some data on an fd, for a special slot and connection_id
eData sendData(eDVBCISlot* slot, unsigned char* data, int len)
{
#if HAVE_ARM_HARDWARE
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
unsigned char *d = (unsigned char*) malloc(len);
memcpy(d, data, len);
transmitData(slot, d, len);
@@ -476,9 +481,14 @@ void cCA::process_tpdu(eDVBCISlot* slot, unsigned char tpdu_tag, __u8* data, int
bool cCA::SendMessage(const CA_MESSAGE *msg)
{
lt_debug("%s\n", __func__);
hal_debug("%s\n", __func__);
if(cam_messenger)
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
cam_messenger(EVT_CA_MESSAGE, (uintptr_t) msg);
#else
cam_messenger(EVT_CA_MESSAGE, (uint32_t) msg);
#endif
#if z_debug
printf("*******Message\n");
printf("msg: %p\n", msg);
@@ -631,6 +641,7 @@ bool cCA::StopLiveCI( u64 TP, u16 SID, u8 source, u32 calen)
{
if ((*it)->liveUse[j] && (*it)->TP == TP && (*it)->SID[j] == SID && (*it)->source == source && !calen)
{
(*it)->SID[j] = 0;
(*it)->liveUse[j] = false;
return true;
}
@@ -649,6 +660,7 @@ bool cCA::StopRecordCI( u64 TP, u16 SID, u8 source, u32 calen)
{
if ((*it)->recordUse[j] && (*it)->TP == TP && (*it)->SID[j] == SID && (*it)->source == source && !calen)
{
(*it)->SID[j] = 0;
(*it)->recordUse[j] = false;
return true;
}
@@ -875,6 +887,10 @@ bool cCA::SendCAPMT(u64 tpid, u8 source, u8 camask, const unsigned char * cabuf,
(*It)->SID[0] = SID;
(*It)->ci_use_count = 1;
(*It)->TP = TP;
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
if(!checkLiveSlot && mode && (*It)->source != source)
setInputSource((eDVBCISlot*)(*It), false);
#endif
(*It)->source = source;
(*It)->pmtlen = calen;
for (i = 0; i < calen; i++)
@@ -882,7 +898,7 @@ bool cCA::SendCAPMT(u64 tpid, u8 source, u8 camask, const unsigned char * cabuf,
(*It)->newCapmt = true;
}
#if HAVE_ARM_HARDWARE
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
if ((*It)->newCapmt)
extractPids((eDVBCISlot*)(*It));
#endif
@@ -910,7 +926,7 @@ bool cCA::SendCAPMT(u64 tpid, u8 source, u8 camask, const unsigned char * cabuf,
}
else
{
#if HAVE_ARM_HARDWARE
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
std::list<eDVBCISlot*>::iterator it;
recordUse_found = false;
for (it = slot_data.begin(); it != slot_data.end(); ++it)
@@ -922,12 +938,13 @@ bool cCA::SendCAPMT(u64 tpid, u8 source, u8 camask, const unsigned char * cabuf,
if ((*it)->recordUse[j])
recordUse_found = true;
}
if (!recordUse_found)
if (!recordUse_found && (*it)->init)
{
printf("Slot: %d Change Input to Tuner: %d\n", (*it)->slot, (*it)->source);
setInputSource((eDVBCISlot*)(*it), false);
}
}
if (!(*it)->init)
last_source = (int)source;
}
#endif
printf("No free ci-slot\n");
@@ -950,7 +967,7 @@ bool cCA::SendCAPMT(u64 tpid, u8 source, u8 camask, const unsigned char * cabuf,
return true;
}
#if HAVE_ARM_HARDWARE
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
void cCA::extractPids(eDVBCISlot* slot)
{
u32 prg_info_len;
@@ -1009,12 +1026,76 @@ void cCA::setSource(eDVBCISlot* slot)
case TUNER_D:
fprintf(ci, "D");
break;
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUDUO4KSE || BOXMODEL_VUULTIMO4K
case TUNER_E:
fprintf(ci, "E");
break;
case TUNER_F:
fprintf(ci, "F");
break;
case TUNER_G:
fprintf(ci, "G");
break;
case TUNER_H:
fprintf(ci, "H");
break;
case TUNER_I:
fprintf(ci, "I");
break;
case TUNER_J:
fprintf(ci, "J");
break;
case TUNER_K:
fprintf(ci, "K");
break;
case TUNER_L:
fprintf(ci, "L");
break;
case TUNER_M:
fprintf(ci, "M");
break;
case TUNER_N:
fprintf(ci, "N");
break;
case TUNER_O:
fprintf(ci, "O");
break;
case TUNER_P:
fprintf(ci, "P");
break;
#if BOXMODEL_VUULTIMO4K
case TUNER_Q:
fprintf(ci, "Q");
break;
case TUNER_R:
fprintf(ci, "R");
break;
case TUNER_S:
fprintf(ci, "S");
break;
case TUNER_T:
fprintf(ci, "T");
break;
case TUNER_U:
fprintf(ci, "U");
break;
case TUNER_V:
fprintf(ci, "V");
break;
case TUNER_W:
fprintf(ci, "W");
break;
case TUNER_X:
fprintf(ci, "X");
break;
#endif
#endif
}
fclose(ci);
}
}
#if HAVE_ARM_HARDWARE
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
static std::string getTunerLetter(int number) { return std::string(1, char(65 + number)); }
void cCA::setInputs()
@@ -1023,7 +1104,15 @@ void cCA::setInputs()
char choices[64];
FILE * fd = 0;
#if BOXMODEL_VUULTIMO4K
for (int number = 0; number < 24; number++) // tuner A to X, input 0 to 23
#else
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUDUO4KSE || BOXMODEL_VUUNO4KSE || BOXMODEL_VUUNO4K
for (int number = 0; number < 16; number++) // tuner A to P, input 0 to 15
#else
for (int number = 0; number < 4; number++) // tuner A to D, input 0 to 3
#endif
#endif
{
snprintf(choices, 64, "/proc/stb/tsmux/input%d_choices", number);
if(access(choices, R_OK) < 0)
@@ -1037,7 +1126,8 @@ void cCA::setInputs()
if (fd)
{
printf("set input%d to tuner %s\n", number, getTunerLetter(number).c_str());
fprintf(fd, getTunerLetter(number).c_str());
fprintf(fd,"%s", getTunerLetter(number).c_str());
fclose(fd);
}
else
{
@@ -1049,6 +1139,7 @@ void cCA::setInputs()
void cCA::setInputSource(eDVBCISlot* slot, bool ci)
{
char buf[64];
printf("%s set input%d to %s%d\n", FILENAME, slot->source, ci ? "ci" : "tuner", ci ? slot->slot : slot->source);
snprintf(buf, 64, "/proc/stb/tsmux/input%d", slot->source);
FILE *input = fopen(buf, "wb");
@@ -1082,6 +1173,70 @@ void cCA::setInputSource(eDVBCISlot* slot, bool ci)
case TUNER_D:
fprintf(input, "D");
break;
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUDUO4KSE || BOXMODEL_VUULTIMO4K || BOXMODEL_VUUNO4KSE || BOXMODEL_VUUNO4K
case TUNER_E:
fprintf(input, "E");
break;
case TUNER_F:
fprintf(input, "F");
break;
case TUNER_G:
fprintf(input, "G");
break;
case TUNER_H:
fprintf(input, "H");
break;
case TUNER_I:
fprintf(input, "I");
break;
case TUNER_J:
fprintf(input, "J");
break;
case TUNER_K:
fprintf(input, "K");
break;
case TUNER_L:
fprintf(input, "L");
break;
case TUNER_M:
fprintf(input, "M");
break;
case TUNER_N:
fprintf(input, "N");
break;
case TUNER_O:
fprintf(input, "O");
break;
case TUNER_P:
fprintf(input, "P");
break;
#if BOXMODEL_VUULTIMO4K
case TUNER_Q:
fprintf(input, "Q");
break;
case TUNER_R:
fprintf(input, "R");
break;
case TUNER_S:
fprintf(input, "S");
break;
case TUNER_T:
fprintf(input, "T");
break;
case TUNER_U:
fprintf(input, "U");
break;
case TUNER_V:
fprintf(input, "V");
break;
case TUNER_W:
fprintf(input, "W");
break;
case TUNER_X:
fprintf(input, "X");
break;
#endif
#endif
}
}
fclose(input);
@@ -1094,7 +1249,7 @@ cCA::cCA(int Slots)
printf("%s -> %s %d\n", FILENAME, __func__, Slots);
num_slots = Slots;
#if HAVE_ARM_HARDWARE
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
setInputs();
#endif
@@ -1190,6 +1345,10 @@ void cCA::ModuleReset(enum CA_SLOT_TYPE, uint32_t slot)
{
(*it)->status = eStatusReset;
usleep(200000);
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
last_source = (int)(*it)->source;
setInputSource((eDVBCISlot*)(*it), false);
#endif
if ((*it)->hasCCManager)
(*it)->ccmgrSession->ci_ccmgr_doClose((eDVBCISlot*)(*it));
eDVBCISession::deleteSessions((eDVBCISlot*)(*it));
@@ -1279,6 +1438,10 @@ void cCA::ci_inserted(eDVBCISlot* slot)
void cCA::ci_removed(eDVBCISlot* slot)
{
printf("cam (%d) status changed ->cam now _not_ present\n", slot->slot);
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
last_source = (int)slot->source;
setInputSource(slot, false);
#endif
if (slot->hasCCManager)
slot->ccmgrSession->ci_ccmgr_doClose(slot);
eDVBCISession::deleteSessions(slot);
@@ -1342,12 +1505,11 @@ void cCA::slot_pollthread(void *c)
{
unsigned char data[1024 * 4];
eDVBCISlot* slot = (eDVBCISlot*) c;
bool wait = false;
while (1)
{
#if HAVE_ARM_HARDWARE /* Armbox */
if (slot->init && !slot->mmiOpened)
sleep(1);
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE /* Armbox/Mipsbox */
int len = 1024 *4;
eData status;
@@ -1377,9 +1539,13 @@ void cCA::slot_pollthread(void *c)
}
#endif
ci_inserted(slot);
//setInputSource(slot, true);
goto FROM_FIRST;
}
}
/* slow down the loop, if no CI cam present */
// printf("***sleep\n");
sleep(1);
} /* case statusnone */
break;
case eStatusWait:
@@ -1388,6 +1554,7 @@ void cCA::slot_pollthread(void *c)
FROM_FIRST:
if (status == eDataReady)
{
wait = false;
slot->pollConnection = false;
if (len)
{
@@ -1397,6 +1564,7 @@ FROM_FIRST:
} /*if data ready */
else if (status == eDataWrite)
{
wait = true;
/* only writing any data here while status = eDataWrite */
if (!slot->sendqueue.empty())
{
@@ -1582,6 +1750,14 @@ FROM_FIRST:
break;
} /* switch(slot->status) */
#endif /* end Duckbox */
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
if (!slot->init && slot->camIsReady && last_source > -1)
{
slot->source = (u8)last_source;
setInputSource(slot, true);
last_source = -1;
}
#endif
if (slot->hasCAManager && slot->hasAppManager && !slot->init)
{
slot->init = true;
@@ -1618,12 +1794,22 @@ FROM_FIRST:
if (slot->ccmgr_ready && slot->hasCCManager && slot->scrambled && !slot->SidBlackListed)
slot->ccmgrSession->resendKey(slot);
}
/* slow down for hd51 to avoid high cpu load */
if (wait && slot->init && !slot->mmiOpened)
usleep(300000);
}
}
bool cCA::SendCaPMT(eDVBCISlot* slot)
{
printf("%s -> %s\n", FILENAME, __func__);
if (slot->fd > 0)
{
#if HAVE_ARM_HARDWARE || HAVE_MIPS_HARDWARE
setInputSource(slot, true);
#endif
setSource(slot);
}
if ((slot->fd > 0) && (slot->camIsReady))
{
if (slot->hasCAManager)
@@ -1639,14 +1825,6 @@ bool cCA::SendCaPMT(eDVBCISlot* slot)
slot->camgrSession->sendSPDU(0x90, 0, 0, slot->pmtdata, slot->pmtlen);
}
}
if (slot->fd > 0)
{
#if HAVE_ARM_HARDWARE
setInputSource(slot, true);
#endif
setSource(slot);
}
return true;
}
@@ -1737,7 +1915,7 @@ void cCA::setCheckLiveSlot(int check)
checkLiveSlot = false;
}
void cCA::SetTSClock(u32 Speed)
void cCA::SetTSClock(u32 Speed, int slot)
{
/* TODO:
* For now using the coolstream values from neutrino cam_menu
@@ -1749,20 +1927,47 @@ void cCA::SetTSClock(u32 Speed)
* and here too.
* On the other hand: or ci_clock will be set here for all ci slots ????
*/
char buf[64];
snprintf(buf, 64, "/proc/stb/tsmux/ci%d_tsclk", 0);
char buf[64];
snprintf(buf, 64, "/proc/stb/tsmux/ci%d_tsclk", slot);
FILE *ci = fopen(buf, "wb");
printf("%s -> %s to: %s\n", FILENAME, __func__, Speed > 6 * 1000000 ? "high" : "normal");
printf("%s -> %s to: %s\n", FILENAME, __func__, Speed > 9 * 1000000 ? "extra_high" : Speed > 6 * 1000000 ? "high" : "normal");
if (ci)
{
if (Speed > 6 * 1000000)
{
fprintf(ci, "high");
}
if (Speed > 9 * 1000000)
fprintf(ci, "extra_high");
else
if (Speed > 6 * 1000000)
fprintf(ci, "high");
else
{
fprintf(ci, "normal");
}
fclose(ci);
}
}
#if BOXMODEL_VUPLUS_ALL
void cCA::SetCIDelay(int Delay)
{
char buf[64];
snprintf(buf, 64, "/proc/stb/tsmux/rmx_delay");
FILE *ci = fopen(buf, "wb");
printf("%s -> %s to: %i\n", FILENAME, __func__, Delay);
if (ci)
{
fprintf(ci, "%i", Delay);
fclose(ci);
}
}
void cCA::SetCIRelevantPidsRouting(int RPR, int slot)
{
char buf[64];
snprintf(buf, 64, "/proc/stb/tsmux/ci%d_relevant_pids_routing", slot);
FILE *ci = fopen(buf, "wb");
printf("%s -> %s to: %i\n", FILENAME, __func__, RPR);
if (ci)
{
fprintf(ci, "%s", RPR == 1 ? "yes" : "no");
fclose(ci);
}
}
#endif

View File

@@ -1,4 +1,4 @@
/* libtriple debug functions */
/* libstb-hal debug functions */
#include <stdarg.h>
#include <stdio.h>
@@ -12,7 +12,7 @@ int cnxt_debug = 0; /* compat, unused */
int debuglevel = -1;
static const char* lt_facility[] = {
static const char* hal_facility[] = {
"audio ",
"video ",
"demux ",
@@ -24,10 +24,10 @@ static const char* lt_facility[] = {
NULL
};
void _lt_info(int facility, const void *func, const char *fmt, ...)
void _hal_info(int facility, const void *func, const char *fmt, ...)
{
/* %p does print "(nil)" instead of 0x00000000 for NULL */
fprintf(stderr, "[LT:%08lx:%s] ", (long) func, lt_facility[facility]);
fprintf(stderr, "[HAL:%08lx:%s] ", (long) func, hal_facility[facility]);
va_list args;
va_start(args, fmt);
vfprintf(stderr, fmt, args);
@@ -35,22 +35,22 @@ void _lt_info(int facility, const void *func, const char *fmt, ...)
}
void _lt_debug(int facility, const void *func, const char *fmt, ...)
void _hal_debug(int facility, const void *func, const char *fmt, ...)
{
if (debuglevel < 0)
fprintf(stderr, "lt_debug: debuglevel not initialized!\n");
fprintf(stderr, "hal_debug: debuglevel not initialized!\n");
if (! ((1 << facility) & debuglevel))
return;
fprintf(stderr, "[LT:%08lx:%s] ", (long)func, lt_facility[facility]);
fprintf(stderr, "[HAL:%08lx:%s] ", (long)func, hal_facility[facility]);
va_list args;
va_start(args, fmt);
vfprintf(stderr, fmt, args);
va_end(args);
}
void lt_debug_init(void)
void hal_debug_init(void)
{
int i = 0;
char *tmp = getenv("HAL_DEBUG");
@@ -65,16 +65,16 @@ void lt_debug_init(void)
{
fprintf(stderr, "libstb-hal debug options can be set by exporting HAL_DEBUG.\n");
fprintf(stderr, "The following values (or bitwise OR combinations) are valid:\n");
while (lt_facility[i]) {
fprintf(stderr, "\tcomponent: %s 0x%02x\n", lt_facility[i], 1 << i);
while (hal_facility[i]) {
fprintf(stderr, "\tcomponent: %s 0x%02x\n", hal_facility[i], 1 << i);
i++;
}
fprintf(stderr, "\tall components: 0x%02x\n", (1 << i) - 1);
} else {
fprintf(stderr, "libstb-hal debug is active for the following components:\n");
while (lt_facility[i]) {
while (hal_facility[i]) {
if (debuglevel & (1 << i))
fprintf(stderr, "%s ", lt_facility[i]);
fprintf(stderr, "%s ", hal_facility[i]);
i++;
}
fprintf(stderr, "\n");

22
common/hal_debug.h Normal file
View File

@@ -0,0 +1,22 @@
#ifndef __HAL_DEBUG_H__
#define __HAL_DEBUG_H__
#define HAL_DEBUG_AUDIO 0
#define HAL_DEBUG_VIDEO 1
#define HAL_DEBUG_DEMUX 2
#define HAL_DEBUG_PLAYBACK 3
#define HAL_DEBUG_PWRMNGR 4
#define HAL_DEBUG_INIT 5
#define HAL_DEBUG_CA 6
#define HAL_DEBUG_RECORD 7
#define HAL_DEBUG_ALL ((1<<8)-1)
extern int debuglevel;
void _hal_debug(int facility, const void *, const char *fmt, ...) __attribute__ ((format (printf, 3, 4)));
void _hal_info(int facility, const void *, const char *fmt, ...) __attribute__ ((format (printf, 3, 4)));
void hal_debug_init(void);
void hal_set_threadname(const char *name);
#endif // __HAL_DEBUG_H__

View File

@@ -1 +0,0 @@
../include/hardware_caps.h

View File

@@ -1,30 +0,0 @@
#ifndef __LT_DEBUG_H
#define __LT_DEBUG_H
#define TRIPLE_DEBUG_AUDIO 0
#define TRIPLE_DEBUG_VIDEO 1
#define TRIPLE_DEBUG_DEMUX 2
#define TRIPLE_DEBUG_PLAYBACK 3
#define TRIPLE_DEBUG_PWRMNGR 4
#define TRIPLE_DEBUG_INIT 5
#define TRIPLE_DEBUG_CA 6
#define TRIPLE_DEBUG_RECORD 7
#define TRIPLE_DEBUG_ALL ((1<<8)-1)
#define HAL_DEBUG_AUDIO 0
#define HAL_DEBUG_VIDEO 1
#define HAL_DEBUG_DEMUX 2
#define HAL_DEBUG_PLAYBACK 3
#define HAL_DEBUG_PWRMNGR 4
#define HAL_DEBUG_INIT 5
#define HAL_DEBUG_CA 6
#define HAL_DEBUG_RECORD 7
#define HAL_DEBUG_ALL ((1<<8)-1)
extern int debuglevel;
void hal_set_threadname(const char *name);
void _lt_debug(int facility, const void *, const char *fmt, ...) __attribute__ ((format (printf, 3, 4)));
void _lt_info(int facility, const void *, const char *fmt, ...) __attribute__ ((format (printf, 3, 4)));
void lt_debug_init(void);
#endif

179
common/pwrmngr.cpp Normal file
View File

@@ -0,0 +1,179 @@
/*
* (C) 2010-2013 Stefan Seyfried
*
* 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.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <config.h>
#include "pwrmngr.h"
#include "hal_debug.h"
#include <stdio.h>
#include <cstdlib>
#include <fcntl.h>
#include <unistd.h>
#include <sys/ioctl.h>
#include <sys/stat.h>
#include <sys/types.h>
#if HAVE_TRIPLEDRAGON
#include <avs/avs_inf.h>
#include <tdpanel/lcdstuff.h>
#endif
#define hal_debug(args...) _hal_debug(HAL_DEBUG_PWRMNGR, this, args)
#define hal_info(args...) _hal_info(HAL_DEBUG_PWRMNGR, this, args)
/* cpufreqmanager */
void cCpuFreqManager::Up(void)
{
hal_debug("%s\n", __func__);
}
void cCpuFreqManager::Down(void)
{
hal_debug("%s\n", __func__);
}
void cCpuFreqManager::Reset(void)
{
hal_debug("%s\n", __func__);
}
/* those function dummies return true or "harmless" values */
bool cCpuFreqManager::SetDelta(unsigned long)
{
hal_debug("%s\n", __func__);
return true;
}
unsigned long cCpuFreqManager::GetDelta(void)
{
hal_debug("%s\n", __func__);
return 0;
}
#if HAVE_SPARK_HARDWARE || HAVE_DUCKBOX_HARDWARE
unsigned long cCpuFreqManager::GetCpuFreq(void) {
int freq = 0;
if (FILE *pll0 = fopen("/proc/cpu_frequ/pll0_ndiv_mdiv", "r")) {
char buffer[120];
while(fgets(buffer, sizeof(buffer), pll0)) {
if (1 == sscanf(buffer, "SH4 = %d MHZ", &freq))
break;
}
fclose(pll0);
return 1000 * 1000 * (unsigned long) freq;
}
return 0;
}
#else
unsigned long cCpuFreqManager::GetCpuFreq(void)
{
hal_debug("%s\n", __func__);
return 0;
}
#endif
bool cCpuFreqManager::SetCpuFreq(unsigned long f)
{
hal_info("%s(%lu) => set standby = %s\n", __func__, f, f?"true":"false");
#if HAVE_TRIPLEDRAGON
/* actually SetCpuFreq is used to determine if the system is in standby
this is an "elegant" hack, because:
* during a recording, cpu freq is kept "high", even if the box is sent to standby
* the "SetStandby" call is made even if a recording is running
On the TD, setting standby disables the frontend, so we must not do it
if a recording is running.
For now, the values in neutrino are hardcoded:
* f == 0 => max => not standby
* f == 50000000 => min => standby
*/
int fd = open("/dev/stb/tdsystem", O_RDONLY);
if (fd < 0)
{
perror("open tdsystem");
return false;
}
if (f)
{
ioctl(fd, IOC_AVS_SET_VOLUME, 31); /* mute AVS to avoid ugly noise */
ioctl(fd, IOC_AVS_STANDBY_ENTER);
if (getenv("TRIPLE_LCDBACKLIGHT"))
{
hal_info("%s: TRIPLE_LCDBACKLIGHT is set: keeping LCD backlight on\n", __func__);
close(fd);
fd = open("/dev/stb/tdlcd", O_RDONLY);
if (fd < 0)
hal_info("%s: open tdlcd error: %m\n", __func__);
else
ioctl(fd, IOC_LCD_BACKLIGHT_ON);
}
}
else
{
ioctl(fd, IOC_AVS_SET_VOLUME, 31); /* mute AVS to avoid ugly noise */
ioctl(fd, IOC_AVS_STANDBY_LEAVE);
/* unmute will be done by cAudio::do_mute(). Ugly, but prevents pops */
// ioctl(fd, IOC_AVS_SET_VOLUME, 0); /* max gain */
}
close(fd);
#elif HAVE_SPARK_HARDWARE || HAVE_DUCKBOX_HARDWARE
if (f) {
FILE *pll0 = fopen ("/proc/cpu_frequ/pll0_ndiv_mdiv", "w");
if (pll0) {
f /= 1000000;
fprintf(pll0, "%lu\n", (f/10 << 8) | 3);
fclose (pll0);
return false;
}
}
#endif
return true;
}
cCpuFreqManager::cCpuFreqManager(void)
{
hal_debug("%s\n", __func__);
}
/* powermanager */
bool cPowerManager::Open(void)
{
hal_debug("%s\n", __func__);
return true;
}
void cPowerManager::Close(void)
{
hal_debug("%s\n", __func__);
}
bool cPowerManager::SetStandby(bool Active, bool Passive)
{
hal_debug("%s(%d, %d)\n", __func__, Active, Passive);
return true;
}
cPowerManager::cPowerManager(void)
{
hal_debug("%s\n", __func__);
}
cPowerManager::~cPowerManager()
{
hal_debug("%s\n", __func__);
}

51
common/version_hal.cpp Normal file
View File

@@ -0,0 +1,51 @@
/*
* (C) 2018 Thilo Graf
*
* 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.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <libstb-hal-config.h>
#include <version_hal.h>
void hal_get_lib_version(hal_libversion_t *ver)
{
if (!ver)
return;
//init struct
*ver = {"",0,0,0,"","",""};
#ifdef VERSION
ver->vVersion = VERSION;
#endif
#ifdef PACKAGE_VERSION_MAJOR
ver->vMajor = PACKAGE_VERSION_MAJOR;
#endif
#ifdef PACKAGE_VERSION_MAJOR
ver->vMinor = PACKAGE_VERSION_MINOR;
#endif
#ifdef PACKAGE_VERSION_MINOR
ver->vPatch = PACKAGE_VERSION_MICRO;
#endif
#ifdef PACKAGE_NAME
ver->vName = PACKAGE_NAME;
#endif
#ifdef PACKAGE_STRING
ver->vStr = PACKAGE_STRING;
#endif
#ifdef PACKAGE_VERSION_GIT
ver->vGitDescribe = PACKAGE_VERSION_GIT;
#endif
}

View File

@@ -1,11 +1,28 @@
AC_INIT([libstb-hal], [1.0.1])
AM_INIT_AUTOMAKE
# explicit defines for separate revision handling
define(ver_major, 1)
define(ver_minor, 4)
define(ver_micro, 0)
# sync with current git
define(ver_git, m4_esyscmd([
GITBRANCH=$(git rev-parse --abbrev-ref HEAD);
GITDESCRIBE=$(git describe --always --tags --dirty);
printf "$GITDESCRIBE $GITBRANCH"
]))
AC_PACKAGE_NAME, PACKAGE_NAME_LIBSTB_HAL
AC_INIT([Tuxbox-libstb-hal], [ver_major.ver_minor.ver_micro])
AM_INIT_AUTOMAKE([foreign])
AC_CONFIG_HEADERS([libstb-hal-config.h:config.h.in])
m4_ifdef([AM_SILENT_RULES], [AM_SILENT_RULES])
AC_CONFIG_MACRO_DIR([m4])
AC_GNU_SOURCE
AC_DEFINE(PACKAGE_VERSION_MAJOR, ver_major, [Major version number])
AC_DEFINE(PACKAGE_VERSION_MINOR, ver_minor, [Minor version number])
AC_DEFINE(PACKAGE_VERSION_MICRO, ver_micro, [Micro version number])
AC_DEFINE(PACKAGE_VERSION_GIT, "ver_git", [internal vcs version info])
TUXBOX_APPS
TUXBOX_APPS_DIRECTORY
TUXBOX_BOXTYPE
AC_PROG_CC
@@ -18,42 +35,57 @@ PKG_PROG_PKG_CONFIG
AC_DISABLE_SHARED
AC_DISABLE_STATIC
AC_SYS_LARGEFILE
AC_PROG_LIBTOOL
LT_INIT
AC_ARG_ENABLE(clutter,
AS_HELP_STRING(--enable-clutter, use clutter instead of OpenGL),
,[enable_clutter=no])
AM_CONDITIONAL(USE_CLUTTER,test "$enable_clutter" = "yes")
AM_CONDITIONAL(USE_OPENGL,test "$enable_clutter" = "no")
if test "$enable_clutter" = "yes"; then
AC_DEFINE(USE_CLUTTER,1,[use clutter instead of opengl])
else
AC_DEFINE(USE_OPENGL,1,[use opengl instead of clutter])
fi
if test x"$BOXTYPE" = x"tripledragon"; then
PKG_CHECK_MODULES([DIRECTFB], [directfb])
fi
AC_ARG_ENABLE(gstreamer_01,
AS_HELP_STRING(--enable-gstreamer_01,use gstreamer 0.10 playback),
,[enable_gstreamer_01=no])
AS_HELP_STRING(--enable-gstreamer_01, use gstreamer 0.10 playback),
,[enable_gstreamer_01=no])
AM_CONDITIONAL(ENABLE_GSTREAMER_01,test "$enable_gstreamer_01" = "yes")
if test "$enable_gstreamer_01" = "yes"; then
AC_DEFINE(ENABLE_GSTREAMER_01,1,[use gstreamer 0.10 playback])
PKG_CHECK_MODULES([GSTREAMER], [gstreamer-0.10])
PKG_CHECK_MODULES([GSTREAMER_INTERFACES], [gstinterfaces-0.10])
AC_DEFINE(ENABLE_GSTREAMER_01, 1, [use gstreamer 0.10 playback])
PKG_CHECK_MODULES([GSTREAMER], [gstreamer-0.10])
PKG_CHECK_MODULES([GSTREAMER_INTERFACES], [gstinterfaces-0.10])
fi
AC_ARG_ENABLE(gstreamer_10,
AS_HELP_STRING(--enable-gstreamer_10,use gstreamer 1.0 playback),
,[enable_gstreamer_10=no])
AS_HELP_STRING(--enable-gstreamer_10, use gstreamer 1.0 playback),
,[enable_gstreamer_10=no])
AM_CONDITIONAL(ENABLE_GSTREAMER_10,test "$enable_gstreamer_10" = "yes")
AM_CONDITIONAL(ENABLE_GSTREAMER_10, test "$enable_gstreamer_10" = "yes")
if test "$enable_gstreamer_10" = "yes"; then
AC_DEFINE(ENABLE_GSTREAMER_10,1,[use gstreamer 1.0 playback])
PKG_CHECK_MODULES([GSTREAMER], [gstreamer-1.0])
PKG_CHECK_MODULES([GSTREAMER_AUDIO], [gstreamer-audio-1.0])
PKG_CHECK_MODULES([GSTREAMER_VIDEO], [gstreamer-video-1.0])
AC_DEFINE(ENABLE_GSTREAMER_10, 1, [use gstreamer 1.0 playback])
PKG_CHECK_MODULES([GSTREAMER], [gstreamer-1.0])
PKG_CHECK_MODULES([GSTREAMER_AUDIO], [gstreamer-audio-1.0])
PKG_CHECK_MODULES([GSTREAMER_VIDEO], [gstreamer-video-1.0])
fi
if test x$BOXTYPE = xarmbox ; then
PKG_CHECK_MODULES([GSTREAMER], [gstreamer-1.0])
PKG_CHECK_MODULES([GSTREAMER_AUDIO], [gstreamer-audio-1.0])
PKG_CHECK_MODULES([GSTREAMER_VIDEO], [gstreamer-video-1.0])
if test x$BOXTYPE = xarmbox -a "$enable_gstreamer_10" = "yes"; then
PKG_CHECK_MODULES([GSTREAMER], [gstreamer-1.0])
PKG_CHECK_MODULES([GSTREAMER_AUDIO], [gstreamer-audio-1.0])
PKG_CHECK_MODULES([GSTREAMER_VIDEO], [gstreamer-video-1.0])
fi
if test x$BOXTYPE = xgeneric -a x$BOXMODEL != xraspi; then
if test x"$enable_clutter" = xyes; then
PKG_CHECK_MODULES([CLUTTER], [clutter-1.0])
fi
PKG_CHECK_MODULES([AVFORMAT], [libavformat >= 53.21.1])
PKG_CHECK_MODULES([AVCODEC], [libavcodec >= 54.28.0])
# don't know which version is exactly needed here...
@@ -62,19 +94,28 @@ if test x$BOXTYPE = xgeneric -a x$BOXMODEL != xraspi; then
PKG_CHECK_MODULES([SWRESAMPLE], [libswresample])
fi
AC_OUTPUT([
AC_ARG_ENABLE(flv2mpeg4,
AS_HELP_STRING(--enable-flv2mpeg4, use flv2mpeg4 libeplayer3),
,[enable_flv2mpeg4=no])
AM_CONDITIONAL(ENABLE_FLV2MPEG4, test "$enable_flv2mpeg4" = "yes")
if test "$enable_flv2mpeg4" = "yes"; then
AC_DEFINE(ENABLE_FLV2MPEG4, 1, [use flv2mpeg4 libeplayer3])
fi
AC_CONFIG_FILES([
Makefile
common/Makefile
libeplayer3/Makefile
libthread/Makefile
azbox/Makefile
generic-pc/Makefile
libmipsbox/Makefile
libarmbox/Makefile
libduckbox/Makefile
libdvbci/Makefile
libtriple/Makefile
libeplayer3/Makefile
libeplayer3-sh4/Makefile
libgeneric-pc/Makefile
libraspi/Makefile
libspark/Makefile
libarmbox/Makefile
raspi/Makefile
tools/Makefile
])
AC_OUTPUT

View File

@@ -1 +0,0 @@
../libspark/cs_api.h

View File

@@ -1 +0,0 @@
#include "dmx_lib.h"

View File

@@ -1,70 +0,0 @@
#ifndef __DEMUX_TD_H
#define __DEMUX_TD_H
#include <cstdlib>
#include <vector>
#include <inttypes.h>
#include <sys/ioctl.h>
#include <linux/dvb/dmx.h>
#include "../common/cs_types.h"
#define MAX_DMX_UNITS 4
typedef enum
{
DMX_INVALID = 0,
DMX_VIDEO_CHANNEL = 1,
DMX_AUDIO_CHANNEL,
DMX_PES_CHANNEL,
DMX_PSI_CHANNEL,
DMX_PIP_CHANNEL,
DMX_TP_CHANNEL,
DMX_PCR_ONLY_CHANNEL
} DMX_CHANNEL_TYPE;
typedef struct
{
int fd;
unsigned short pid;
} pes_pids;
class cDemux
{
private:
int num;
int fd;
int buffersize;
bool measure;
uint64_t last_measure, last_data;
DMX_CHANNEL_TYPE dmx_type;
std::vector<pes_pids> pesfds;
struct dmx_sct_filter_params s_flt;
struct dmx_pes_filter_params p_flt;
public:
bool Open(DMX_CHANNEL_TYPE pes_type, void * x = NULL, int y = 0);
void Close(void);
bool Start(bool record = false);
bool Stop(void);
int Read(unsigned char *buff, int len, int Timeout = 0);
bool sectionFilter(unsigned short pid, const unsigned char * const filter, const unsigned char * const mask, int len, int Timeout = 0, const unsigned char * const negmask = NULL);
bool pesFilter(const unsigned short pid);
void SetSyncMode(AVSYNC_TYPE mode);
void * getBuffer();
void * getChannel();
DMX_CHANNEL_TYPE getChannelType(void) { return dmx_type; };
bool addPid(unsigned short pid);
void getSTC(int64_t * STC);
int getUnit(void);
static bool SetSource(int unit, int source);
static int GetSource(int unit);
// TD only functions
int getFD(void) { return fd; }; /* needed by cPlayback class */
void removePid(unsigned short Pid); /* needed by cRecord class */
std::vector<pes_pids> getPesPids(void) { return pesfds; };
//
cDemux(int num = 0);
~cDemux();
};
#endif //__DEMUX_H

View File

@@ -1,5 +0,0 @@
#ifndef __INIT_TD_H
#define __INIT_TD_H
void init_td_api();
void shutdown_td_api();
#endif

View File

@@ -1 +0,0 @@
../libspark/pwrmngr.cpp

View File

@@ -1 +0,0 @@
../libspark/pwrmngr.h

View File

@@ -1,7 +1,5 @@
#include <config.h>
#if HAVE_TRIPLEDRAGON
#include "../libtriple/audio_td.h"
#elif HAVE_DUCKBOX_HARDWARE
#if HAVE_DUCKBOX_HARDWARE
#include "../libduckbox/audio_lib.h"
#include "../libduckbox/audio_mixer.h"
#elif HAVE_SPARK_HARDWARE
@@ -9,15 +7,14 @@
#include "../libspark/audio_mixer.h"
#elif HAVE_ARM_HARDWARE
#include "../libarmbox/audio_lib.h"
#include "../libarmbox/audio_mixer.h"
#elif HAVE_AZBOX_HARDWARE
#include "../azbox/audio_lib.h"
#elif HAVE_MIPS_HARDWARE
#include "../libmipsbox/audio_lib.h"
#elif HAVE_GENERIC_HARDWARE
#if BOXMODEL_RASPI
#include "../raspi/audio_lib.h"
#include "../libraspi/audio_lib.h"
#else
#include "../generic-pc/audio_lib.h"
#include "../libgeneric-pc/audio_lib.h"
#endif
#else
#error neither HAVE_TRIPLEDRAGON nor HAVE_SPARK_HARDWARE defined
#error no valid hardware defined
#endif

View File

@@ -1,11 +1,5 @@
/*
* dummy functions to implement ca_cs.h interface
*/
#if HAVE_DUCKBOX_HARDWARE || HAVE_ARM_HARDWARE
#include "ca_ci.h"
#else
#ifndef __CA_LIBTRIPLE_H_
#define __CA_LIBTRIPLE_H_
#ifndef __CA_H__
#define __CA_H__
#include <stdint.h>
#include "cs_types.h"
@@ -116,11 +110,10 @@ public:
void MenuAnswer(enum CA_SLOT_TYPE, uint32_t Slot, uint32_t choice);
void InputAnswer(enum CA_SLOT_TYPE, uint32_t Slot, uint8_t * Data, int Len);
void MenuClose(enum CA_SLOT_TYPE, uint32_t Slot);
void SetTSClock(u32 /*Speed*/) { return; };
void SetTSClock(u32 /*Speed*/, int /*slot*/) { return; };
bool checkChannelID(u64 /*chanID*/) { return false; };
void setCheckLiveSlot(int /*check*/) { return; };
virtual ~cCA();
};
#endif // __CA_LIBTRIPLE_H_
#endif // HAVE_DUCKBOX_HARDWARE
#endif // __CA_H__

View File

@@ -1,6 +1,7 @@
#ifndef __CA_H_
#define __CA_H_
#ifndef __CA_CI_H__
#define __CA_CI_H__
#include <config.h>
#include <stdint.h>
#include <asm/types.h>
#include <pthread.h>
@@ -126,6 +127,30 @@ typedef enum {
TUNER_B,
TUNER_C,
TUNER_D
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUDUO4KSE || BOXMODEL_VUULTIMO4K || BOXMODEL_VUUNO4KSE || BOXMODEL_VUUNO4K
, TUNER_E
, TUNER_F
, TUNER_G
, TUNER_H
, TUNER_I
, TUNER_J
, TUNER_K
, TUNER_L
, TUNER_M
, TUNER_N
, TUNER_O
, TUNER_P
#if BOXMODEL_VUULTIMO4K
, TUNER_Q
, TUNER_R
, TUNER_S
, TUNER_T
, TUNER_U
, TUNER_V
, TUNER_W
, TUNER_X
#endif
#endif
} source_t;
typedef enum {
@@ -302,7 +327,15 @@ public:
void SetInitMask(enum CA_INIT_MASK InitMask);
/// Sets the frequency (in Hz) of the TS stream input (only valid for CI)
/// sh4 unused
void SetTSClock(u32 Speed);
void SetTSClock(u32 Speed, int slot = 0);
#if BOXMODEL_VUPLUS_ALL
/// dvb wait delay for ci response
void SetCIDelay(int Delay);
/// relevant pids routing
void SetCIRelevantPidsRouting(int RPR, int slot = 0);
#endif
/// Start the CA module
/// sh4 unused
bool Start(void);
@@ -347,4 +380,4 @@ public:
virtual ~cCA();
};
#endif ///__CA_H_
#endif // __CA_CI_H__

View File

@@ -1 +0,0 @@
#include "../common/ca.h"

11
include/ca_hal.h Normal file
View File

@@ -0,0 +1,11 @@
#if HAVE_DUCKBOX_HARDWARE \
|| HAVE_MIPS_HARDWARE \
|| (HAVE_ARM_HARDWARE \
&& !BOXMODEL_HD60 \
&& !BOXMODEL_OSMIO4K \
&& !BOXMODEL_OSMIO4KPLUS \
)
#include "ca_ci.h"
#else
#include "ca.h"
#endif

View File

@@ -1,23 +0,0 @@
#ifndef _CONDITION_ABSTRACTION_H
#define _CONDITION_ABSTRACTION_H
#include <pthread.h>
#include "mutex_abstraction.h"
class Condition
{
pthread_cond_t mCondition;
Condition(const Condition&);
const Condition& operator=(const Condition&);
public:
Condition();
virtual ~Condition();
virtual int wait(Mutex* const aMutex);
virtual int broadcast();
virtual int signal();
};
#endif

View File

@@ -1,20 +1,44 @@
/* compatibility header for tripledragon. I'm lazy, so I just left it
as "cs_api.h" so that I don't need too many ifdefs in the code */
#ifndef __CS_API_H__
#define __CS_API_H__
#include "init.h"
#include <config.h>
#if HAVE_TRIPLEDRAGON
#include "../libtriple/cs_api.h"
#elif HAVE_DUCKBOX_HARDWARE
#include "../libduckbox/cs_api.h"
#elif HAVE_SPARK_HARDWARE
#include "../libspark/cs_api.h"
#elif HAVE_ARM_HARDWARE
#include "../libarmbox/cs_api.h"
#elif HAVE_AZBOX_HARDWARE
#include "../azbox/cs_api.h"
#elif HAVE_GENERIC_HARDWARE
#if BOXMODEL_RASPI
#include "../raspi/cs_api.h"
typedef void (*cs_messenger) (unsigned int msg, unsigned int data);
inline void cs_api_init()
{
hal_api_init();
};
inline void cs_api_exit()
{
hal_api_exit();
};
#define cs_malloc_uncached malloc
#define cs_free_uncached free
// Callback function helpers
#if HAVE_DUCKBOX_HARDWARE \
|| HAVE_MIPS_HARDWARE \
|| (HAVE_ARM_HARDWARE \
&& !BOXMODEL_HD60 \
&& !BOXMODEL_OSMIO4K \
&& !BOXMODEL_OSMIO4KPLUS \
)
void cs_register_messenger(cs_messenger messenger);
#else
#include "../generic-pc/cs_api.h"
#endif
#else
#error neither HAVE_TRIPLEDRAGON nor HAVE_SPARK_HARDWARE defined
static inline void cs_register_messenger(cs_messenger) { return; };
#endif
static inline void cs_deregister_messenger(void) { return; };
/* compat... HD1 seems to be version 6. everything newer ist > 6... */
static inline unsigned int cs_get_revision(void) { return 1; };
static inline unsigned int cs_get_chip_type(void) { return 0; };
extern int cnxt_debug;
#endif // __CS_API_H__

View File

@@ -1,5 +1,5 @@
#ifndef __DUCKBOX_VFD__
#define __DUCKBOX_VFD__
#ifndef __CS_FRONTPANEL_H__
#define __CS_FRONTPANEL_H__
#define VFDDISPLAYCHARS 0xc0425a00
#define VFDWRITECGRAM 0x40425a01
@@ -317,4 +317,4 @@ typedef struct {
bool number_support;
} fp_display_caps_t;
#endif /* __DUCKBOX_VFD__ */
#endif // __CS_FRONTPANEL_H__

View File

@@ -1,8 +1,8 @@
/* pretty useless, but we don't need to work around this if
* we just copy it over... */
#ifndef __CS_TYPES_H_
#define __CS_TYPES_H_
#ifndef __CS_TYPES_H__
#define __CS_TYPES_H__
typedef enum
{
@@ -20,4 +20,4 @@ typedef signed int s32;
typedef signed short s16;
typedef signed char s8;
#endif // __CS_TYPES_H_
#endif // __CS_TYPES_H__

View File

@@ -1 +0,0 @@
#include "dmx_hal.h"

View File

@@ -1,20 +1,129 @@
/*
* (C) 2010-2013 Stefan Seyfried
*
* 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.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef __DMX_HAL_H__
#define __DMX_HAL_H__
#include <config.h>
#if HAVE_TRIPLEDRAGON
#include "../libtriple/dmx_td.h"
#elif HAVE_DUCKBOX_HARDWARE
#include "../libduckbox/dmx_lib.h"
#elif HAVE_SPARK_HARDWARE
#include "../libspark/dmx_lib.h"
#elif HAVE_AZBOX_HARDWARE
#include "../azbox/dmx_lib.h"
#elif HAVE_ARM_HARDWARE
#include "../libarmbox/dmx_lib.h"
#elif HAVE_GENERIC_HARDWARE
#if BOXMODEL_RASPI
#include "../raspi/dmx_lib.h"
#else
#include "../generic-pc/dmx_lib.h"
#include <cstdlib>
#include <vector>
#include <inttypes.h>
/* at least on td, config.h needs to be included before... */
#ifndef HAVE_TRIPLEDRAGON
#include <linux/dvb/dmx.h>
#else /* TRIPLEDRAGON */
extern "C" {
#include <hardware/xp/xp_osd_user.h>
}
#if defined DMX_FILTER_SIZE
#undef DMX_FILTER_SIZE
#endif
#define DMX_FILTER_SIZE FILTER_LENGTH
#endif /* TRIPLEDRAGON */
#include <cs_types.h>
#if BOXMODEL_VUULTIMO4K
#define MAX_DMX_UNITS 24
#else
#error neither HAVE_TRIPLEDRAGON nor HAVE_SPARK_HARDWARE defined
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUDUO4KSE || BOXMODEL_VUUNO4KSE || BOXMODEL_VUUNO4K
#define MAX_DMX_UNITS 16
#else
#define MAX_DMX_UNITS 4
#endif
#endif
#ifndef DMX_SET_SOURCE
/**
* DMX_SET_SOURCE and dmx_source enum removed on 4.14 kernel
* From Github.com/OpenPLI/enigma2 commit 7996dbb
**/
enum dmx_source
{
DMX_SOURCE_FRONT0 = 0,
DMX_SOURCE_FRONT1,
DMX_SOURCE_FRONT2,
DMX_SOURCE_FRONT3,
#if BOXMODEL_VUPLUS_ARM
DMX_SOURCE_DVR0 = 32,
#else
DMX_SOURCE_DVR0 = 16,
#endif
DMX_SOURCE_DVR1,
DMX_SOURCE_DVR2,
DMX_SOURCE_DVR3
};
#define DMX_SET_SOURCE _IOW('o', 49, enum dmx_source)
#endif
typedef enum
{
DMX_INVALID = 0,
DMX_VIDEO_CHANNEL = 1,
DMX_AUDIO_CHANNEL,
DMX_PES_CHANNEL,
DMX_PSI_CHANNEL,
DMX_PIP_CHANNEL,
DMX_TP_CHANNEL,
DMX_PCR_ONLY_CHANNEL
} DMX_CHANNEL_TYPE;
typedef struct
{
int fd;
unsigned short pid;
} pes_pids;
class cRecord;
class cPlayback;
class cDemux
{
friend class cRecord;
friend class cPlayback;
public:
bool Open(DMX_CHANNEL_TYPE pes_type, void * x = NULL, int y = 0);
void Close(void);
bool Start(bool record = false);
bool Stop(void);
int Read(unsigned char *buff, int len, int Timeout = 0);
bool sectionFilter(unsigned short pid, const unsigned char * const filter, const unsigned char * const mask, int len, int Timeout = 0, const unsigned char * const negmask = NULL);
bool pesFilter(const unsigned short pid);
void SetSyncMode(AVSYNC_TYPE mode);
void * getBuffer();
void * getChannel();
DMX_CHANNEL_TYPE getChannelType(void) { return dmx_type; };
bool addPid(unsigned short pid);
void getSTC(int64_t * STC);
int getUnit(void);
static bool SetSource(int unit, int source);
static int GetSource(int unit);
int getFD(void) { return fd; }; /* needed by cPlayback class */
cDemux(int num = 0);
~cDemux();
private:
void removePid(unsigned short Pid); /* needed by cRecord class */
int num;
int fd;
int buffersize;
uint16_t pid;
uint8_t flt;
std::vector<pes_pids> pesfds;
DMX_CHANNEL_TYPE dmx_type;
void *pdata;
};
#endif // __DMX_HAL_H__

View File

@@ -1,10 +1,44 @@
#include <config.h>
#if HAVE_GENERIC_HARDWARE
#if BOXMODEL_RASPI
#include "../raspi/glfb.h"
#else
#include "../generic-pc/glfb.h"
#endif
#else
#error glfb.h only works with HAVE_GENERIC_HARDWARE defined
#endif
/*
Copyright 2010 Carsten Juttner <carjay@gmx.net>
Copyright 2012,2013 Stefan Seyfried <seife@tuxboxcvs.slipkontur.de>
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.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef __GLFB_H__
#define __GLFB_H__
#include <OpenThreads/Thread>
#include <vector>
#include <linux/fb.h> /* for screeninfo etc. */
class GLFramebuffer : public OpenThreads::Thread
{
public:
GLFramebuffer(int x, int y);
~GLFramebuffer();
std::vector<unsigned char> *getOSDBuffer() { return &osd_buf; } /* pointer to OSD bounce buffer */
void blit();
fb_var_screeninfo getScreenInfo() { return si; }
private:
fb_var_screeninfo si;
std::vector<unsigned char> osd_buf; /* silly bounce buffer */
void run(); /* for OpenThreads::Thread */
void setup();
void blit_osd();
void *pdata; /* not yet used */
};
#endif // __GLFB_H__

View File

@@ -15,6 +15,7 @@ extern "C" {
typedef enum
{
HW_DISPLAY_NONE,
HW_DISPLAY_LED_ONLY,
HW_DISPLAY_LED_NUM, /* simple 7 segment LED display */
HW_DISPLAY_LINE_TEXT, /* 1 line text display */
HW_DISPLAY_GFX
@@ -28,6 +29,7 @@ typedef struct hw_caps
int has_SCART;
int has_SCART_input;
int has_YUV_cinch;
int can_cpufreq;
int can_shutdown;
int can_cec;
int can_ar_14_9; /* video drivers have 14:9 aspect ratio mode */
@@ -38,6 +40,10 @@ typedef struct hw_caps
int display_yres;
int display_can_set_brightness;
int display_can_deepstandby;
int display_has_statusline;
int display_has_colon;
int has_button_timer;
int has_button_vformat;
char boxvendor[64];
char boxname[64];
char boxarch[64];
@@ -50,4 +56,5 @@ hw_caps_t *get_hwcaps(void);
#ifdef __cplusplus
}
#endif
#endif
#endif // __HARDWARE_CAPS_H__

7
include/init.h Normal file
View File

@@ -0,0 +1,7 @@
#ifndef __INIT_H__
#define __INIT_H__
void hal_api_init();
void hal_api_exit();
#endif // __INIT_H__

View File

@@ -1,2 +0,0 @@
#warning using init_cs.h from libstb-hal
#include "init_td.h"

View File

@@ -1,5 +0,0 @@
#ifndef __INIT_TD_H
#define __INIT_TD_H
void init_td_api();
void shutdown_td_api();
#endif

View File

@@ -1,12 +1,12 @@
#ifndef __MMI_H_
#define __MMI_H_
#ifndef __MMI_H__
#define __MMI_H__
#define MAX_MMI_ITEMS 40
#define MAX_MMI_TEXT_LEN 255
#define MAX_MMI_CHOICE_TEXT_LEN 255
typedef enum {
MMI_TOP_MENU_SUBS = 1,
MMI_TOP_MENU_SUBS = 1,
MMI_TOP_MENU_EVENTS,
MMI_TOP_MENU_TOKENS,
MMI_TOP_MENU_PIN,
@@ -15,13 +15,13 @@ typedef enum {
} MMI_MENU_CURRENT;
typedef enum {
MMI_MENU_LEVEL_MAIN = 0,
MMI_MENU_LEVEL_MAIN = 0,
MMI_MENU_LEVEL_MATURE,
MMI_MENU_LEVEL_ASK_PIN_MATURE
} MMI_MENU_LEVEL;
typedef enum {
MMI_PIN_LEVEL_ASK_OLD = 0,
MMI_PIN_LEVEL_ASK_OLD = 0,
MMI_PIN_LEVEL_CHECK_CURRENT,
MMI_PIN_LEVEL_ASK_REPEAT,
MMI_PIN_LEVEL_CHECK_AND_CHANGE
@@ -44,8 +44,8 @@ typedef struct {
} MMI_ENQUIRY_INFO;
/* compat */
#define enguiryText enquiryText
#define enguiryText enquiryText
#define MMI_ENGUIRY_INFO MMI_ENQUIRY_INFO
#endif // __MMI_H_
#endif // __MMI_H__

View File

@@ -1,25 +0,0 @@
#ifndef _MUTEX_ABSTRACTION_H
#define _MUTEX_ABSTRACTION_H
#include <pthread.h>
class Mutex
{
friend class Condition;
pthread_mutex_t mMutex;
Mutex(const Mutex&);
const Mutex& operator=(const Mutex&);
protected:
explicit Mutex(int);
public:
Mutex();
virtual ~Mutex();
virtual void lock();
virtual void unlock();
};
#endif

View File

@@ -1,2 +0,0 @@
#include <config.h>
#include "playback_hal.h"

View File

@@ -1,24 +1,30 @@
#include <config.h>
#if HAVE_TRIPLEDRAGON
#include "../libtriple/playback_td.h"
#elif HAVE_DUCKBOX_HARDWARE
#if HAVE_DUCKBOX_HARDWARE
#include "../libduckbox/playback_libeplayer3.h"
#elif HAVE_SPARK_HARDWARE
#include "../libspark/playback_libeplayer3.h"
#elif HAVE_ARM_HARDWARE
#if ENABLE_GSTREAMER_10
#include "../libarmbox/playback_gst.h"
#elif HAVE_AZBOX_HARDWARE
#include "../azbox/playback.h"
#else
#if BOXMODEL_HISILICON
#include "../libarmbox/playback_hisilicon.h"
#else
#include "../libarmbox/playback_libeplayer3.h"
#endif
#endif
#elif HAVE_MIPS_HARDWARE
#include "../libmipsbox/playback_libeplayer3.h"
#elif HAVE_GENERIC_HARDWARE
#if BOXMODEL_RASPI
#include "../raspi/playback.h"
#include "../libraspi/playback_lib.h"
#else
#if ENABLE_GSTREAMER
#include "../generic-pc/playback_gst.h"
#include "../libgeneric-pc/playback_gst.h"
#else
#include "../generic-pc/playback.h"
#include "../libgeneric-pc/playback_lib.h"
#endif
#endif
#else
#error neither HAVE_TRIPLEDRAGON nor HAVE_SPARK_HARDWARE defined
#error no valid hardware defined
#endif

View File

@@ -1,20 +1,47 @@
#include <config.h>
#if HAVE_TRIPLEDRAGON
#include "../libtriple/pwrmngr.h"
#elif HAVE_DUCKBOX_HARDWARE
#include "../libduckbox/pwrmngr.h"
#elif HAVE_SPARK_HARDWARE
#include "../libspark/pwrmngr.h"
#elif HAVE_ARM_HARDWARE
#include "../libarmbox/pwrmngr.h"
#elif HAVE_AZBOX_HARDWARE
#include "../azbox/pwrmngr.h"
#elif HAVE_GENERIC_HARDWARE
#if BOXMODEL_RASPI
#include "../raspi/pwrmngr.h"
#else
#include "../generic-pc/pwrmngr.h"
#endif
#else
#error neither HAVE_TRIPLEDRAGON nor HAVE_SPARK_HARDWARE defined
#endif
/*
* (C) 2010-2013 Stefan Seyfried
*
* 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.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef __PWRMNGR_H__
#define __PWRMNGR_H__
class cCpuFreqManager
{
public:
cCpuFreqManager(void);
void Up(void);
void Down(void);
void Reset(void);
bool SetCpuFreq(unsigned long CpuFreq);
bool SetDelta(unsigned long Delta);
unsigned long GetCpuFreq(void);
unsigned long GetDelta(void);
};
class cPowerManager
{
public:
cPowerManager(void);
virtual ~cPowerManager();
bool Open(void);
void Close(void);
bool SetStandby(bool Active, bool Passive);
};
#endif // __PWRMNGR_H__

View File

@@ -1,20 +1,18 @@
#include <config.h>
#if HAVE_TRIPLEDRAGON
#include "../libtriple/record_td.h"
#elif HAVE_DUCKBOX_HARDWARE
#if HAVE_DUCKBOX_HARDWARE
#include "../libduckbox/record_lib.h"
#elif HAVE_SPARK_HARDWARE
#include "../libspark/record_lib.h"
#elif HAVE_ARM_HARDWARE
#include "../libarmbox/record_lib.h"
#elif HAVE_AZBOX_HARDWARE
#include "../azbox/record_lib.h"
#elif HAVE_MIPS_HARDWARE
#include "../libmipsbox/record_lib.h"
#elif HAVE_GENERIC_HARDWARE
#if BOXMODEL_RASPI
#include "../raspi/record_lib.h"
#include "../libraspi/record_lib.h"
#else
#include "../generic-pc/record_lib.h"
#include "../libgeneric-pc/record_lib.h"
#endif
#else
#error neither HAVE_TRIPLEDRAGON nor HAVE_SPARK_HARDWARE defined
#error no valid hardware defined
#endif

View File

@@ -1,16 +0,0 @@
#ifndef _REENTRANT_MUTEX_H
#define _REENTRANT_MUTEX_H
#include "mutex_abstraction.h"
class ReentrantMutex : public Mutex
{
ReentrantMutex(const ReentrantMutex&);
const ReentrantMutex& operator=(const ReentrantMutex&);
public:
ReentrantMutex();
virtual ~ReentrantMutex();
};
#endif

View File

@@ -1,18 +0,0 @@
#ifndef _SCOPED_LOCK_H
#define _SCOPED_LOCK_H
#include "mutex_abstraction.h"
class ScopedLock
{
Mutex& mMutex;
ScopedLock(const ScopedLock&);
const ScopedLock& operator=(const ScopedLock&);
public:
ScopedLock(Mutex&);
~ScopedLock();
};
#endif

View File

@@ -1,30 +0,0 @@
#ifndef _THREAD_ABSTRACTION_H
#define _THREAD_ABSTRACTION_H
#include <pthread.h>
class Thread
{
bool mIsRunning;
pthread_t mThread;
static void* runThread(void*);
Thread(const Thread&);
const Thread& operator=(const Thread&);
public:
Thread();
virtual ~Thread();
int startThread();
int cancelThread();
int detachThread();
int joinThread();
int setCancelModeDisable();
int setSchedulePriority(int);
protected:
virtual void run() = 0;
};
#endif

22
include/version_hal.h Normal file
View File

@@ -0,0 +1,22 @@
#ifndef __VERSION_HAL_H__
#define __VERSION_HAL_H__
#include <string>
// library version functions
typedef struct hal_libversion_t
{
std::string vVersion;
int vMajor;
int vMinor;
int vPatch;;
std::string vName;
std::string vStr;
std::string vGitDescribe;
} hal_libversion_struct_t;
void hal_get_lib_version(hal_libversion_t *ver);
#endif //__VERSION_HAL_H__

View File

@@ -1 +0,0 @@
#include "video_hal.h"

View File

@@ -1,22 +1,22 @@
#include <config.h>
#if HAVE_TRIPLEDRAGON
#include "../libtriple/video_td.h"
#elif HAVE_DUCKBOX_HARDWARE
#if HAVE_DUCKBOX_HARDWARE
#include "../libduckbox/video_lib.h"
#elif HAVE_SPARK_HARDWARE
#include "../libspark/video_lib.h"
#elif HAVE_ARM_HARDWARE
#include "../libarmbox/video_lib.h"
#elif HAVE_AZBOX_HARDWARE
#include "../azbox/video_lib.h"
#include "../libarmbox/hdmi_cec.h"
#elif HAVE_MIPS_HARDWARE
#include "../libmipsbox/video_lib.h"
#include "../libmipsbox/hdmi_cec.h"
#elif HAVE_GENERIC_HARDWARE
#if BOXMODEL_RASPI
#include "../raspi/video_lib.h"
#include "../libraspi/video_lib.h"
#else
#include "../generic-pc/video_lib.h"
#include "../libgeneric-pc/video_lib.h"
#endif
#else
#error neither HAVE_TRIPLEDRAGON nor HAVE_SPARK_HARDWARE defined
#error no valid hardware defined
#endif
#if STB_HAL_VIDEO_HAS_GETSCREENIMAGE

View File

@@ -1,7 +1,6 @@
noinst_LTLIBRARIES = libarmbox.la
AM_CPPFLAGS = -D__STDC_FORMAT_MACROS -D__STDC_CONSTANT_MACROS
AM_CPPFLAGS += \
AM_CPPFLAGS = \
-I$(top_srcdir)/common \
-I$(top_srcdir)/include
@@ -13,10 +12,7 @@ AM_LDFLAGS = \
@AVUTIL_LIBS@ \
@AVCODEC_LIBS@ \
@SWRESAMPLE_LIBS@ \
-lpthread -lasound -lrt \
-lgstreamer-1.0 \
-lgsttag-1.0 \
-lgstmpegts-1.0
-lpthread -lass -lrt
libarmbox_la_SOURCES = \
hardware_caps.c \
@@ -24,6 +20,31 @@ libarmbox_la_SOURCES = \
video.cpp \
audio.cpp \
init.cpp \
playback_gst.cpp \
pwrmngr.cpp \
record.cpp
record.cpp \
hdmi_cec.cpp
if ENABLE_GSTREAMER_10
libarmbox_la_SOURCES += \
playback_gst.cpp
AM_LDFLAGS += \
-lgstreamer-1.0 \
-lgsttag-1.0 \
-lgstmpegts-1.0
else
if BOXMODEL_HISILICON
libarmbox_la_SOURCES += \
playback_hisilicon.cpp
else
libarmbox_la_SOURCES += \
playback_libeplayer3.cpp
AM_CPPFLAGS += \
-I$(top_srcdir)/libeplayer3/include
endif
AM_LDFLAGS += \
-lass
endif
AM_CPPFLAGS += -D__STDC_FORMAT_MACROS -D__STDC_CONSTANT_MACROS

View File

@@ -9,13 +9,14 @@
#include <linux/dvb/audio.h>
#include <proc_tools.h>
#include "audio_lib.h"
//#include "audio_mixer.h"
#include "lt_debug.h"
#include "hal_debug.h"
#include <config.h>
#define AUDIO_DEVICE "/dev/dvb/adapter0/audio0"
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_AUDIO, this, args)
#define lt_info(args...) _lt_info(TRIPLE_DEBUG_AUDIO, this, args)
#define hal_debug(args...) _hal_debug(HAL_DEBUG_AUDIO, this, args)
#define hal_info(args...) _hal_info(HAL_DEBUG_AUDIO, this, args)
#include <linux/soundcard.h>
@@ -26,42 +27,30 @@ cAudio::cAudio(void *, void *, void *)
fd = -1;
clipfd = -1;
mixer_fd = -1;
/*
mixerAnalog = mixerHDMI = mixerSPDIF = NULL;
volumeAnalog = volumeHDMI = volumeSPDIF = 0;
mixersMuted = false
*/
openDevice();
Muted = false;
}
cAudio::~cAudio(void)
{
//closeMixers();
closeDevice();
}
void cAudio::openDevice(void)
{
//openMixers();
if (fd < 0)
{
if ((fd = open(AUDIO_DEVICE, O_RDWR)) < 0)
lt_info("openDevice: open failed (%m)\n");
hal_info("openDevice: open failed (%m)\n");
fcntl(fd, F_SETFD, FD_CLOEXEC);
do_mute(true, false);
//do_mute(true, false);
}
else
lt_info("openDevice: already open (fd = %d)\n", fd);
hal_info("openDevice: already open (fd = %d)\n", fd);
}
void cAudio::closeDevice(void)
{
//closeMixers();
if (fd > -1) {
close(fd);
fd = -1;
@@ -78,7 +67,8 @@ void cAudio::closeDevice(void)
int cAudio::do_mute(bool enable, bool remember)
{
lt_debug("%s(%d, %d)\n", __FUNCTION__, enable, remember);
hal_debug("%s(%d, %d)\n", __FUNCTION__, enable, remember);
char str[4];
if (remember)
@@ -87,14 +77,12 @@ int cAudio::do_mute(bool enable, bool remember)
sprintf(str, "%d", Muted);
proc_put("/proc/stb/audio/j1_mute", str, strlen(str));
if (!enable)
if (fd > 0)
{
int f = open("/proc/stb/avs/0/volume", O_RDWR);
read(f, str, 4);
close(f);
str[3] = '\0';
proc_put("/proc/stb/avs/0/volume", str, strlen(str));
if (ioctl(fd, AUDIO_SET_MUTE, enable) < 0)
perror("AUDIO_SET_MUTE");
}
return 0;
}
@@ -104,33 +92,44 @@ int map_volume(const int volume)
if (vol > 100)
vol = 100;
// convert to -1dB steps
vol = 63 - vol * 63 / 100;
// now range is 63..0, where 0 is loudest
#if BOXMODEL_VUPLUS_ALL
if (vol == 63)
vol = 255;
#endif
return vol;
}
int cAudio::setVolume(unsigned int left, unsigned int right)
{
lt_debug("%s(%d, %d)\n", __func__, left, right);
hal_info("cAudio::%s(%d, %d)\n", __func__, left, right);
volume = (left + right) / 2;
int v = map_volume(volume);
#if 0
if (clipfd != -1 && mixer_fd != -1) {
int tmp = 0;
/* not sure if left / right is correct here, but it is always the same anyways ;-) */
if (! Muted)
tmp = left << 8 | right;
int ret = ioctl(mixer_fd, MIXER_WRITE(mixer_num), &tmp);
if (ret == -1)
lt_info("%s: MIXER_WRITE(%d),%04x: %m\n", __func__, mixer_num, tmp);
return ret;
left = map_volume(volume);
right = map_volume(volume);
audio_mixer_t mixer;
mixer.volume_left = left;
mixer.volume_right = right;
if (fd > 0)
{
if (ioctl(fd, AUDIO_SET_MIXER, &mixer) < 0)
perror("AUDIO_SET_MIXER");
}
#endif
char str[4];
sprintf(str, "%d", v);
proc_put("/proc/stb/avs/0/volume", str, strlen(str));
return 0;
}
@@ -138,6 +137,9 @@ int cAudio::Start(void)
{
int ret;
ret = ioctl(fd, AUDIO_PLAY);
#if BOXMODEL_HISILICON
ioctl(fd, AUDIO_CONTINUE);
#endif
return ret;
}
@@ -154,12 +156,10 @@ bool cAudio::Pause(bool Pcm)
void cAudio::SetSyncMode(AVSYNC_TYPE Mode)
{
lt_debug("%s %d\n", __func__, Mode);
hal_debug("%s %d\n", __func__, Mode);
ioctl(fd, AUDIO_SET_AV_SYNC, Mode);
}
// E2 streamtype values. These correspond to
// player2/linux/drivers/media/dvb/stm/dvb/dvb_audio.c:AudioIoctlSetBypassMode
#define AUDIO_STREAMTYPE_AC3 0
#define AUDIO_STREAMTYPE_MPEG 1
#define AUDIO_STREAMTYPE_DTS 2
@@ -169,7 +169,7 @@ void cAudio::SetSyncMode(AVSYNC_TYPE Mode)
void cAudio::SetStreamType(AUDIO_FORMAT type)
{
int bypass = AUDIO_STREAMTYPE_MPEG;
lt_debug("%s %d\n", __FUNCTION__, type);
hal_debug("%s %d\n", __FUNCTION__, type);
StreamType = type;
switch (type)
@@ -194,12 +194,12 @@ void cAudio::SetStreamType(AUDIO_FORMAT type)
// Normaly the encoding should be set using AUDIO_SET_ENCODING
// But as we implemented the behavior to bypass (cause of e2) this is correct here
if (ioctl(fd, AUDIO_SET_BYPASS_MODE, bypass) < 0)
lt_info("%s: AUDIO_SET_BYPASS_MODE failed (%m)\n", __func__);
hal_info("%s: AUDIO_SET_BYPASS_MODE failed (%m)\n", __func__);
}
int cAudio::setChannel(int channel)
{
lt_debug("%s %d\n", __FUNCTION__, channel);
hal_debug("%s %d\n", __FUNCTION__, channel);
return 0;
}
@@ -209,12 +209,13 @@ int cAudio::PrepareClipPlay(int ch, int srate, int bits, int little_endian)
unsigned int devmask, stereo, usable;
const char *dsp_dev = getenv("DSP_DEVICE");
const char *mix_dev = getenv("MIX_DEVICE");
lt_debug("%s ch %d srate %d bits %d le %d\n", __FUNCTION__, ch, srate, bits, little_endian);
hal_info("cAudio::%s ch %d srate %d bits %d le %d\n", __FUNCTION__, ch, srate, bits, little_endian);
if (clipfd > -1) {
lt_info("%s: clipfd already opened (%d)\n", __FUNCTION__, clipfd);
hal_info("%s: clipfd already opened (%d)\n", __func__, clipfd);
return -1;
}
mixer_num = -1;
mixer_fd = -1;
/* a different DSP device can be given with DSP_DEVICE and MIX_DEVICE
* if this device cannot be opened, we fall back to the internal OSS device
* Example:
@@ -225,21 +226,21 @@ int cAudio::PrepareClipPlay(int ch, int srate, int bits, int little_endian)
*/
if ((!dsp_dev) || (access(dsp_dev, W_OK))) {
if (dsp_dev)
lt_info("%s: DSP_DEVICE is set (%s) but cannot be opened,"
" fall back to /dev/dsp\n", __func__, dsp_dev);
hal_info("%s: DSP_DEVICE is set (%s) but cannot be opened,"
" fall back to /dev/dsp\n", __func__, dsp_dev);
dsp_dev = "/dev/dsp";
}
if ((!mix_dev) || (access(mix_dev, W_OK))) {
if (mix_dev)
lt_info("%s: MIX_DEVICE is set (%s) but cannot be opened,"
hal_info("%s: MIX_DEVICE is set (%s) but cannot be opened,"
" fall back to /dev/mixer\n", __func__, dsp_dev);
mix_dev = "/dev/mixer";
}
lt_info("%s: dsp_dev %s mix_dev %s\n", __func__, dsp_dev, mix_dev); /* NULL mix_dev is ok */
hal_info("cAudio::%s: dsp_dev %s mix_dev %s\n", __func__, dsp_dev, mix_dev); /* NULL mix_dev is ok */
/* the tdoss dsp driver seems to work only on the second open(). really. */
clipfd = open(dsp_dev, O_WRONLY);
if (clipfd < 0) {
lt_info("%s open %s: %m\n", dsp_dev, __FUNCTION__);
hal_info("%s open %s: %m\n", dsp_dev, __FUNCTION__);
return -1;
}
fcntl(clipfd, F_SETFD, FD_CLOEXEC);
@@ -254,29 +255,31 @@ int cAudio::PrepareClipPlay(int ch, int srate, int bits, int little_endian)
perror("SNDCTL_DSP_CHANNELS");
if (ioctl(clipfd, SNDCTL_DSP_SPEED, &srate))
perror("SNDCTL_DSP_SPEED");
#if !BOXMODEL_HD51 && !BOXMODEL_BRE2ZE4K && !BOXMODEL_H7
if (ioctl(clipfd, SNDCTL_DSP_RESET))
perror("SNDCTL_DSP_RESET");
#endif
if (!mix_dev)
return 0;
mixer_fd = open(mix_dev, O_RDWR);
if (mixer_fd < 0) {
lt_info("%s: open mixer %s failed (%m)\n", __func__, mix_dev);
hal_info("%s: open mixer %s failed (%m)\n", __func__, mix_dev);
/* not a real error */
return 0;
}
if (ioctl(mixer_fd, SOUND_MIXER_READ_DEVMASK, &devmask) == -1) {
lt_info("%s: SOUND_MIXER_READ_DEVMASK %m\n", __func__);
hal_info("%s: SOUND_MIXER_READ_DEVMASK %m\n", __func__);
devmask = 0;
}
if (ioctl(mixer_fd, SOUND_MIXER_READ_STEREODEVS, &stereo) == -1) {
lt_info("%s: SOUND_MIXER_READ_STEREODEVS %m\n", __func__);
hal_info("%s: SOUND_MIXER_READ_STEREODEVS %m\n", __func__);
stereo = 0;
}
usable = devmask & stereo;
if (usable == 0) {
lt_info("%s: devmask: %08x stereo: %08x, no usable dev :-(\n",
hal_info("%s: devmask: %08x stereo: %08x, no usable dev :-(\n",
__func__, devmask, stereo);
close(mixer_fd);
mixer_fd = -1;
@@ -285,13 +288,13 @@ int cAudio::PrepareClipPlay(int ch, int srate, int bits, int little_endian)
/* __builtin_popcount needs GCC, it counts the set bits... */
if (__builtin_popcount (usable) != 1) {
/* TODO: this code is not yet tested as I have only single-mixer devices... */
lt_info("%s: more than one mixer control: devmask %08x stereo %08x\n"
hal_info("%s: more than one mixer control: devmask %08x stereo %08x\n"
"%s: querying MIX_NUMBER environment variable...\n",
__func__, devmask, stereo, __func__);
const char *tmp = getenv("MIX_NUMBER");
if (tmp)
mixer_num = atoi(tmp);
lt_info("%s: mixer_num is %d -> device %08x\n",
hal_info("%s: mixer_num is %d -> device %08x\n",
__func__, mixer_num, (mixer_num >= 0) ? (1 << mixer_num) : 0);
/* no error checking, you'd better know what you are doing... */
} else {
@@ -308,28 +311,47 @@ int cAudio::PrepareClipPlay(int ch, int srate, int bits, int little_endian)
int cAudio::WriteClip(unsigned char *buffer, int size)
{
int ret;
// lt_debug("cAudio::%s\n", __FUNCTION__);
int ret, __attribute__ ((unused)) count = 1;
// hal_debug("cAudio::%s\n", __FUNCTION__);
if (clipfd < 0) {
lt_info("%s: clipfd not yet opened\n", __FUNCTION__);
hal_info("%s: clipfd not yet opened\n", __FUNCTION__);
return -1;
}
#if BOXMODEL_HD51 || BOXMODEL_BRE2ZE4K || BOXMODEL_H7
again:
#endif
ret = write(clipfd, buffer, size);
if (ret < 0)
lt_info("%s: write error (%m)\n", __FUNCTION__);
if (ret < 0) {
hal_info("%s: write error (%m)\n", __FUNCTION__);
return ret;
}
#if BOXMODEL_HD51 || BOXMODEL_BRE2ZE4K || BOXMODEL_H7
if (ret != size) {
hal_info("cAudio::%s: difference > to write (%d) != written (%d) try (%d) > reset dsp and restart write\n", __FUNCTION__, size, ret, count);
if (ioctl(clipfd, SNDCTL_DSP_RESET))
perror("SNDCTL_DSP_RESET");
count++;
if (count < 3)
goto again;
}
#endif
return ret;
};
int cAudio::StopClip()
{
lt_debug("%s\n", __FUNCTION__);
hal_info("cAudio::%s\n", __FUNCTION__);
if (clipfd < 0) {
lt_info("%s: clipfd not yet opened\n", __FUNCTION__);
hal_info("%s: clipfd not yet opened\n", __FUNCTION__);
return -1;
}
#if BOXMODEL_VUPLUS_ARM
ioctl(clipfd, SNDCTL_DSP_RESET);
#endif
close(clipfd);
clipfd = -1;
if (mixer_fd >= -1) {
if (mixer_fd > -1) {
close(mixer_fd);
mixer_fd = -1;
}
@@ -339,7 +361,7 @@ int cAudio::StopClip()
void cAudio::getAudioInfo(int &type, int &layer, int &freq, int &bitrate, int &mode)
{
lt_debug("%s\n", __FUNCTION__);
hal_debug("%s\n", __FUNCTION__);
type = 0;
layer = 0;
freq = 0;
@@ -388,13 +410,13 @@ void cAudio::getAudioInfo(int &type, int &layer, int &freq, int &bitrate, int &m
void cAudio::SetSRS(int /*iq_enable*/, int /*nmgr_enable*/, int /*iq_mode*/, int /*iq_level*/)
{
lt_debug("%s\n", __FUNCTION__);
hal_debug("%s\n", __FUNCTION__);
};
void cAudio::SetHdmiDD(bool enable)
{
const char *opt[] = { "downmix", "passthrough" };
lt_debug("%s %d\n", __func__, enable);
hal_debug("%s %d\n", __func__, enable);
proc_put("/proc/stb/audio/ac3", opt[enable], strlen(opt[enable]));
}
@@ -402,18 +424,18 @@ void cAudio::SetSpdifDD(bool enable)
{
//using this function for dts passthrough
const char *opt[] = { "downmix", "passthrough" };
lt_debug("%s %d\n", __func__, enable);
hal_debug("%s %d\n", __func__, enable);
proc_put("/proc/stb/audio/dts", opt[enable], strlen(opt[enable]));
}
void cAudio::ScheduleMute(bool On)
{
lt_debug("%s %d\n", __FUNCTION__, On);
hal_debug("%s %d\n", __FUNCTION__, On);
}
void cAudio::EnableAnalogOut(bool enable)
{
lt_debug("%s %d\n", __FUNCTION__, enable);
hal_debug("%s %d\n", __FUNCTION__, enable);
}
#define AUDIO_BYPASS_ON 0
@@ -422,59 +444,5 @@ void cAudio::setBypassMode(bool disable)
{
int mode = disable ? AUDIO_BYPASS_OFF : AUDIO_BYPASS_ON;
if (ioctl(fd, AUDIO_SET_BYPASS_MODE, mode) < 0)
lt_info("%s AUDIO_SET_BYPASS_MODE %d: %m\n", __func__, mode);
hal_info("%s AUDIO_SET_BYPASS_MODE %d: %m\n", __func__, mode);
}
#if 0
void cAudio::openMixers(void)
{
if (!mixerAnalog)
mixerAnalog = new mixerVolume("Analog", "1");
if (!mixerHDMI)
mixerHDMI = new mixerVolume("HDMI", "1");
if (!mixerSPDIF)
mixerSPDIF = new mixerVolume("SPDIF", "1");
}
void cAudio::closeMixers(void)
{
delete mixerAnalog;
delete mixerHDMI;
delete mixerSPDIF;
mixerAnalog = mixerHDMI = mixerSPDIF = NULL;
}
void cAudio::setMixerVolume(const char *name, long value, bool remember)
{
if (!strcmp(name, "Analog")) {
mixerAnalog->setVolume(value);
if (remember)
volumeAnalog = value;
}
if (!strcmp(name, "HDMI")) {
mixerHDMI->setVolume(value);
if (remember)
volumeHDMI = value;
}
if (!strcmp(name, "SPDIF")) {
mixerSPDIF->setVolume(value);
if (remember)
volumeSPDIF = value;
}
}
void cAudio::muteMixers(bool m)
{
if (m && !mixersMuted) {
mixersMuted = true;
setMixerVolume("Analog", 0, false);
setMixerVolume("HDMI", 0, false);
setMixerVolume("SPDIF", 0, false);
} else if (!m && mixersMuted) {
mixersMuted = false;
setMixerVolume("Analog", volumeAnalog, false);
setMixerVolume("HDMI", volumeHDMI, false);
setMixerVolume("SPDIF", volumeSPDIF, false);
}
}
#endif

View File

@@ -1,8 +1,9 @@
/* public header file */
#ifndef _AUDIO_TD_H_
#define _AUDIO_TD_H_
#include "../common/cs_types.h"
#ifndef __AUDIO_LIB_H__
#define __AUDIO_LIB_H__
#include "cs_types.h"
typedef enum
{
@@ -57,10 +58,6 @@ class cAudio
int do_mute(bool enable, bool remember);
void setBypassMode(bool disable);
mixerVolume *mixerAnalog, *mixerHDMI, *mixerSPDIF;
int volumeAnalog, volumeHDMI, volumeSPDIF;
bool mixersMuted;
public:
/* construct & destruct */
cAudio(void *, void *, void *);
@@ -99,13 +96,6 @@ class cAudio
void SetSpdifDD(bool enable);
void ScheduleMute(bool On);
void EnableAnalogOut(bool enable);
#if 0
void openMixers(void);
void closeMixers(void);
void setMixerVolume(const char *name, long value, bool remember = true);
void muteMixers(bool m = true);
#endif
};
#endif
#endif // __AUDIO_LIB_H__

View File

@@ -1,68 +0,0 @@
/*
* audio_mixer.cpp
*
* (C) 2012 martii
*
* 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.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <audio_mixer.h>
mixerVolume::mixerVolume(const char *name, const char *card, long volume) {
snd_mixer_selem_id_t *sid = NULL;
elem = NULL;
handle = NULL;
min = 0;
max = 100;
char cardId[10];
if (!name || !card)
return;
int cx = snd_card_get_index(card);
if (cx < 0 || cx > 31)
return;
snprintf(cardId, sizeof(cardId), "hw:%i", cx);
if (0 > snd_mixer_open(&handle, 0))
return;
if (0 > snd_mixer_attach(handle, cardId))
return;
if (0 > snd_mixer_selem_register(handle, NULL, NULL))
return;
if (0 > snd_mixer_load(handle))
return;
snd_mixer_selem_id_alloca(&sid);
if (!sid)
return;
snd_mixer_selem_id_set_index(sid, 0);
snd_mixer_selem_id_set_name(sid, name);
elem = snd_mixer_find_selem(handle, sid);
if (elem) {
snd_mixer_selem_get_playback_volume_range(elem, &min, &max);
setVolume(volume);
}
}
mixerVolume::~mixerVolume()
{
if (handle)
snd_mixer_close(handle);
}
bool mixerVolume::setVolume(long volume) {
return elem
&& (volume > -1)
&& (volume < 101)
&& !snd_mixer_selem_set_playback_volume_all(elem, min + volume * (max - min)/100);
}

View File

@@ -1,36 +0,0 @@
/*
* audio_mixer.h
*
* (C) 2012 martii
*
* 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.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef __AUDIO_MIXER_H__
#define __AUDIO_MIXER_H__
#include <alsa/asoundlib.h>
class mixerVolume
{
private:
long min, max;
snd_mixer_t *handle;
snd_mixer_elem_t* elem;
public:
mixerVolume(const char *selem_name, const char *Card, long volume = -1);
~mixerVolume(void);
bool setVolume(long volume);
};
#endif

View File

@@ -1,67 +0,0 @@
/* compatibility header for tripledragon. I'm lazy, so I just left it
as "cs_api.h" so that I don't need too many ifdefs in the code */
#ifndef __CS_API_H_
#define __CS_API_H_
#include "init_lib.h"
typedef void (*cs_messenger) (unsigned int msg, unsigned int data);
#if 0
enum CS_LOG_MODULE {
CS_LOG_CI = 0,
CS_LOG_HDMI_CEC,
CS_LOG_HDMI,
CS_LOG_VIDEO,
CS_LOG_VIDEO_DRM,
CS_LOG_AUDIO,
CS_LOG_DEMUX,
CS_LOG_DENC,
CS_LOG_PVR_RECORD,
CS_LOG_PVR_PLAY,
CS_LOG_POWER_CTRL,
CS_LOG_POWER_CLK,
CS_LOG_MEM,
CS_LOG_API,
};
#endif
inline void cs_api_init()
{
init_td_api();
};
inline void cs_api_exit()
{
shutdown_td_api();
};
#define cs_malloc_uncached malloc
#define cs_free_uncached free
// Callback function helpers
void cs_register_messenger(cs_messenger messenger);
static inline void cs_deregister_messenger(void) { return; };
//cs_messenger cs_get_messenger(void);
#if 0
// Logging functions
void cs_log_enable(void);
void cs_log_disable(void);
void cs_log_message(const char *prefix, const char *fmt, ...);
void cs_log_module_enable(enum CS_LOG_MODULE module);
void cs_log_module_disable(enum CS_LOG_MODULE module);
void cs_log_module_message(enum CS_LOG_MODULE module, const char *fmt, ...);
// TS Routing
unsigned int cs_get_ts_output(void);
int cs_set_ts_output(unsigned int port);
// Serial nr and revision accessors
unsigned long long cs_get_serial(void);
#endif
/* compat... HD1 seems to be version 6. everything newer ist > 6... */
static inline unsigned int cs_get_revision(void) { return 1; };
static inline unsigned int cs_get_chip_type(void) { return 0; };
extern int cnxt_debug;
#endif //__CS_API_H_

View File

@@ -1,6 +1,6 @@
/*
* cDemux implementation for SH4 receivers (tested on fulan spark and
* fulan spark7162 hardware)
* cDemux implementation for arm receivers (tested on mutant hd51
* hardware)
*
* derived from libtriple/dmx_td.cpp
*
@@ -20,41 +20,7 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
/*
* Theory of operation (or "why is this dmx_source thing so strange and
* what is the _open() good for?")
*
* the sh4 pti driver, driving the /dev/dvb/adapter0/dmxN devices, can
* apparently only map one input to on demux device at a time, so e.g.
* DMX_SOURCE_FRONT1 -> demux0
* DMX_SOURCE_FRONT2 -> demux0
* DMX_SOURCE_FRONT1 -> demux1
* does not work. The driver makes sure that a one-to-one mapping of
* DMX_SOURCE_FRONTn to demuxM is maintained, and it does by e.g changing
* the default of
* FRONT0 -> demux0
* FRONT1 -> demux1
* FRONT2 -> demux2
* to
* FRONT1 -> demux0
* FRONT0 -> demux1
* FRONT2 -> demux2
* if you do a DMX_SET_SOURCE(FRONT1) ioctl on demux0.
* This means, it also changes demux1's source on the SET_SOURCE ioctl on
* demux0, potentially disturbing any operation on demux1 (e.g. recording).
*
* In order to avoid this, I do not change the source->demuxdev mapping
* but instead just always use the demux device that is attached to the
* correct source.
*
* The tricky part is, that the source might actually be changed after
* Open() has been called, so Open() gets a dummy placeholder that just
* sets some variables while the real device open is put into _open().
* _open() gets called later, whenever the device is actually used or
* configured and -- if the source has changed -- closes the old and
* opens the correct new device node.
*/
#include <config.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
@@ -66,30 +32,31 @@
#include <cstring>
#include <cstdio>
#include <string>
#include "dmx_lib.h"
#include "lt_debug.h"
#include <sys/ioctl.h>
#include <OpenThreads/Mutex>
#include <OpenThreads/ScopedLock>
#include "dmx_hal.h"
#include "hal_debug.h"
#include "video_lib.h"
/* needed for getSTC... */
extern cVideo *videoDecoder;
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_DEMUX, this, args)
#define lt_info(args...) _lt_info(TRIPLE_DEBUG_DEMUX, this, args)
#define lt_info_c(args...) _lt_info(TRIPLE_DEBUG_DEMUX, NULL, args)
#define hal_debug(args...) _hal_debug(HAL_DEBUG_DEMUX, this, args)
#define hal_info(args...) _hal_info(HAL_DEBUG_DEMUX, this, args)
#define hal_debug_c(args...) _hal_debug(HAL_DEBUG_DEMUX, NULL, args)
#define hal_info_c(args...) _hal_info(HAL_DEBUG_DEMUX, NULL, args)
#define hal_info_z(args...) _hal_info(HAL_DEBUG_DEMUX, thiz, args)
#define hal_debug_z(args...) _hal_debug(HAL_DEBUG_DEMUX, thiz, args)
#define dmx_err(_errfmt, _errstr, _revents) do { \
uint16_t _pid = (uint16_t)-1; uint16_t _f = 0;\
if (dmx_type == DMX_PSI_CHANNEL) { \
_pid = s_flt.pid; _f = s_flt.filter.filter[0]; \
} else { \
_pid = p_flt.pid; \
}; \
lt_info("%s " _errfmt " fd:%d, ev:0x%x %s pid:0x%04hx flt:0x%02hx\n", \
__func__, _errstr, fd, _revents, DMX_T[dmx_type], _pid, _f); \
hal_info("%s " _errfmt " fd:%d, ev:0x%x %s pid:0x%04hx flt:0x%02hx\n", \
__func__, _errstr, fd, _revents, DMX_T[dmx_type], pid, flt); \
} while(0);
cDemux *videoDemux = NULL;
cDemux *audioDemux = NULL;
//cDemux *pcrDemux = NULL;
static const char *DMX_T[] = {
"DMX_INVALID",
@@ -104,12 +71,36 @@ static const char *DMX_T[] = {
/* this is the number of different cDemux() units, not the number of
* /dev/dvb/.../demuxX devices! */
#if BOXMODEL_VUULTIMO4K
#define NUM_DEMUX 24
#else
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUDUO4KSE || BOXMODEL_VUUNO4KSE || BOXMODEL_VUUNO4K
#define NUM_DEMUX 16
#else
#define NUM_DEMUX 4
#endif
#endif
/* the current source of each cDemux unit */
#if BOXMODEL_VUULTIMO4K
static int dmx_source[NUM_DEMUX] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
#else
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUDUO4KSE || BOXMODEL_VUUNO4KSE || BOXMODEL_VUUNO4K
static int dmx_source[NUM_DEMUX] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
#else
static int dmx_source[NUM_DEMUX] = { 0, 0, 0, 0 };
#endif
#endif
/* map the device numbers. */
#if BOXMODEL_VUULTIMO4K
#define NUM_DEMUXDEV 24
#else
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUDUO4KSE || BOXMODEL_VUUNO4KSE || BOXMODEL_VUUNO4K
#define NUM_DEMUXDEV 16
#else
#define NUM_DEMUXDEV 8
#endif
#endif
static const char *devname[NUM_DEMUXDEV] = {
"/dev/dvb/adapter0/demux0",
"/dev/dvb/adapter0/demux1",
@@ -119,36 +110,76 @@ static const char *devname[NUM_DEMUXDEV] = {
"/dev/dvb/adapter0/demux5",
"/dev/dvb/adapter0/demux6",
"/dev/dvb/adapter0/demux7"
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUULTIMO4K || BOXMODEL_VUUNO4KSE || BOXMODEL_VUUNO4K
, "/dev/dvb/adapter0/demux8"
, "/dev/dvb/adapter0/demux9"
, "/dev/dvb/adapter0/demux10"
, "/dev/dvb/adapter0/demux11"
, "/dev/dvb/adapter0/demux12"
, "/dev/dvb/adapter0/demux13"
, "/dev/dvb/adapter0/demux14"
, "/dev/dvb/adapter0/demux15"
#if BOXMODEL_VUULTIMO4K
, "/dev/dvb/adapter0/demux16"
, "/dev/dvb/adapter0/demux17"
, "/dev/dvb/adapter0/demux18"
, "/dev/dvb/adapter0/demux19"
, "/dev/dvb/adapter0/demux20"
, "/dev/dvb/adapter0/demux21"
, "/dev/dvb/adapter0/demux22"
, "/dev/dvb/adapter0/demux23"
#endif
#endif
};
/* did we already DMX_SET_SOURCE on that demux device? */
#if BOXMODEL_VUULTIMO4K
static bool init[NUM_DEMUXDEV] = { false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false };
#else
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUDUO4KSE || BOXMODEL_VUUNO4KSE || BOXMODEL_VUUNO4K
static bool init[NUM_DEMUXDEV] = { false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false };
#else
static bool init[NUM_DEMUXDEV] = { false, false, false, false, false, false, false, false };
#endif
#endif
typedef struct dmx_pdata {
int last_source;
OpenThreads::Mutex *mutex;
} dmx_pdata;
#define P ((dmx_pdata *)pdata)
cDemux::cDemux(int n)
{
if (n < 0 || n >= NUM_DEMUX)
{
lt_info("%s ERROR: n invalid (%d)\n", __FUNCTION__, n);
hal_info("%s ERROR: n invalid (%d)\n", __FUNCTION__, n);
num = 0;
}
else
num = n;
fd = -1;
measure = false;
last_measure = 0;
last_data = 0;
last_source = -1;
pdata = (void *)calloc(1, sizeof(dmx_pdata));
P->last_source = -1;
P->mutex = new OpenThreads::Mutex;
dmx_type = DMX_INVALID;
}
cDemux::~cDemux()
{
lt_debug("%s #%d fd: %d\n", __FUNCTION__, num, fd);
hal_debug("%s #%d fd: %d\n", __FUNCTION__, num, fd);
Close();
/* wait until Read() has released the mutex */
(*P->mutex).lock();
(*P->mutex).unlock();
free(P->mutex);
free(pdata);
pdata = NULL;
}
bool cDemux::Open(DMX_CHANNEL_TYPE pes_type, void * /*hVideoBuffer*/, int uBufferSize)
{
if (fd > -1)
lt_info("%s FD ALREADY OPENED? fd = %d\n", __FUNCTION__, fd);
hal_info("%s FD ALREADY OPENED? fd = %d\n", __FUNCTION__, fd);
dmx_type = pes_type;
buffersize = uBufferSize;
@@ -157,18 +188,18 @@ bool cDemux::Open(DMX_CHANNEL_TYPE pes_type, void * /*hVideoBuffer*/, int uBuffe
return true;
}
bool cDemux::_open(void)
static bool _open(cDemux *thiz, int num, int &fd, int &last_source, DMX_CHANNEL_TYPE dmx_type, int buffersize)
{
int flags = O_RDWR|O_CLOEXEC;
int devnum = dmx_source[num];
if (last_source == devnum) {
lt_debug("%s #%d: source (%d) did not change\n", __func__, num, last_source);
hal_debug_z("%s #%d: source (%d) did not change\n", __func__, num, last_source);
if (fd > -1)
return true;
}
if (fd > -1) {
/* we changed source -> close and reopen the fd */
lt_debug("%s #%d: FD ALREADY OPENED fd = %d lastsource %d devnum %d\n",
hal_debug_z("%s #%d: FD ALREADY OPENED fd = %d lastsource %d devnum %d\n",
__func__, num, fd, last_source, devnum);
close(fd);
}
@@ -179,10 +210,10 @@ bool cDemux::_open(void)
fd = open(devname[devnum], flags);
if (fd < 0)
{
lt_info("%s %s: %m\n", __FUNCTION__, devname[devnum]);
hal_info_z("%s %s: %m\n", __FUNCTION__, devname[devnum]);
return false;
}
lt_debug("%s #%d pes_type: %s(%d), uBufferSize: %d fd: %d\n", __func__,
hal_debug_z("%s #%d pes_type: %s(%d), uBufferSize: %d fd: %d\n", __func__,
num, DMX_T[dmx_type], dmx_type, buffersize, fd);
/* this would actually need locking, but the worst that weill happen is, that
@@ -191,9 +222,9 @@ bool cDemux::_open(void)
{
/* this should not change anything... */
int n = DMX_SOURCE_FRONT0 + devnum;
lt_info("%s: setting %s to source %d\n", __func__, devname[devnum], n);
hal_info_z("%s: setting %s to source %d\n", __func__, devname[devnum], n);
if (ioctl(fd, DMX_SET_SOURCE, &n) < 0)
lt_info("%s DMX_SET_SOURCE failed!\n", __func__);
hal_info_z("%s DMX_SET_SOURCE failed!\n", __func__);
else
init[devnum] = true;
}
@@ -203,7 +234,7 @@ bool cDemux::_open(void)
{
/* probably uBufferSize == 0 means "use default size". TODO: find a reasonable default */
if (ioctl(fd, DMX_SET_BUFFER_SIZE, buffersize) < 0)
lt_info("%s DMX_SET_BUFFER_SIZE failed (%m)\n", __func__);
hal_info_z("%s DMX_SET_BUFFER_SIZE failed (%m)\n", __func__);
}
last_source = devnum;
@@ -212,10 +243,10 @@ bool cDemux::_open(void)
void cDemux::Close(void)
{
lt_debug("%s #%d, fd = %d\n", __FUNCTION__, num, fd);
hal_debug("%s #%d, fd = %d\n", __FUNCTION__, num, fd);
if (fd < 0)
{
lt_info("%s #%d: not open!\n", __FUNCTION__, num);
hal_info("%s #%d: not open!\n", __FUNCTION__, num);
return;
}
@@ -223,15 +254,14 @@ void cDemux::Close(void)
ioctl(fd, DMX_STOP);
close(fd);
fd = -1;
if (measure)
return;
}
bool cDemux::Start(bool)
{
hal_debug("%s #%d fd: %d type: %s\n", __func__, num, fd, DMX_T[dmx_type]);
if (fd < 0)
{
lt_info("%s #%d: not open!\n", __FUNCTION__, num);
hal_info("%s #%d: not open!\n", __FUNCTION__, num);
return false;
}
ioctl(fd, DMX_START);
@@ -240,9 +270,10 @@ bool cDemux::Start(bool)
bool cDemux::Stop(void)
{
hal_debug("%s #%d fd: %d type: %s\n", __func__, num, fd, DMX_T[dmx_type]);
if (fd < 0)
{
lt_info("%s #%d: not open!\n", __FUNCTION__, num);
hal_info("%s #%d: not open!\n", __FUNCTION__, num);
return false;
}
ioctl(fd, DMX_STOP);
@@ -258,9 +289,11 @@ int cDemux::Read(unsigned char *buff, int len, int timeout)
#endif
if (fd < 0)
{
lt_info("%s #%d: not open!\n", __func__, num);
hal_info("%s #%d: not open!\n", __func__, num);
return -1;
}
/* avoid race in destructor: ~cDemux needs to wait until Read() returns */
OpenThreads::ScopedLock<OpenThreads::Mutex> m_lock(*P->mutex);
int rc;
int to = timeout;
struct pollfd ufds;
@@ -278,6 +311,12 @@ int cDemux::Read(unsigned char *buff, int len, int timeout)
{
retry:
rc = ::poll(&ufds, 1, to);
if (ufds.fd != fd)
{
/* Close() will set fd to -1, this is normal. Everything else is not. */
hal_info("%s:1 ========== fd has changed, %d->%d ==========\n", __func__, ufds.fd, fd);
return -1;
}
if (!rc)
{
if (timeout == 0) /* we took the emergency exit */
@@ -290,7 +329,7 @@ int cDemux::Read(unsigned char *buff, int len, int timeout)
else if (rc < 0)
{
dmx_err("poll: %s,", strerror(errno), 0)
//lt_info("%s poll: %m\n", __FUNCTION__);
//hal_info("%s poll: %m\n", __FUNCTION__);
/* happens, when running under gdb... */
if (errno == EINTR)
goto retry;
@@ -315,6 +354,11 @@ int cDemux::Read(unsigned char *buff, int len, int timeout)
return 0;
}
}
if (ufds.fd != fd) /* does this ever happen? and if, is it harmful? */
{ /* read(-1,...) will just return EBADF anyway... */
hal_info("%s:2 ========== fd has changed, %d->%d ==========\n", __func__, ufds.fd, fd);
return -1;
}
rc = ::read(fd, buff, len);
//fprintf(stderr, "fd %d ret: %d\n", fd, rc);
@@ -324,19 +368,22 @@ int cDemux::Read(unsigned char *buff, int len, int timeout)
return rc;
}
bool cDemux::sectionFilter(unsigned short pid, const unsigned char * const filter,
bool cDemux::sectionFilter(unsigned short _pid, const unsigned char * const filter,
const unsigned char * const mask, int len, int timeout,
const unsigned char * const negmask)
{
struct dmx_sct_filter_params s_flt;
memset(&s_flt, 0, sizeof(s_flt));
pid = _pid;
_open();
_open(this, num, fd, P->last_source, dmx_type, buffersize);
if (len > DMX_FILTER_SIZE)
{
lt_info("%s #%d: len too long: %d, DMX_FILTER_SIZE %d\n", __func__, num, len, DMX_FILTER_SIZE);
hal_info("%s #%d: len too long: %d, DMX_FILTER_SIZE %d\n", __func__, num, len, DMX_FILTER_SIZE);
len = DMX_FILTER_SIZE;
}
flt = filter[0];
s_flt.pid = pid;
s_flt.timeout = timeout;
memcpy(s_flt.filter.filter, filter, len);
@@ -347,79 +394,80 @@ bool cDemux::sectionFilter(unsigned short pid, const unsigned char * const filte
s_flt.flags = DMX_IMMEDIATE_START|DMX_CHECK_CRC;
int to = 0;
switch (filter[0]) {
case 0x00: /* program_association_section */
to = 2000;
break;
case 0x01: /* conditional_access_section */
to = 6000;
break;
case 0x02: /* program_map_section */
to = 1500;
break;
case 0x03: /* transport_stream_description_section */
to = 10000;
break;
/* 0x04 - 0x3F: reserved */
case 0x40: /* network_information_section - actual_network */
to = 10000;
break;
case 0x41: /* network_information_section - other_network */
to = 15000;
break;
case 0x42: /* service_description_section - actual_transport_stream */
to = 10000;
break;
/* 0x43 - 0x45: reserved for future use */
case 0x46: /* service_description_section - other_transport_stream */
to = 10000;
break;
/* 0x47 - 0x49: reserved for future use */
case 0x4A: /* bouquet_association_section */
to = 11000;
break;
/* 0x4B - 0x4D: reserved for future use */
case 0x4E: /* event_information_section - actual_transport_stream, present/following */
to = 2000;
break;
case 0x4F: /* event_information_section - other_transport_stream, present/following */
to = 10000;
break;
/* 0x50 - 0x5F: event_information_section - actual_transport_stream, schedule */
/* 0x60 - 0x6F: event_information_section - other_transport_stream, schedule */
case 0x70: /* time_date_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
s_flt.flags |= DMX_ONESHOT;
//s_flt.pid = 0x0014;
to = 30000;
break;
case 0x71: /* running_status_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
to = 0;
break;
case 0x72: /* stuffing_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
to = 0;
break;
case 0x73: /* time_offset_section */
s_flt.flags |= DMX_ONESHOT;
//s_flt.pid = 0x0014;
to = 30000;
break;
/* 0x74 - 0x7D: reserved for future use */
case 0x7E: /* discontinuity_information_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
to = 0;
break;
case 0x7F: /* selection_information_section */
to = 0;
break;
/* 0x80 - 0x8F: ca_message_section */
/* 0x90 - 0xFE: user defined */
/* 0xFF: reserved */
default:
break;
// return -1;
switch (filter[0])
{
case 0x00: /* program_association_section */
to = 2000;
break;
case 0x01: /* conditional_access_section */
to = 6000;
break;
case 0x02: /* program_map_section */
to = 1500;
break;
case 0x03: /* transport_stream_description_section */
to = 10000;
break;
/* 0x04 - 0x3F: reserved */
case 0x40: /* network_information_section - actual_network */
to = 10000;
break;
case 0x41: /* network_information_section - other_network */
to = 15000;
break;
case 0x42: /* service_description_section - actual_transport_stream */
to = 10000;
break;
/* 0x43 - 0x45: reserved for future use */
case 0x46: /* service_description_section - other_transport_stream */
to = 10000;
break;
/* 0x47 - 0x49: reserved for future use */
case 0x4A: /* bouquet_association_section */
to = 11000;
break;
/* 0x4B - 0x4D: reserved for future use */
case 0x4E: /* event_information_section - actual_transport_stream, present/following */
to = 2000;
break;
case 0x4F: /* event_information_section - other_transport_stream, present/following */
to = 10000;
break;
/* 0x50 - 0x5F: event_information_section - actual_transport_stream, schedule */
/* 0x60 - 0x6F: event_information_section - other_transport_stream, schedule */
case 0x70: /* time_date_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
s_flt.flags |= DMX_ONESHOT;
//s_flt.pid = 0x0014;
to = 30000;
break;
case 0x71: /* running_status_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
to = 0;
break;
case 0x72: /* stuffing_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
to = 0;
break;
case 0x73: /* time_offset_section */
s_flt.flags |= DMX_ONESHOT;
//s_flt.pid = 0x0014;
to = 30000;
break;
/* 0x74 - 0x7D: reserved for future use */
case 0x7E: /* discontinuity_information_section */
s_flt.flags &= ~DMX_CHECK_CRC; /* section has no CRC */
to = 0;
break;
case 0x7F: /* selection_information_section */
to = 0;
break;
/* 0x80 - 0x8F: ca_message_section */
/* 0x90 - 0xFE: user defined */
/* 0xFF: reserved */
default:
//return -1;
break;
}
/* the negmask == NULL is a hack: the users of negmask are PMT-update
* and sectionsd EIT-Version change. And they really want no timeout
@@ -427,12 +475,12 @@ bool cDemux::sectionFilter(unsigned short pid, const unsigned char * const filte
if (timeout == 0 && negmask == NULL)
s_flt.timeout = to;
lt_debug("%s #%d pid:0x%04hx fd:%d type:%s len:%d to:%d flags:%x flt[0]:%02x\n", __func__, num,
pid, fd, DMX_T[dmx_type], len, s_flt.timeout,s_flt.flags, s_flt.filter.filter[0]);
hal_debug("%s #%d pid:0x%04hx fd:%d type:%s len:%d to:%d flags:%x flt[0]:%02x\n", __func__, num,
pid, fd, DMX_T[dmx_type], len, s_flt.timeout, s_flt.flags, s_flt.filter.filter[0]);
#if 0
fprintf(stderr,"filt: ");for(int i=0;i<FILTER_LENGTH;i++)fprintf(stderr,"%02hhx ",s_flt.filter[i]);fprintf(stderr,"\n");
fprintf(stderr,"mask: ");for(int i=0;i<FILTER_LENGTH;i++)fprintf(stderr,"%02hhx ",s_flt.mask [i]);fprintf(stderr,"\n");
fprintf(stderr,"posi: ");for(int i=0;i<FILTER_LENGTH;i++)fprintf(stderr,"%02hhx ",s_flt.positive[i]);fprintf(stderr,"\n");
fprintf(stderr,"filt: "); for (int i = 0; i < len; i++) fprintf(stderr, "%02hhx ", s_flt.filter.filter[i]); fprintf(stderr, "\n");
fprintf(stderr,"mask: "); for (int i = 0; i < len; i++) fprintf(stderr, "%02hhx ", s_flt.filter.mask [i]); fprintf(stderr, "\n");
fprintf(stderr,"mode: "); for (int i = 0; i < len; i++) fprintf(stderr, "%02hhx ", s_flt.filter.mode [i]); fprintf(stderr, "\n");
#endif
ioctl (fd, DMX_STOP);
if (ioctl(fd, DMX_SET_FILTER, &s_flt) < 0)
@@ -441,8 +489,11 @@ bool cDemux::sectionFilter(unsigned short pid, const unsigned char * const filte
return true;
}
bool cDemux::pesFilter(const unsigned short pid)
bool cDemux::pesFilter(const unsigned short _pid)
{
struct dmx_pes_filter_params p_flt;
pid = _pid;
flt = 0;
/* allow PID 0 for web streaming e.g.
* this check originally is from tuxbox cvs but I'm not sure
* what it is good for...
@@ -452,9 +503,9 @@ bool cDemux::pesFilter(const unsigned short pid)
if ((pid >= 0x0002 && pid <= 0x000f) || pid >= 0x1fff)
return false;
lt_debug("%s #%d pid: 0x%04hx fd: %d type: %s\n", __FUNCTION__, num, pid, fd, DMX_T[dmx_type]);
hal_debug("%s #%d pid: 0x%04hx fd: %d type: %s\n", __FUNCTION__, num, pid, fd, DMX_T[dmx_type]);
_open();
_open(this, num, fd, P->last_source, dmx_type, buffersize);
memset(&p_flt, 0, sizeof(p_flt));
p_flt.pid = pid;
@@ -462,70 +513,71 @@ bool cDemux::pesFilter(const unsigned short pid)
p_flt.input = DMX_IN_FRONTEND;
p_flt.flags = 0;
switch (dmx_type) {
case DMX_PCR_ONLY_CHANNEL:
p_flt.pes_type = DMX_PES_PCR;
break;
case DMX_AUDIO_CHANNEL:
p_flt.pes_type = DMX_PES_AUDIO;
break;
case DMX_VIDEO_CHANNEL:
p_flt.pes_type = DMX_PES_VIDEO;
break;
case DMX_PIP_CHANNEL: /* PIP is a special version of DMX_VIDEO_CHANNEL */
p_flt.pes_type = DMX_PES_VIDEO1;
break;
case DMX_PES_CHANNEL:
p_flt.pes_type = DMX_PES_OTHER;
p_flt.output = DMX_OUT_TAP;
break;
case DMX_TP_CHANNEL:
p_flt.pes_type = DMX_PES_OTHER;
p_flt.output = DMX_OUT_TSDEMUX_TAP;
break;
default:
lt_info("%s #%d invalid dmx_type %d!\n", __func__, num, dmx_type);
return false;
switch (dmx_type)
{
case DMX_PCR_ONLY_CHANNEL:
p_flt.pes_type = DMX_PES_PCR;
break;
case DMX_AUDIO_CHANNEL:
p_flt.pes_type = DMX_PES_AUDIO;
break;
case DMX_VIDEO_CHANNEL:
p_flt.pes_type = DMX_PES_VIDEO;
break;
case DMX_PIP_CHANNEL: /* PIP is a special version of DMX_VIDEO_CHANNEL */
p_flt.pes_type = DMX_PES_VIDEO1;
break;
case DMX_PES_CHANNEL:
p_flt.pes_type = DMX_PES_OTHER;
p_flt.output = DMX_OUT_TAP;
break;
case DMX_TP_CHANNEL:
p_flt.pes_type = DMX_PES_OTHER;
p_flt.output = DMX_OUT_TSDEMUX_TAP;
break;
default:
hal_info("%s #%d invalid dmx_type %d!\n", __func__, num, dmx_type);
return false;
}
return (ioctl(fd, DMX_SET_PES_FILTER, &p_flt) >= 0);
}
void cDemux::SetSyncMode(AVSYNC_TYPE /*mode*/)
{
lt_debug("%s #%d\n", __FUNCTION__, num);
hal_debug("%s #%d\n", __FUNCTION__, num);
}
void *cDemux::getBuffer()
{
lt_debug("%s #%d\n", __FUNCTION__, num);
hal_debug("%s #%d\n", __FUNCTION__, num);
return NULL;
}
void *cDemux::getChannel()
{
lt_debug("%s #%d\n", __FUNCTION__, num);
hal_debug("%s #%d\n", __FUNCTION__, num);
return NULL;
}
bool cDemux::addPid(unsigned short Pid)
{
lt_debug("%s: pid 0x%04hx\n", __func__, Pid);
hal_debug("%s: pid 0x%04hx\n", __func__, Pid);
pes_pids pfd;
int ret;
if (dmx_type != DMX_TP_CHANNEL)
{
lt_info("%s pes_type %s not implemented yet! pid=%hx\n", __FUNCTION__, DMX_T[dmx_type], Pid);
hal_info("%s pes_type %s not implemented yet! pid=%hx\n", __FUNCTION__, DMX_T[dmx_type], Pid);
return false;
}
_open();
_open(this, num, fd, P->last_source, dmx_type, buffersize);
if (fd == -1)
lt_info("%s bucketfd not yet opened? pid=%hx\n", __FUNCTION__, Pid);
hal_info("%s bucketfd not yet opened? pid=%hx\n", __FUNCTION__, Pid);
pfd.fd = fd; /* dummy */
pfd.pid = Pid;
pesfds.push_back(pfd);
ret = (ioctl(fd, DMX_ADD_PID, &Pid));
if (ret < 0)
lt_info("%s: DMX_ADD_PID (%m) pid=%hx\n", __func__, Pid);
hal_info("%s: DMX_ADD_PID (%m) pid=%hx\n", __func__, Pid);
return (ret != -1);
}
@@ -533,27 +585,27 @@ void cDemux::removePid(unsigned short Pid)
{
if (dmx_type != DMX_TP_CHANNEL)
{
lt_info("%s pes_type %s not implemented yet! pid=%hx\n", __FUNCTION__, DMX_T[dmx_type], Pid);
hal_info("%s pes_type %s not implemented yet! pid=%hx\n", __FUNCTION__, DMX_T[dmx_type], Pid);
return;
}
for (std::vector<pes_pids>::iterator i = pesfds.begin(); i != pesfds.end(); ++i)
{
if ((*i).pid == Pid) {
lt_debug("removePid: removing demux fd %d pid 0x%04x\n", fd, Pid);
hal_debug("removePid: removing demux fd %d pid 0x%04x\n", fd, Pid);
if (ioctl(fd, DMX_REMOVE_PID, Pid) < 0)
lt_info("%s: (DMX_REMOVE_PID, 0x%04hx): %m\n", __func__, Pid);
hal_info("%s: (DMX_REMOVE_PID, 0x%04hx): %m\n", __func__, Pid);
pesfds.erase(i);
return; /* TODO: what if the same PID is there multiple times */
}
}
lt_info("%s pid 0x%04x not found\n", __FUNCTION__, Pid);
hal_info("%s pid 0x%04x not found\n", __FUNCTION__, Pid);
}
void cDemux::getSTC(int64_t * STC)
{
/* apparently I can only get the PTS of the video decoder,
* but that's good enough for dvbsub */
lt_debug("%s #%d\n", __func__, num);
hal_debug("%s #%d\n", __func__, num);
int64_t pts = 0;
if (videoDecoder)
pts = videoDecoder->GetPTS();
@@ -562,7 +614,7 @@ void cDemux::getSTC(int64_t * STC)
int cDemux::getUnit(void)
{
lt_debug("%s #%d\n", __FUNCTION__, num);
hal_debug("%s #%d\n", __FUNCTION__, num);
/* just guessed that this is the right thing to do.
right now this is only used by the CA code which is stubbed out
anyway */
@@ -572,12 +624,12 @@ int cDemux::getUnit(void)
bool cDemux::SetSource(int unit, int source)
{
if (unit >= NUM_DEMUX || unit < 0) {
lt_info_c("%s: unit (%d) out of range, NUM_DEMUX %d\n", __func__, unit, NUM_DEMUX);
hal_info_c("%s: unit (%d) out of range, NUM_DEMUX %d\n", __func__, unit, NUM_DEMUX);
return false;
}
lt_info_c("%s(%d, %d) => %d to %d\n", __func__, unit, source, dmx_source[unit], source);
hal_debug_c("%s(%d, %d) => %d to %d\n", __func__, unit, source, dmx_source[unit], source);
if (source < 0 || source >= NUM_DEMUXDEV)
lt_info_c("%s(%d, %d) ERROR: source %d out of range!\n", __func__, unit, source, source);
hal_info_c("%s(%d, %d) ERROR: source %d out of range!\n", __func__, unit, source, source);
else
dmx_source[unit] = source;
return true;
@@ -586,9 +638,9 @@ bool cDemux::SetSource(int unit, int source)
int cDemux::GetSource(int unit)
{
if (unit >= NUM_DEMUX || unit < 0) {
lt_info_c("%s: unit (%d) out of range, NUM_DEMUX %d\n", __func__, unit, NUM_DEMUX);
hal_info_c("%s: unit (%d) out of range, NUM_DEMUX %d\n", __func__, unit, NUM_DEMUX);
return -1;
}
lt_info_c("%s(%d) => %d\n", __func__, unit, dmx_source[unit]);
hal_debug_c("%s(%d) => %d\n", __func__, unit, dmx_source[unit]);
return dmx_source[unit];
}

View File

@@ -1 +0,0 @@
#include "dmx_lib.h"

View File

@@ -1,72 +0,0 @@
#ifndef __DEMUX_TD_H
#define __DEMUX_TD_H
#include <cstdlib>
#include <vector>
#include <inttypes.h>
#include <sys/ioctl.h>
#include <linux/dvb/dmx.h>
#include "../common/cs_types.h"
#define MAX_DMX_UNITS 4
typedef enum
{
DMX_INVALID = 0,
DMX_VIDEO_CHANNEL = 1,
DMX_AUDIO_CHANNEL,
DMX_PES_CHANNEL,
DMX_PSI_CHANNEL,
DMX_PIP_CHANNEL,
DMX_TP_CHANNEL,
DMX_PCR_ONLY_CHANNEL
} DMX_CHANNEL_TYPE;
typedef struct
{
int fd;
unsigned short pid;
} pes_pids;
class cDemux
{
private:
int num;
int fd;
int buffersize;
bool measure;
uint64_t last_measure, last_data;
DMX_CHANNEL_TYPE dmx_type;
std::vector<pes_pids> pesfds;
struct dmx_sct_filter_params s_flt;
struct dmx_pes_filter_params p_flt;
int last_source;
bool _open(void);
public:
bool Open(DMX_CHANNEL_TYPE pes_type, void * unused = NULL, int bufsize = 0);
void Close(void);
bool Start(bool record = false);
bool Stop(void);
int Read(unsigned char *buff, int len, int Timeout = 0);
bool sectionFilter(unsigned short pid, const unsigned char * const filter, const unsigned char * const mask, int len, int Timeout = 0, const unsigned char * const negmask = NULL);
bool pesFilter(const unsigned short pid);
void SetSyncMode(AVSYNC_TYPE mode);
void * getBuffer();
void * getChannel();
DMX_CHANNEL_TYPE getChannelType(void) { return dmx_type; };
bool addPid(unsigned short pid);
void getSTC(int64_t * STC);
int getUnit(void);
static bool SetSource(int unit, int source);
static int GetSource(int unit);
// TD only functions
int getFD(void) { return fd; }; /* needed by cPlayback class */
void removePid(unsigned short Pid); /* needed by cRecord class */
std::vector<pes_pids> getPesPids(void) { return pesfds; };
//
cDemux(int num = 0);
~cDemux();
};
#endif //__DEMUX_H

View File

@@ -7,6 +7,7 @@
* License: GPL v2 or later
*/
#include <config.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
@@ -28,16 +29,270 @@ hw_caps_t *get_hwcaps(void)
memset(&caps, 0, sizeof(hw_caps_t));
#if BOXMODEL_VUSOLO4K
initialized = 1;
caps.has_CI = 1;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_xres = 480;
caps.display_yres = 320;
caps.display_type = HW_DISPLAY_GFX;
caps.display_can_deepstandby = 0; // 0 because we use graphlcd/lcd4linux
caps.display_can_set_brightness = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_statusline = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_colon = 0;
caps.has_button_timer = 1;
caps.has_button_vformat = 0;
caps.has_HDMI = 1;
strcpy(caps.boxvendor, "VU+");
strcpy(caps.boxname, "SOLO4K");
strcpy(caps.boxarch, "BCM7376");
#endif
#if BOXMODEL_VUDUO4K
initialized = 1;
caps.has_CI = 2;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_xres = 480;
caps.display_yres = 320;
caps.display_type = HW_DISPLAY_GFX;
caps.display_can_deepstandby = 0; // 0 because we use graphlcd/lcd4linux
caps.display_can_set_brightness = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_statusline = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_colon = 0;
caps.has_button_timer = 1;
caps.has_button_vformat = 0;
caps.has_HDMI = 2;
strcpy(caps.boxvendor, "VU+");
strcpy(caps.boxname, "DUO4K");
strcpy(caps.boxarch, "BCM7278");
#endif
#if BOXMODEL_VUDUO4KSE
initialized = 1;
caps.has_CI = 2;
caps.can_cec = 1;
caps.can_shutdown = 1;
caps.display_xres = 480;
caps.display_yres = 320;
caps.display_type = HW_DISPLAY_GFX;
caps.display_can_deepstandby = 0; // 0 because we use graphlcd/lcd4linux
caps.display_can_set_brightness = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_statusline = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_colon = 0;
caps.has_button_timer = 1;
caps.has_HDMI = 2;
strcpy(caps.boxvendor, "VU+");
strcpy(caps.boxname, "DUO4KSE");
strcpy(caps.boxarch, "BCM7444S");
#endif
#if BOXMODEL_VUULTIMO4K
initialized = 1;
caps.has_CI = 2;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_xres = 800;
caps.display_yres = 480;
caps.display_type = HW_DISPLAY_GFX;
caps.display_can_deepstandby = 0; // 0 because we use graphlcd/lcd4linux
caps.display_can_set_brightness = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_statusline = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_colon = 0;
caps.has_button_timer = 1;
caps.has_button_vformat = 0;
caps.has_HDMI = 2;
strcpy(caps.boxvendor, "VU+");
strcpy(caps.boxname, "ULTIMO4K");
strcpy(caps.boxarch, "BCM7444S");
#endif
#if BOXMODEL_VUZERO4K
initialized = 1;
caps.has_CI = 1;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_type = HW_DISPLAY_LED_ONLY;
caps.display_can_deepstandby = 0;
caps.display_can_set_brightness = 1;
caps.display_has_statusline = 0;
caps.display_has_colon = 0;
caps.has_button_timer = 1;
caps.has_button_vformat = 0;
caps.has_HDMI = 1;
strcpy(caps.boxvendor, "VU+");
strcpy(caps.boxname, "ZERO4K");
strcpy(caps.boxarch, "BCM72604");
#endif
#if BOXMODEL_VUUNO4KSE
initialized = 1;
caps.has_CI = 1;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_xres = 400;
caps.display_yres = 240;
caps.display_type = HW_DISPLAY_GFX;
caps.display_can_deepstandby = 0; // 0 because we use graphlcd/lcd4linux
caps.display_can_set_brightness = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_statusline = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_colon = 0;
caps.has_button_timer = 1;
caps.has_button_vformat = 0;
caps.has_HDMI = 2;
strcpy(caps.boxvendor, "VU+");
strcpy(caps.boxname, "UNO4KSE");
strcpy(caps.boxarch, "BCM7252S");
#endif
#if BOXMODEL_VUUNO4K
initialized = 1;
caps.has_CI = 1;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_type = HW_DISPLAY_LED_ONLY;
caps.display_can_deepstandby = 0;
caps.display_can_set_brightness = 1;
caps.display_has_statusline = 0;
caps.display_has_colon = 0;
caps.has_button_timer = 1;
caps.has_button_vformat = 0;
caps.has_HDMI = 1;
strcpy(caps.boxvendor, "VU+");
strcpy(caps.boxname, "UNO4K");
strcpy(caps.boxarch, "BCM7252S");
#endif
#if BOXMODEL_HD51
initialized = 1;
caps.has_CI = 1;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_xres = 16;
caps.display_type = HW_DISPLAY_LINE_TEXT;
caps.display_can_deepstandby = 0;
caps.display_can_set_brightness = 1;
caps.display_has_statusline = 0;
caps.display_has_colon = 0;
caps.has_button_timer = 1;
caps.has_button_vformat = 0;
caps.has_HDMI = 1;
strcpy(caps.boxvendor, "AX-Technologies");
strcpy(caps.boxname, "HD51");
strcpy(caps.boxarch, "BCM7251S");
#endif
#if BOXMODEL_HD60
initialized = 1;
caps.has_CI = 0;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_xres = 4;
caps.display_type = HW_DISPLAY_LED_NUM;
caps.display_can_deepstandby = 0;
caps.display_can_set_brightness = 1;
caps.display_has_statusline = 0;
caps.display_has_colon = 1;
caps.has_button_timer = 1;
caps.has_button_vformat = 0;
caps.has_HDMI = 1;
strcpy(caps.boxvendor, "AX-Technologies");
strcpy(caps.boxname, "HD60");
strcpy(caps.boxarch, "HI3798M");
#endif
#if BOXMODEL_HD61
initialized = 1;
caps.has_CI = 2;
caps.can_cec = 1;
caps.can_shutdown = 1;
caps.display_xres = 4;
caps.display_type = HW_DISPLAY_LED_NUM;
caps.display_can_deepstandby = 0;
caps.display_can_set_brightness = 1;
caps.display_has_statusline = 0;
caps.has_button_timer = 1;
caps.has_HDMI = 1;
strcpy(caps.boxvendor, "AX-Technologies");
strcpy(caps.boxname, "HD61");
strcpy(caps.boxarch, "HI3798M");
#endif
#if BOXMODEL_BRE2ZE4K
initialized = 1;
caps.has_CI = 1;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_xres = 4;
caps.display_type = HW_DISPLAY_LED_NUM;
caps.display_can_deepstandby = 0;
caps.display_can_set_brightness = 1;
caps.display_has_statusline = 0;
caps.display_has_colon = 1;
caps.has_button_timer = 1;
caps.has_button_vformat = 1;
caps.has_HDMI = 1;
strcpy(caps.boxvendor, "WWIO");
strcpy(caps.boxname, "BRE2ZE4K");
strcpy(caps.boxarch, "BCM7251S");
#endif
#if BOXMODEL_H7
initialized = 1;
caps.has_CI = 1;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_xres = 4;
caps.display_type = HW_DISPLAY_LED_NUM;
caps.display_can_deepstandby = 0;
caps.display_can_set_brightness = 1;
caps.display_has_statusline = 0;
caps.display_has_colon = 1;
caps.has_button_timer = 1;
caps.has_button_vformat = 0;
caps.has_HDMI = 1;
strcpy(caps.boxvendor, "AirDigital");
strcpy(caps.boxname, "Zgemma H7C/S");
strcpy(caps.boxarch, "BCM7251S");
#endif
#if BOXMODEL_OSMIO4K
initialized = 1;
caps.has_CI = 0;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_xres = 4;
caps.display_type = HW_DISPLAY_LED_NUM;
caps.display_can_deepstandby = 0;
caps.display_can_set_brightness = 1;
caps.display_has_statusline = 1;
caps.display_has_colon = 1;
caps.has_button_timer = 1;
caps.has_button_vformat = 1;
caps.has_HDMI = 1;
strcpy(caps.boxvendor, "Edision");
strcpy(caps.boxname, "OS mio 4K");
strcpy(caps.boxarch, "BCM72604");
#endif
#if BOXMODEL_OSMIO4KPLUS
initialized = 1;
caps.has_CI = 0;
caps.can_cec = 1;
caps.can_cpufreq = 0;
caps.can_shutdown = 1;
caps.display_xres = 128;
caps.display_yres = 64;
caps.display_type = HW_DISPLAY_GFX;
caps.display_can_deepstandby = 0; // 0 because we use graphlcd/lcd4linux
caps.display_can_set_brightness = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_statusline = 0; // 0 because we use graphlcd/lcd4linux
caps.display_has_colon = 0;
caps.has_button_timer = 1;
caps.has_button_vformat = 1;
caps.has_HDMI = 1;
strcpy(caps.boxvendor, "Edision");
strcpy(caps.boxname, "OS mio+ 4K");
strcpy(caps.boxarch, "BCM72604");
#endif
return &caps;
}

834
libarmbox/hdmi_cec.cpp Normal file
View File

@@ -0,0 +1,834 @@
/*
Copyright (C) 2018-2020 TangoCash
License: GPLv2
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;
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.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <fcntl.h>
#include <sys/ioctl.h>
#include <sys/mman.h>
#include <sys/epoll.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <utime.h>
#include <errno.h>
#include <ctype.h>
#include <array>
#include <cstring>
#include <cstdio>
#include <cstdlib>
#include <linux/input.h>
#include "linux-uapi-cec.h"
#include "hdmi_cec.h"
#include "hdmi_cec_types.h"
#include "hal_debug.h"
#define RED "\x1B[31m"
#define GREEN "\x1B[32m"
#define NORMAL "\x1B[0m"
#define EPOLL_WAIT_TIMEOUT (-1)
#define EPOLL_MAX_EVENTS (1)
#define hal_debug(args...) _hal_debug(HAL_DEBUG_INIT, this, args)
#define hal_info(args...) _hal_info(HAL_DEBUG_INIT, this, args)
#define hal_debug_c(args...) _hal_debug(HAL_DEBUG_INIT, NULL, args)
#define hal_info_c(args...) _hal_info(HAL_DEBUG_INIT, NULL, args)
#define fop(cmd, args...) ({ \
int _r; \
if (fd >= 0) { \
if ((_r = ::cmd(fd, args)) < 0) \
hal_info(#cmd"(fd, "#args")\n"); \
else \
hal_debug(#cmd"(fd, "#args")\n");\
} \
else { _r = fd; } \
_r; \
})
#define CEC_FALLBACK_DEVICE "/dev/cec0"
#define CEC_HDMIDEV "/dev/hdmi_cec"
#if BOXMODEL_H7
#define RC_DEVICE "/dev/input/event2"
#else
#define RC_DEVICE "/dev/input/event1"
#endif
hdmi_cec * hdmi_cec::hdmi_cec_instance = NULL;
//hack to get an instance before first call
hdmi_cec * CEC = hdmi_cec::getInstance();
hdmi_cec::hdmi_cec()
{
standby_cec_activ = autoview_cec_activ = standby = muted = false;
hdmiFd = -1;
volume = 0;
fallback = false;
tv_off = true;
deviceType = CEC_LOG_ADDR_TYPE_UNREGISTERED;
}
hdmi_cec::~hdmi_cec()
{
if (hdmiFd >= 0)
{
close(hdmiFd);
hdmiFd = -1;
}
}
hdmi_cec* hdmi_cec::getInstance()
{
if (hdmi_cec_instance == NULL)
{
hdmi_cec_instance = new hdmi_cec();
hal_info_c(GREEN "[CEC] new instance created \n" NORMAL);
}
return hdmi_cec_instance;
}
bool hdmi_cec::SetCECMode(VIDEO_HDMI_CEC_MODE _deviceType)
{
physicalAddress[0] = 0x10;
physicalAddress[1] = 0x00;
logicalAddress = 1;
if (_deviceType == VIDEO_HDMI_CEC_MODE_OFF)
{
Stop();
hal_info(GREEN "[CEC] switch off %s\n" NORMAL, __func__);
return false;
}
else
deviceType = _deviceType;
hal_info(GREEN "[CEC] switch on %s\n" NORMAL, __func__);
#if BOXMODEL_VUPLUS_ALL
if (hdmiFd == -1)
{
hdmiFd = ::open(CEC_HDMIDEV, O_RDWR | O_NONBLOCK | O_CLOEXEC);
if (hdmiFd >= 0)
{
::ioctl(hdmiFd, 0); /* flush old messages */
}
}
#endif
if (hdmiFd == -1)
{
hdmiFd = open(CEC_FALLBACK_DEVICE, O_RDWR | O_CLOEXEC);
if (hdmiFd >= 0)
{
fallback = true;
#if BOXMODEL_VUPLUS_ALL
hal_info(RED "[CEC] fallback on %s\n" NORMAL, __func__);
#endif
__u32 monitor = CEC_MODE_INITIATOR | CEC_MODE_FOLLOWER;
struct cec_caps caps = {};
if (ioctl(hdmiFd, CEC_ADAP_G_CAPS, &caps) < 0)
hal_info(RED "[CEC] %s: get caps failed (%m)\n" NORMAL, __func__);
if (caps.capabilities & CEC_CAP_LOG_ADDRS)
{
struct cec_log_addrs laddrs = {};
if (ioctl(hdmiFd, CEC_ADAP_S_LOG_ADDRS, &laddrs) < 0)
hal_info(RED "[CEC] %s: reset log addr failed (%m)\n" NORMAL, __func__);
memset(&laddrs, 0, sizeof(laddrs));
/*
* NOTE: cec_version, osd_name and deviceType should be made configurable,
* CEC_ADAP_S_LOG_ADDRS delayed till the desired values are available
* (saves us some startup speed as well, polling for a free logical address
* takes some time)
*/
laddrs.cec_version = CEC_OP_CEC_VERSION_2_0;
strcpy(laddrs.osd_name, "neutrino");
laddrs.vendor_id = CEC_VENDOR_ID_NONE;
switch (deviceType)
{
case CEC_LOG_ADDR_TV:
laddrs.log_addr_type[laddrs.num_log_addrs] = CEC_LOG_ADDR_TYPE_TV;
laddrs.all_device_types[laddrs.num_log_addrs] = CEC_OP_ALL_DEVTYPE_TV;
laddrs.primary_device_type[laddrs.num_log_addrs] = CEC_OP_PRIM_DEVTYPE_TV;
break;
case CEC_LOG_ADDR_RECORD_1:
laddrs.log_addr_type[laddrs.num_log_addrs] = CEC_LOG_ADDR_TYPE_RECORD;
laddrs.all_device_types[laddrs.num_log_addrs] = CEC_OP_ALL_DEVTYPE_RECORD;
laddrs.primary_device_type[laddrs.num_log_addrs] = CEC_OP_PRIM_DEVTYPE_RECORD;
break;
case CEC_LOG_ADDR_TUNER_1:
laddrs.log_addr_type[laddrs.num_log_addrs] = CEC_LOG_ADDR_TYPE_TUNER;
laddrs.all_device_types[laddrs.num_log_addrs] = CEC_OP_ALL_DEVTYPE_TUNER;
laddrs.primary_device_type[laddrs.num_log_addrs] = CEC_OP_PRIM_DEVTYPE_TUNER;
break;
case CEC_LOG_ADDR_PLAYBACK_1:
laddrs.log_addr_type[laddrs.num_log_addrs] = CEC_LOG_ADDR_TYPE_PLAYBACK;
laddrs.all_device_types[laddrs.num_log_addrs] = CEC_OP_ALL_DEVTYPE_PLAYBACK;
laddrs.primary_device_type[laddrs.num_log_addrs] = CEC_OP_PRIM_DEVTYPE_PLAYBACK;
break;
case CEC_LOG_ADDR_AUDIOSYSTEM:
laddrs.log_addr_type[laddrs.num_log_addrs] = CEC_LOG_ADDR_TYPE_AUDIOSYSTEM;
laddrs.all_device_types[laddrs.num_log_addrs] = CEC_OP_ALL_DEVTYPE_AUDIOSYSTEM;
laddrs.primary_device_type[laddrs.num_log_addrs] = CEC_OP_PRIM_DEVTYPE_AUDIOSYSTEM;
break;
default:
laddrs.log_addr_type[laddrs.num_log_addrs] = CEC_LOG_ADDR_TYPE_UNREGISTERED;
laddrs.all_device_types[laddrs.num_log_addrs] = CEC_OP_ALL_DEVTYPE_SWITCH;
laddrs.primary_device_type[laddrs.num_log_addrs] = CEC_OP_PRIM_DEVTYPE_SWITCH;
break;
}
laddrs.num_log_addrs++;
if (ioctl(hdmiFd, CEC_ADAP_S_LOG_ADDRS, &laddrs) < 0)
hal_info(RED "[CEC] %s: et log addr failed (%m)\n" NORMAL, __func__);
}
if (ioctl(hdmiFd, CEC_S_MODE, &monitor) < 0)
hal_info(RED "[CEC] %s: monitor failed (%m)\n" NORMAL, __func__);
}
}
if (hdmiFd >= 0)
{
GetCECAddressInfo();
if(autoview_cec_activ)
SetCECState(false);
Start();
return true;
}
return false;
}
void hdmi_cec::GetCECAddressInfo()
{
if (hdmiFd >= 0)
{
bool hasdata = false;
struct addressinfo addressinfo;
if (fallback)
{
__u16 phys_addr;
struct cec_log_addrs laddrs = {};
::ioctl(hdmiFd, CEC_ADAP_G_PHYS_ADDR, &phys_addr);
addressinfo.physical[0] = (phys_addr >> 8) & 0xff;
addressinfo.physical[1] = phys_addr & 0xff;
::ioctl(hdmiFd, CEC_ADAP_G_LOG_ADDRS, &laddrs);
addressinfo.logical = laddrs.log_addr[0];
switch (laddrs.log_addr_type[0])
{
case CEC_LOG_ADDR_TYPE_TV:
addressinfo.type = CEC_LOG_ADDR_TV;
break;
case CEC_LOG_ADDR_TYPE_RECORD:
addressinfo.type = CEC_LOG_ADDR_RECORD_1;
break;
case CEC_LOG_ADDR_TYPE_TUNER:
addressinfo.type = CEC_LOG_ADDR_TUNER_1;
break;
case CEC_LOG_ADDR_TYPE_PLAYBACK:
addressinfo.type = CEC_LOG_ADDR_PLAYBACK_1;
break;
case CEC_LOG_ADDR_TYPE_AUDIOSYSTEM:
addressinfo.type = CEC_LOG_ADDR_AUDIOSYSTEM;
break;
case CEC_LOG_ADDR_TYPE_UNREGISTERED:
default:
addressinfo.type = CEC_LOG_ADDR_UNREGISTERED;
break;
}
hasdata = true;
}
else
{
if (::ioctl(hdmiFd, 1, &addressinfo) >= 0)
{
hasdata = true;
}
}
if (hasdata)
{
deviceType = addressinfo.type;
logicalAddress = addressinfo.logical;
if (memcmp(physicalAddress, addressinfo.physical, sizeof(physicalAddress)))
{
hal_info(GREEN "[CEC] %s: detected physical address change: %02X%02X --> %02X%02X\n" NORMAL, __func__, physicalAddress[0], physicalAddress[1], addressinfo.physical[0], addressinfo.physical[1]);
memcpy(physicalAddress, addressinfo.physical, sizeof(physicalAddress));
ReportPhysicalAddress();
}
}
}
}
void hdmi_cec::ReportPhysicalAddress()
{
struct cec_message txmessage;
txmessage.initiator = logicalAddress;
txmessage.destination = CEC_LOG_ADDR_BROADCAST;
txmessage.data[0] = CEC_MSG_REPORT_PHYSICAL_ADDR;
txmessage.data[1] = physicalAddress[0];
txmessage.data[2] = physicalAddress[1];
txmessage.data[3] = deviceType;
txmessage.length = 4;
SendCECMessage(txmessage);
}
void hdmi_cec::SendCECMessage(struct cec_message &txmessage, int sleeptime)
{
if (hdmiFd >= 0)
{
char str[txmessage.length*6];
for (int i = 0; i < txmessage.length; i++)
{
sprintf(str+(i*6),"[0x%02X]", txmessage.data[i]);
}
hal_info(GREEN "[CEC] send message %s to %s (0x%02X>>0x%02X) '%s' (%s)\n" NORMAL,ToString((cec_logical_address)txmessage.initiator), txmessage.destination == 0xf ? "all" : ToString((cec_logical_address)txmessage.destination), txmessage.initiator, txmessage.destination, ToString((cec_opcode)txmessage.data[0]), str);
if (fallback)
{
struct cec_msg msg;
cec_msg_init(&msg, txmessage.initiator, txmessage.destination);
memcpy(&msg.msg[1], txmessage.data, txmessage.length);
msg.len = txmessage.length + 1;
ioctl(hdmiFd, CEC_TRANSMIT, &msg);
}
else
{
struct cec_message_fb message;
message.address = txmessage.destination;
message.length = txmessage.length;
memcpy(&message.data, txmessage.data, txmessage.length);
::write(hdmiFd, &message, 2 + message.length);
}
usleep(sleeptime * 10000);
}
}
void hdmi_cec::SetCECAutoStandby(bool state)
{
standby_cec_activ = state;
}
void hdmi_cec::SetCECAutoView(bool state)
{
autoview_cec_activ = state;
}
void hdmi_cec::SetCECState(bool state)
{
struct cec_message message;
standby = state;
if ((standby_cec_activ) && state)
{
message.initiator = logicalAddress;
message.destination = CEC_OP_PRIM_DEVTYPE_TV;
message.data[0] = CEC_MSG_STANDBY;
message.length = 1;
SendCECMessage(message);
message.initiator = logicalAddress;
message.destination = CEC_OP_PRIM_DEVTYPE_TV;
message.data[0] = CEC_MSG_GIVE_DEVICE_POWER_STATUS;
message.length = 1;
SendCECMessage(message);
}
if ((autoview_cec_activ) && !state)
{
message.initiator = logicalAddress;
message.destination = CEC_OP_PRIM_DEVTYPE_TV;
message.data[0] = CEC_MSG_GET_CEC_VERSION;
message.length = 1;
SendCECMessage(message);
message.initiator = logicalAddress;
message.destination = CEC_OP_PRIM_DEVTYPE_TV;
message.data[0] = CEC_MSG_GIVE_DEVICE_POWER_STATUS;
message.length = 1;
SendCECMessage(message);
#if BOXMODEL_VUPLUS_ALL
int cnt = 0;
while (tv_off && (cnt < 5))
{
#endif
message.initiator = logicalAddress;
message.destination = CEC_OP_PRIM_DEVTYPE_TV;
message.data[0] = CEC_MSG_IMAGE_VIEW_ON;
message.length = 1;
SendCECMessage(message);
message.initiator = logicalAddress;
message.destination = CEC_OP_PRIM_DEVTYPE_TV;
message.data[0] = CEC_MSG_GIVE_DEVICE_POWER_STATUS;
message.length = 1;
SendCECMessage(message);
#if BOXMODEL_VUPLUS_ALL
cnt++;
}
#endif
message.initiator = logicalAddress;
message.destination = CEC_LOG_ADDR_BROADCAST;
message.data[0] = CEC_MSG_ACTIVE_SOURCE;
message.data[1] = physicalAddress[0];
message.data[2] = physicalAddress[1];
message.length = 3;
SendCECMessage(message);
message.initiator = logicalAddress;
message.destination = CEC_LOG_ADDR_BROADCAST;
message.data[0] = CEC_OPCODE_SET_OSD_NAME;
message.data[1] = 0x6e; //n
message.data[2] = 0x65; //e
message.data[3] = 0x75; //u
message.data[4] = 0x74; //t
message.data[5] = 0x72; //r
message.data[6] = 0x69; //i
message.data[7] = 0x6e; //n
message.data[8] = 0x6f; //o
message.length = 9;
SendCECMessage(message);
request_audio_status();
}
}
long hdmi_cec::translateKey(unsigned char code)
{
long key = 0;
switch (code)
{
case CEC_USER_CONTROL_CODE_PREVIOUS_CHANNEL:
key = KEY_MENU;
break;
case CEC_USER_CONTROL_CODE_NUMBER0:
key = KEY_0;
break;
case CEC_USER_CONTROL_CODE_NUMBER1:
key = KEY_1;
break;
case CEC_USER_CONTROL_CODE_NUMBER2:
key = KEY_2;
break;
case CEC_USER_CONTROL_CODE_NUMBER3:
key = KEY_3;
break;
case CEC_USER_CONTROL_CODE_NUMBER4:
key = KEY_4;
break;
case CEC_USER_CONTROL_CODE_NUMBER5:
key = KEY_5;
break;
case CEC_USER_CONTROL_CODE_NUMBER6:
key = KEY_6;
break;
case CEC_USER_CONTROL_CODE_NUMBER7:
key = KEY_7;
break;
case CEC_USER_CONTROL_CODE_NUMBER8:
key = KEY_8;
break;
case CEC_USER_CONTROL_CODE_NUMBER9:
key = KEY_9;
break;
case CEC_USER_CONTROL_CODE_CHANNEL_UP:
key = KEY_CHANNELUP;
break;
case CEC_USER_CONTROL_CODE_CHANNEL_DOWN:
key = KEY_CHANNELDOWN;
break;
case CEC_USER_CONTROL_CODE_PLAY:
key = KEY_PLAY;
break;
case CEC_USER_CONTROL_CODE_STOP:
key = KEY_STOP;
break;
case CEC_USER_CONTROL_CODE_PAUSE:
key = KEY_PAUSE;
break;
case CEC_USER_CONTROL_CODE_RECORD:
key = KEY_RECORD;
break;
case CEC_USER_CONTROL_CODE_REWIND:
key = KEY_REWIND;
break;
case CEC_USER_CONTROL_CODE_FAST_FORWARD:
key = KEY_FASTFORWARD;
break;
case CEC_USER_CONTROL_CODE_ELECTRONIC_PROGRAM_GUIDE:
key = KEY_INFO;
break;
case CEC_USER_CONTROL_CODE_TIMER_PROGRAMMING:
key = KEY_PROGRAM;
break;
case CEC_USER_CONTROL_CODE_PLAY_FUNCTION:
key = KEY_PLAY;
break;
case CEC_USER_CONTROL_CODE_PAUSE_PLAY_FUNCTION:
key = KEY_PLAYPAUSE;
break;
case CEC_USER_CONTROL_CODE_RECORD_FUNCTION:
key = KEY_RECORD;
break;
case CEC_USER_CONTROL_CODE_STOP_FUNCTION:
key = KEY_STOP;
break;
case CEC_USER_CONTROL_CODE_SELECT:
key = KEY_OK;
break;
case CEC_USER_CONTROL_CODE_LEFT:
key = KEY_LEFT;
break;
case CEC_USER_CONTROL_CODE_RIGHT:
key = KEY_RIGHT;
break;
case CEC_USER_CONTROL_CODE_UP:
key = KEY_UP;
break;
case CEC_USER_CONTROL_CODE_DOWN:
key = KEY_DOWN;
break;
case CEC_USER_CONTROL_CODE_EXIT:
key = KEY_EXIT;
break;
case CEC_USER_CONTROL_CODE_F2_RED:
key = KEY_RED;
break;
case CEC_USER_CONTROL_CODE_F3_GREEN:
key = KEY_GREEN;
break;
case CEC_USER_CONTROL_CODE_F4_YELLOW:
key = KEY_YELLOW;
break;
case CEC_USER_CONTROL_CODE_F1_BLUE:
key = KEY_BLUE;
break;
default:
key = KEY_MENU;
break;
}
return key;
}
bool hdmi_cec::Start()
{
if (running)
return false;
if (hdmiFd == -1)
return false;
running = true;
OpenThreads::Thread::setSchedulePriority(THREAD_PRIORITY_MIN);
return (OpenThreads::Thread::start() == 0);
}
bool hdmi_cec::Stop()
{
if (!running)
return false;
running = false;
OpenThreads::Thread::cancel();
if (hdmiFd >= 0)
{
close(hdmiFd);
hdmiFd = -1;
}
return (OpenThreads::Thread::join() == 0);
}
void hdmi_cec::run()
{
OpenThreads::Thread::setCancelModeAsynchronous();
int n;
int epollfd = epoll_create1(0);
struct epoll_event event;
event.data.fd = hdmiFd;
event.events = EPOLLIN;
epoll_ctl(epollfd, EPOLL_CTL_ADD, hdmiFd, &event);
std::array<struct epoll_event, EPOLL_MAX_EVENTS> events;
while (running)
{
n = epoll_wait(epollfd, events.data(), EPOLL_MAX_EVENTS, EPOLL_WAIT_TIMEOUT);
for (int i = 0; i < n; ++i)
{
if (events[i].events & EPOLLIN)
Receive(events[i].events);
}
}
}
void hdmi_cec::Receive(int what)
{
if (what & EPOLLIN)
{
bool hasdata = false;
struct cec_message rxmessage;
struct cec_message txmessage;
if (fallback)
{
struct cec_msg msg;
if (::ioctl(hdmiFd, CEC_RECEIVE, &msg) >= 0)
{
rxmessage.length = msg.len - 1;
rxmessage.initiator = cec_msg_initiator(&msg);
rxmessage.destination = cec_msg_destination(&msg);
rxmessage.opcode = cec_msg_opcode(&msg);
memcpy(&rxmessage.data, &msg.msg[1], rxmessage.length);
hasdata = true;
}
}
else
{
struct cec_message_fb rx_message;
if (::read(hdmiFd, &rx_message, 2) == 2)
{
if (::read(hdmiFd, &rx_message.data, rx_message.length) == rx_message.length)
{
rxmessage.length = rx_message.length;
rxmessage.initiator = rx_message.address;
rxmessage.destination = logicalAddress;
rxmessage.opcode = rx_message.data[0];
memcpy(&rxmessage.data, rx_message.data, rx_message.length);
hasdata = true;
}
}
}
if (hasdata)
{
bool keypressed = false;
static unsigned char pressedkey = 0;
char str[rxmessage.length*6];
for (int i = 0; i < rxmessage.length; i++)
{
sprintf(str+(i*6),"[0x%02X]", rxmessage.data[i]);
}
hal_info(GREEN "[CEC] received message %s to %s (0x%02X>>0x%02X) '%s' (%s)\n" NORMAL,ToString((cec_logical_address)rxmessage.initiator), rxmessage.destination == 0xf ? "all" : ToString((cec_logical_address)rxmessage.destination), rxmessage.initiator, rxmessage.destination, ToString((cec_opcode)rxmessage.opcode), str);
switch (rxmessage.opcode)
{
//case CEC_OPCODE_ACTIVE_SOURCE:
case CEC_OPCODE_REQUEST_ACTIVE_SOURCE:
{
txmessage.destination = CEC_LOG_ADDR_BROADCAST; //rxmessage.initiator;
txmessage.initiator = logicalAddress; //rxmessage.destination;
txmessage.data[0] = CEC_MSG_ACTIVE_SOURCE;
txmessage.data[1] = physicalAddress[0];
txmessage.data[2] = physicalAddress[1];
txmessage.length = 3;
if (!standby)
SendCECMessage(txmessage);
}
case CEC_OPCODE_REPORT_AUDIO_STATUS:
{
muted = ((rxmessage.data[1] & 0x80) == 0x80);
volume = ((rxmessage.data[1] & 0x7F) / 127.0) * 100.0;
if (muted)
hal_info(GREEN "[CEC] %s volume muted\n" NORMAL, ToString((cec_logical_address)rxmessage.initiator));
else
hal_info(GREEN "[CEC] %s volume %d \n" NORMAL, ToString((cec_logical_address)rxmessage.initiator), volume);
break;
}
case CEC_OPCODE_DEVICE_VENDOR_ID:
case CEC_OPCODE_VENDOR_COMMAND_WITH_ID:
{
uint64_t iVendorId = ((uint64_t)rxmessage.data[1] << 16) +
((uint64_t)rxmessage.data[2] << 8) +
(uint64_t)rxmessage.data[3];
hal_info(GREEN "[CEC] decoded message '%s' (%s)\n" NORMAL, ToString((cec_opcode)rxmessage.opcode), ToString((cec_vendor_id)iVendorId));
break;
}
case CEC_OPCODE_GIVE_DEVICE_POWER_STATUS:
{
txmessage.destination = rxmessage.initiator;
txmessage.initiator = rxmessage.destination;
txmessage.data[0] = GetResponseOpcode((cec_opcode)rxmessage.opcode);
txmessage.data[1] = standby ? CEC_POWER_STATUS_STANDBY : CEC_POWER_STATUS_ON;
txmessage.length = 2;
SendCECMessage(txmessage);
break;
}
case CEC_OPCODE_REPORT_POWER_STATUS:
{
if ((rxmessage.data[1] == CEC_POWER_STATUS_ON) || (rxmessage.data[1] == CEC_POWER_STATUS_IN_TRANSITION_STANDBY_TO_ON))
{
hal_info(GREEN "[CEC] %s reporting state on (%d)\n" NORMAL, ToString((cec_logical_address)rxmessage.initiator), rxmessage.data[1]);
if (rxmessage.initiator == CEC_OP_PRIM_DEVTYPE_TV)
tv_off = false;
} else {
hal_info(GREEN "[CEC] %s reporting state off (%d)\n" NORMAL, ToString((cec_logical_address)rxmessage.initiator), rxmessage.data[1]);
if (rxmessage.initiator == CEC_OP_PRIM_DEVTYPE_TV)
tv_off = true;
}
break;
}
case CEC_OPCODE_STANDBY:
{
if (rxmessage.initiator == CEC_OP_PRIM_DEVTYPE_TV)
tv_off = true;
break;
}
case CEC_OPCODE_USER_CONTROL_PRESSED: /* key pressed */
{
keypressed = true;
pressedkey = rxmessage.data[1];
} // fall through
case CEC_OPCODE_USER_CONTROL_RELEASE: /* key released */
{
long code = translateKey(pressedkey);
hal_info(GREEN "[CEC] decoded key %s (%ld)\n" NORMAL,ToString((cec_user_control_code)pressedkey), code);
handleCode(code,keypressed);
break;
}
}
}
}
}
void hdmi_cec::handleCode(long code, bool keypressed)
{
int evd = open(RC_DEVICE, O_RDWR);
if (evd < 0)
{
hal_info(RED "[CEC] opening " RC_DEVICE " failed" NORMAL);
return;
}
if (keypressed)
{
if (rc_send(evd, code, CEC_KEY_PRESSED) < 0)
{
hal_info(RED "[CEC] writing 'KEY_PRESSED' event failed" NORMAL);
close(evd);
return;
}
rc_sync(evd);
}
else
{
if (rc_send(evd, code, CEC_KEY_RELEASED) < 0)
{
hal_info(RED "[CEC] writing 'KEY_RELEASED' event failed" NORMAL);
close(evd);
return;
}
rc_sync(evd);
}
close(evd);
}
int hdmi_cec::rc_send(int fd, unsigned int code, unsigned int value)
{
struct input_event ev;
ev.type = EV_KEY;
ev.code = code;
ev.value = value;
return write(fd, &ev, sizeof(ev));
}
void hdmi_cec::rc_sync(int fd)
{
struct input_event ev;
gettimeofday(&ev.time, NULL);
ev.type = EV_SYN;
ev.code = SYN_REPORT;
ev.value = 0;
write(fd, &ev, sizeof(ev));
}
void hdmi_cec::send_key(unsigned char key, unsigned char destination)
{
struct cec_message txmessage;
txmessage.destination = destination;
txmessage.initiator = logicalAddress;
txmessage.data[0] = CEC_OPCODE_USER_CONTROL_PRESSED;
txmessage.data[1] = key;
txmessage.length = 2;
SendCECMessage(txmessage, 1);
txmessage.destination = destination;
txmessage.initiator = logicalAddress;
txmessage.data[0] = CEC_OPCODE_USER_CONTROL_RELEASE;
txmessage.length = 1;
SendCECMessage(txmessage, 0);
}
void hdmi_cec::request_audio_status()
{
struct cec_message txmessage;
txmessage.destination = CEC_OP_PRIM_DEVTYPE_AUDIOSYSTEM;
txmessage.initiator = logicalAddress;
txmessage.data[0] = CEC_OPCODE_GIVE_AUDIO_STATUS;
txmessage.length = 1;
SendCECMessage(txmessage, 0);
}
void hdmi_cec::vol_up()
{
send_key(CEC_USER_CONTROL_CODE_VOLUME_UP, CEC_OP_PRIM_DEVTYPE_AUDIOSYSTEM);
request_audio_status();
}
void hdmi_cec::vol_down()
{
send_key(CEC_USER_CONTROL_CODE_VOLUME_DOWN, CEC_OP_PRIM_DEVTYPE_AUDIOSYSTEM);
request_audio_status();
}
void hdmi_cec::toggle_mute()
{
send_key(CEC_USER_CONTROL_CODE_MUTE, CEC_OP_PRIM_DEVTYPE_AUDIOSYSTEM);
request_audio_status();
}

108
libarmbox/hdmi_cec.h Normal file
View File

@@ -0,0 +1,108 @@
#ifndef __HDMI_CEC_H__
#define __HDMI_CEC_H__
/*
Copyright (C) 2018-2020 TangoCash
License: GPLv2
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;
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.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <OpenThreads/Thread>
#include <OpenThreads/Condition>
#include "video_lib.h"
struct cec_message
{
unsigned char initiator;
unsigned char destination;
unsigned char opcode;
unsigned char data[256];
unsigned char length;
} __attribute__((packed));
struct cec_message_fb
{
unsigned char address;
unsigned char length;
unsigned char data[256];
} __attribute__((packed));
struct addressinfo
{
unsigned char logical;
unsigned char physical[2];
unsigned char type;
};
enum
{
CEC_KEY_RELEASED = 0,
CEC_KEY_PRESSED,
CEC_KEY_AUTOREPEAT
};
class hdmi_cec : public OpenThreads::Thread
{
private:
hdmi_cec();
static hdmi_cec *hdmi_cec_instance;
void run();
bool Start();
bool Stop();
void Receive(int what);
unsigned char physicalAddress[2];
bool autoview_cec_activ;
unsigned char deviceType, logicalAddress;
int hdmiFd;
long translateKey(unsigned char code);
void handleCode(long code, bool keypressed);
int rc_send(int fd, unsigned int code, unsigned int value);
void rc_sync(int fd);
bool standby;
void send_key(unsigned char key, unsigned char destination);
void request_audio_status();
bool muted;
int volume;
bool fallback;
bool tv_off;
protected:
bool running;
public:
~hdmi_cec();
static hdmi_cec* getInstance();
bool SetCECMode(VIDEO_HDMI_CEC_MODE);
void SetCECAutoView(bool);
void SetCECAutoStandby(bool);
void GetCECAddressInfo();
void SendCECMessage(struct cec_message &message, int sleeptime = 10);
void SetCECState(bool state);
void ReportPhysicalAddress();
bool standby_cec_activ;
void vol_up();
void vol_down();
void toggle_mute();
int GetVolume()
{
return volume;
};
bool isMuted()
{
return muted;
};
};
#endif // __HDMI_CEC_H__

713
libarmbox/hdmi_cec_types.h Normal file
View File

@@ -0,0 +1,713 @@
#ifndef __HDMI_CEC_TYPES_H__
#define __HDMI_CEC_TYPES_H__
typedef enum cec_vendor_id
{
CEC_VENDOR_TOSHIBA = 0x000039,
CEC_VENDOR_SAMSUNG = 0x0000F0,
CEC_VENDOR_DENON = 0x0005CD,
CEC_VENDOR_MARANTZ = 0x000678,
CEC_VENDOR_LOEWE = 0x000982,
CEC_VENDOR_ONKYO = 0x0009B0,
CEC_VENDOR_MEDION = 0x000CB8,
CEC_VENDOR_TOSHIBA2 = 0x000CE7,
CEC_VENDOR_PULSE_EIGHT = 0x001582,
CEC_VENDOR_HARMAN_KARDON2 = 0x001950,
CEC_VENDOR_GOOGLE = 0x001A11,
CEC_VENDOR_AKAI = 0x0020C7,
CEC_VENDOR_AOC = 0x002467,
CEC_VENDOR_PANASONIC = 0x008045,
CEC_VENDOR_PHILIPS = 0x00903E,
CEC_VENDOR_DAEWOO = 0x009053,
CEC_VENDOR_YAMAHA = 0x00A0DE,
CEC_VENDOR_GRUNDIG = 0x00D0D5,
CEC_VENDOR_PIONEER = 0x00E036,
CEC_VENDOR_LG = 0x00E091,
CEC_VENDOR_SHARP = 0x08001F,
CEC_VENDOR_SONY = 0x080046,
CEC_VENDOR_BROADCOM = 0x18C086,
CEC_VENDOR_SHARP2 = 0x534850,
CEC_VENDOR_VIZIO = 0x6B746D,
CEC_VENDOR_BENQ = 0x8065E9,
CEC_VENDOR_HARMAN_KARDON = 0x9C645E,
CEC_VENDOR_UNKNOWN = 0
} cec_vendor_id;
typedef enum cec_user_control_code
{
CEC_USER_CONTROL_CODE_SELECT = 0x00,
CEC_USER_CONTROL_CODE_UP = 0x01,
CEC_USER_CONTROL_CODE_DOWN = 0x02,
CEC_USER_CONTROL_CODE_LEFT = 0x03,
CEC_USER_CONTROL_CODE_RIGHT = 0x04,
CEC_USER_CONTROL_CODE_RIGHT_UP = 0x05,
CEC_USER_CONTROL_CODE_RIGHT_DOWN = 0x06,
CEC_USER_CONTROL_CODE_LEFT_UP = 0x07,
CEC_USER_CONTROL_CODE_LEFT_DOWN = 0x08,
CEC_USER_CONTROL_CODE_ROOT_MENU = 0x09,
CEC_USER_CONTROL_CODE_SETUP_MENU = 0x0A,
CEC_USER_CONTROL_CODE_CONTENTS_MENU = 0x0B,
CEC_USER_CONTROL_CODE_FAVORITE_MENU = 0x0C,
CEC_USER_CONTROL_CODE_EXIT = 0x0D,
// reserved: 0x0E, 0x0F
CEC_USER_CONTROL_CODE_TOP_MENU = 0x10,
CEC_USER_CONTROL_CODE_DVD_MENU = 0x11,
// reserved: 0x12 ... 0x1C
CEC_USER_CONTROL_CODE_NUMBER_ENTRY_MODE = 0x1D,
CEC_USER_CONTROL_CODE_NUMBER11 = 0x1E,
CEC_USER_CONTROL_CODE_NUMBER12 = 0x1F,
CEC_USER_CONTROL_CODE_NUMBER0 = 0x20,
CEC_USER_CONTROL_CODE_NUMBER1 = 0x21,
CEC_USER_CONTROL_CODE_NUMBER2 = 0x22,
CEC_USER_CONTROL_CODE_NUMBER3 = 0x23,
CEC_USER_CONTROL_CODE_NUMBER4 = 0x24,
CEC_USER_CONTROL_CODE_NUMBER5 = 0x25,
CEC_USER_CONTROL_CODE_NUMBER6 = 0x26,
CEC_USER_CONTROL_CODE_NUMBER7 = 0x27,
CEC_USER_CONTROL_CODE_NUMBER8 = 0x28,
CEC_USER_CONTROL_CODE_NUMBER9 = 0x29,
CEC_USER_CONTROL_CODE_DOT = 0x2A,
CEC_USER_CONTROL_CODE_ENTER = 0x2B,
CEC_USER_CONTROL_CODE_CLEAR = 0x2C,
CEC_USER_CONTROL_CODE_NEXT_FAVORITE = 0x2F,
CEC_USER_CONTROL_CODE_CHANNEL_UP = 0x30,
CEC_USER_CONTROL_CODE_CHANNEL_DOWN = 0x31,
CEC_USER_CONTROL_CODE_PREVIOUS_CHANNEL = 0x32,
CEC_USER_CONTROL_CODE_SOUND_SELECT = 0x33,
CEC_USER_CONTROL_CODE_INPUT_SELECT = 0x34,
CEC_USER_CONTROL_CODE_DISPLAY_INFORMATION = 0x35,
CEC_USER_CONTROL_CODE_HELP = 0x36,
CEC_USER_CONTROL_CODE_PAGE_UP = 0x37,
CEC_USER_CONTROL_CODE_PAGE_DOWN = 0x38,
// reserved: 0x39 ... 0x3F
CEC_USER_CONTROL_CODE_POWER = 0x40,
CEC_USER_CONTROL_CODE_VOLUME_UP = 0x41,
CEC_USER_CONTROL_CODE_VOLUME_DOWN = 0x42,
CEC_USER_CONTROL_CODE_MUTE = 0x43,
CEC_USER_CONTROL_CODE_PLAY = 0x44,
CEC_USER_CONTROL_CODE_STOP = 0x45,
CEC_USER_CONTROL_CODE_PAUSE = 0x46,
CEC_USER_CONTROL_CODE_RECORD = 0x47,
CEC_USER_CONTROL_CODE_REWIND = 0x48,
CEC_USER_CONTROL_CODE_FAST_FORWARD = 0x49,
CEC_USER_CONTROL_CODE_EJECT = 0x4A,
CEC_USER_CONTROL_CODE_FORWARD = 0x4B,
CEC_USER_CONTROL_CODE_BACKWARD = 0x4C,
CEC_USER_CONTROL_CODE_STOP_RECORD = 0x4D,
CEC_USER_CONTROL_CODE_PAUSE_RECORD = 0x4E,
// reserved: 0x4F
CEC_USER_CONTROL_CODE_ANGLE = 0x50,
CEC_USER_CONTROL_CODE_SUB_PICTURE = 0x51,
CEC_USER_CONTROL_CODE_VIDEO_ON_DEMAND = 0x52,
CEC_USER_CONTROL_CODE_ELECTRONIC_PROGRAM_GUIDE = 0x53,
CEC_USER_CONTROL_CODE_TIMER_PROGRAMMING = 0x54,
CEC_USER_CONTROL_CODE_INITIAL_CONFIGURATION = 0x55,
CEC_USER_CONTROL_CODE_SELECT_BROADCAST_TYPE = 0x56,
CEC_USER_CONTROL_CODE_SELECT_SOUND_PRESENTATION = 0x57,
// reserved: 0x58 ... 0x5F
CEC_USER_CONTROL_CODE_PLAY_FUNCTION = 0x60,
CEC_USER_CONTROL_CODE_PAUSE_PLAY_FUNCTION = 0x61,
CEC_USER_CONTROL_CODE_RECORD_FUNCTION = 0x62,
CEC_USER_CONTROL_CODE_PAUSE_RECORD_FUNCTION = 0x63,
CEC_USER_CONTROL_CODE_STOP_FUNCTION = 0x64,
CEC_USER_CONTROL_CODE_MUTE_FUNCTION = 0x65,
CEC_USER_CONTROL_CODE_RESTORE_VOLUME_FUNCTION = 0x66,
CEC_USER_CONTROL_CODE_TUNE_FUNCTION = 0x67,
CEC_USER_CONTROL_CODE_SELECT_MEDIA_FUNCTION = 0x68,
CEC_USER_CONTROL_CODE_SELECT_AV_INPUT_FUNCTION = 0x69,
CEC_USER_CONTROL_CODE_SELECT_AUDIO_INPUT_FUNCTION = 0x6A,
CEC_USER_CONTROL_CODE_POWER_TOGGLE_FUNCTION = 0x6B,
CEC_USER_CONTROL_CODE_POWER_OFF_FUNCTION = 0x6C,
CEC_USER_CONTROL_CODE_POWER_ON_FUNCTION = 0x6D,
// reserved: 0x6E ... 0x70
CEC_USER_CONTROL_CODE_F1_BLUE = 0x71,
CEC_USER_CONTROL_CODE_F2_RED = 0X72,
CEC_USER_CONTROL_CODE_F3_GREEN = 0x73,
CEC_USER_CONTROL_CODE_F4_YELLOW = 0x74,
CEC_USER_CONTROL_CODE_F5 = 0x75,
CEC_USER_CONTROL_CODE_DATA = 0x76,
// reserved: 0x77 ... 0xFF
CEC_USER_CONTROL_CODE_AN_RETURN = 0x91, // return (Samsung)
CEC_USER_CONTROL_CODE_AN_CHANNELS_LIST = 0x96, // channels list (Samsung)
CEC_USER_CONTROL_CODE_MAX = 0x96,
CEC_USER_CONTROL_CODE_UNKNOWN = 0xFF
} cec_user_control_code;
typedef enum cec_opcode
{
CEC_OPCODE_ACTIVE_SOURCE = 0x82,
CEC_OPCODE_IMAGE_VIEW_ON = 0x04,
CEC_OPCODE_TEXT_VIEW_ON = 0x0D,
CEC_OPCODE_INACTIVE_SOURCE = 0x9D,
CEC_OPCODE_REQUEST_ACTIVE_SOURCE = 0x85,
CEC_OPCODE_ROUTING_CHANGE = 0x80,
CEC_OPCODE_ROUTING_INFORMATION = 0x81,
CEC_OPCODE_SET_STREAM_PATH = 0x86,
CEC_OPCODE_STANDBY = 0x36,
CEC_OPCODE_RECORD_OFF = 0x0B,
CEC_OPCODE_RECORD_ON = 0x09,
CEC_OPCODE_RECORD_STATUS = 0x0A,
CEC_OPCODE_RECORD_TV_SCREEN = 0x0F,
CEC_OPCODE_CLEAR_ANALOGUE_TIMER = 0x33,
CEC_OPCODE_CLEAR_DIGITAL_TIMER = 0x99,
CEC_OPCODE_CLEAR_EXTERNAL_TIMER = 0xA1,
CEC_OPCODE_SET_ANALOGUE_TIMER = 0x34,
CEC_OPCODE_SET_DIGITAL_TIMER = 0x97,
CEC_OPCODE_SET_EXTERNAL_TIMER = 0xA2,
CEC_OPCODE_SET_TIMER_PROGRAM_TITLE = 0x67,
CEC_OPCODE_TIMER_CLEARED_STATUS = 0x43,
CEC_OPCODE_TIMER_STATUS = 0x35,
CEC_OPCODE_CEC_VERSION = 0x9E,
CEC_OPCODE_GET_CEC_VERSION = 0x9F,
CEC_OPCODE_GIVE_PHYSICAL_ADDRESS = 0x83,
CEC_OPCODE_GET_MENU_LANGUAGE = 0x91,
CEC_OPCODE_REPORT_PHYSICAL_ADDRESS = 0x84,
CEC_OPCODE_SET_MENU_LANGUAGE = 0x32,
CEC_OPCODE_DECK_CONTROL = 0x42,
CEC_OPCODE_DECK_STATUS = 0x1B,
CEC_OPCODE_GIVE_DECK_STATUS = 0x1A,
CEC_OPCODE_PLAY = 0x41,
CEC_OPCODE_GIVE_TUNER_DEVICE_STATUS = 0x08,
CEC_OPCODE_SELECT_ANALOGUE_SERVICE = 0x92,
CEC_OPCODE_SELECT_DIGITAL_SERVICE = 0x93,
CEC_OPCODE_TUNER_DEVICE_STATUS = 0x07,
CEC_OPCODE_TUNER_STEP_DECREMENT = 0x06,
CEC_OPCODE_TUNER_STEP_INCREMENT = 0x05,
CEC_OPCODE_DEVICE_VENDOR_ID = 0x87,
CEC_OPCODE_GIVE_DEVICE_VENDOR_ID = 0x8C,
CEC_OPCODE_VENDOR_COMMAND = 0x89,
CEC_OPCODE_VENDOR_COMMAND_WITH_ID = 0xA0,
CEC_OPCODE_VENDOR_REMOTE_BUTTON_DOWN = 0x8A,
CEC_OPCODE_VENDOR_REMOTE_BUTTON_UP = 0x8B,
CEC_OPCODE_SET_OSD_STRING = 0x64,
CEC_OPCODE_GIVE_OSD_NAME = 0x46,
CEC_OPCODE_SET_OSD_NAME = 0x47,
CEC_OPCODE_MENU_REQUEST = 0x8D,
CEC_OPCODE_MENU_STATUS = 0x8E,
CEC_OPCODE_USER_CONTROL_PRESSED = 0x44,
CEC_OPCODE_USER_CONTROL_RELEASE = 0x45,
CEC_OPCODE_GIVE_DEVICE_POWER_STATUS = 0x8F,
CEC_OPCODE_REPORT_POWER_STATUS = 0x90,
CEC_OPCODE_FEATURE_ABORT = 0x00,
CEC_OPCODE_ABORT = 0xFF,
CEC_OPCODE_GIVE_AUDIO_STATUS = 0x71,
CEC_OPCODE_GIVE_SYSTEM_AUDIO_MODE_STATUS = 0x7D,
CEC_OPCODE_REPORT_AUDIO_STATUS = 0x7A,
CEC_OPCODE_SET_SYSTEM_AUDIO_MODE = 0x72,
CEC_OPCODE_SYSTEM_AUDIO_MODE_REQUEST = 0x70,
CEC_OPCODE_SYSTEM_AUDIO_MODE_STATUS = 0x7E,
CEC_OPCODE_SET_AUDIO_RATE = 0x9A,
/* CEC 1.4 */
CEC_OPCODE_START_ARC = 0xC0,
CEC_OPCODE_REPORT_ARC_STARTED = 0xC1,
CEC_OPCODE_REPORT_ARC_ENDED = 0xC2,
CEC_OPCODE_REQUEST_ARC_START = 0xC3,
CEC_OPCODE_REQUEST_ARC_END = 0xC4,
CEC_OPCODE_END_ARC = 0xC5,
CEC_OPCODE_CDC = 0xF8,
/* when this opcode is set, no opcode will be sent to the device. this is one of the reserved numbers */
CEC_OPCODE_NONE = 0xFD
} cec_opcode;
typedef enum cec_logical_address
{
CECDEVICE_UNKNOWN = -1, //not a valid logical address
CECDEVICE_TV = 0,
CECDEVICE_RECORDINGDEVICE1 = 1,
CECDEVICE_RECORDINGDEVICE2 = 2,
CECDEVICE_TUNER1 = 3,
CECDEVICE_PLAYBACKDEVICE1 = 4,
CECDEVICE_AUDIOSYSTEM = 5,
CECDEVICE_TUNER2 = 6,
CECDEVICE_TUNER3 = 7,
CECDEVICE_PLAYBACKDEVICE2 = 8,
CECDEVICE_RECORDINGDEVICE3 = 9,
CECDEVICE_TUNER4 = 10,
CECDEVICE_PLAYBACKDEVICE3 = 11,
CECDEVICE_RESERVED1 = 12,
CECDEVICE_RESERVED2 = 13,
CECDEVICE_FREEUSE = 14,
CECDEVICE_UNREGISTERED = 15,
CECDEVICE_BROADCAST = 15
} cec_logical_address;
typedef enum cec_power_status
{
CEC_POWER_STATUS_ON = 0x00,
CEC_POWER_STATUS_STANDBY = 0x01,
CEC_POWER_STATUS_IN_TRANSITION_STANDBY_TO_ON = 0x02,
CEC_POWER_STATUS_IN_TRANSITION_ON_TO_STANDBY = 0x03,
CEC_POWER_STATUS_UNKNOWN = 0x99
} cec_power_status;
static const char *ToString(const cec_opcode opcode)
{
switch (opcode)
{
case CEC_OPCODE_ACTIVE_SOURCE:
return "active source";
case CEC_OPCODE_IMAGE_VIEW_ON:
return "image view on";
case CEC_OPCODE_TEXT_VIEW_ON:
return "text view on";
case CEC_OPCODE_INACTIVE_SOURCE:
return "inactive source";
case CEC_OPCODE_REQUEST_ACTIVE_SOURCE:
return "request active source";
case CEC_OPCODE_ROUTING_CHANGE:
return "routing change";
case CEC_OPCODE_ROUTING_INFORMATION:
return "routing information";
case CEC_OPCODE_SET_STREAM_PATH:
return "set stream path";
case CEC_OPCODE_STANDBY:
return "standby";
case CEC_OPCODE_RECORD_OFF:
return "record off";
case CEC_OPCODE_RECORD_ON:
return "record on";
case CEC_OPCODE_RECORD_STATUS:
return "record status";
case CEC_OPCODE_RECORD_TV_SCREEN:
return "record tv screen";
case CEC_OPCODE_CLEAR_ANALOGUE_TIMER:
return "clear analogue timer";
case CEC_OPCODE_CLEAR_DIGITAL_TIMER:
return "clear digital timer";
case CEC_OPCODE_CLEAR_EXTERNAL_TIMER:
return "clear external timer";
case CEC_OPCODE_SET_ANALOGUE_TIMER:
return "set analogue timer";
case CEC_OPCODE_SET_DIGITAL_TIMER:
return "set digital timer";
case CEC_OPCODE_SET_EXTERNAL_TIMER:
return "set external timer";
case CEC_OPCODE_SET_TIMER_PROGRAM_TITLE:
return "set timer program title";
case CEC_OPCODE_TIMER_CLEARED_STATUS:
return "timer cleared status";
case CEC_OPCODE_TIMER_STATUS:
return "timer status";
case CEC_OPCODE_CEC_VERSION:
return "cec version";
case CEC_OPCODE_GET_CEC_VERSION:
return "get cec version";
case CEC_OPCODE_GIVE_PHYSICAL_ADDRESS:
return "give physical address";
case CEC_OPCODE_GET_MENU_LANGUAGE:
return "get menu language";
case CEC_OPCODE_REPORT_PHYSICAL_ADDRESS:
return "report physical address";
case CEC_OPCODE_SET_MENU_LANGUAGE:
return "set menu language";
case CEC_OPCODE_DECK_CONTROL:
return "deck control";
case CEC_OPCODE_DECK_STATUS:
return "deck status";
case CEC_OPCODE_GIVE_DECK_STATUS:
return "give deck status";
case CEC_OPCODE_PLAY:
return "play";
case CEC_OPCODE_GIVE_TUNER_DEVICE_STATUS:
return "give tuner status";
case CEC_OPCODE_SELECT_ANALOGUE_SERVICE:
return "select analogue service";
case CEC_OPCODE_SELECT_DIGITAL_SERVICE:
return "set digital service";
case CEC_OPCODE_TUNER_DEVICE_STATUS:
return "tuner device status";
case CEC_OPCODE_TUNER_STEP_DECREMENT:
return "tuner step decrement";
case CEC_OPCODE_TUNER_STEP_INCREMENT:
return "tuner step increment";
case CEC_OPCODE_DEVICE_VENDOR_ID:
return "device vendor id";
case CEC_OPCODE_GIVE_DEVICE_VENDOR_ID:
return "give device vendor id";
case CEC_OPCODE_VENDOR_COMMAND:
return "vendor command";
case CEC_OPCODE_VENDOR_COMMAND_WITH_ID:
return "vendor command with id";
case CEC_OPCODE_VENDOR_REMOTE_BUTTON_DOWN:
return "vendor remote button down";
case CEC_OPCODE_VENDOR_REMOTE_BUTTON_UP:
return "vendor remote button up";
case CEC_OPCODE_SET_OSD_STRING:
return "set osd string";
case CEC_OPCODE_GIVE_OSD_NAME:
return "give osd name";
case CEC_OPCODE_SET_OSD_NAME:
return "set osd name";
case CEC_OPCODE_MENU_REQUEST:
return "menu request";
case CEC_OPCODE_MENU_STATUS:
return "menu status";
case CEC_OPCODE_USER_CONTROL_PRESSED:
return "user control pressed";
case CEC_OPCODE_USER_CONTROL_RELEASE:
return "user control release";
case CEC_OPCODE_GIVE_DEVICE_POWER_STATUS:
return "give device power status";
case CEC_OPCODE_REPORT_POWER_STATUS:
return "report power status";
case CEC_OPCODE_FEATURE_ABORT:
return "feature abort";
case CEC_OPCODE_ABORT:
return "abort";
case CEC_OPCODE_GIVE_AUDIO_STATUS:
return "give audio status";
case CEC_OPCODE_GIVE_SYSTEM_AUDIO_MODE_STATUS:
return "give audio mode status";
case CEC_OPCODE_REPORT_AUDIO_STATUS:
return "report audio status";
case CEC_OPCODE_SET_SYSTEM_AUDIO_MODE:
return "set system audio mode";
case CEC_OPCODE_SYSTEM_AUDIO_MODE_REQUEST:
return "system audio mode request";
case CEC_OPCODE_SYSTEM_AUDIO_MODE_STATUS:
return "system audio mode status";
case CEC_OPCODE_SET_AUDIO_RATE:
return "set audio rate";
case CEC_OPCODE_START_ARC:
return "start ARC";
case CEC_OPCODE_REPORT_ARC_STARTED:
return "report ARC started";
case CEC_OPCODE_REPORT_ARC_ENDED:
return "report ARC ended";
case CEC_OPCODE_REQUEST_ARC_START:
return "request ARC start";
case CEC_OPCODE_REQUEST_ARC_END:
return "request ARC end";
case CEC_OPCODE_END_ARC:
return "end ARC";
case CEC_OPCODE_CDC:
return "CDC";
case CEC_OPCODE_NONE:
return "poll";
default:
return "UNKNOWN";
}
}
static const char *ToString(const cec_vendor_id vendor)
{
switch (vendor)
{
case CEC_VENDOR_SAMSUNG:
return "Samsung";
case CEC_VENDOR_LG:
return "LG";
case CEC_VENDOR_PANASONIC:
return "Panasonic";
case CEC_VENDOR_PIONEER:
return "Pioneer";
case CEC_VENDOR_ONKYO:
return "Onkyo";
case CEC_VENDOR_YAMAHA:
return "Yamaha";
case CEC_VENDOR_PHILIPS:
return "Philips";
case CEC_VENDOR_SONY:
return "Sony";
case CEC_VENDOR_TOSHIBA:
case CEC_VENDOR_TOSHIBA2:
return "Toshiba";
case CEC_VENDOR_AKAI:
return "Akai";
case CEC_VENDOR_AOC:
return "AOC";
case CEC_VENDOR_BENQ:
return "Benq";
case CEC_VENDOR_DAEWOO:
return "Daewoo";
case CEC_VENDOR_GRUNDIG:
return "Grundig";
case CEC_VENDOR_MEDION:
return "Medion";
case CEC_VENDOR_SHARP:
case CEC_VENDOR_SHARP2:
return "Sharp";
case CEC_VENDOR_VIZIO:
return "Vizio";
case CEC_VENDOR_BROADCOM:
return "Broadcom";
case CEC_VENDOR_LOEWE:
return "Loewe";
case CEC_VENDOR_DENON:
return "Denon";
case CEC_VENDOR_MARANTZ:
return "Marantz";
case CEC_VENDOR_HARMAN_KARDON:
case CEC_VENDOR_HARMAN_KARDON2:
return "Harman/Kardon";
case CEC_VENDOR_PULSE_EIGHT:
return "Pulse Eight";
case CEC_VENDOR_GOOGLE:
return "Google";
default:
return "Unknown";
}
}
static const char *ToString(const cec_user_control_code key)
{
switch (key)
{
case CEC_USER_CONTROL_CODE_SELECT:
return "select";
case CEC_USER_CONTROL_CODE_UP:
return "up";
case CEC_USER_CONTROL_CODE_DOWN:
return "down";
case CEC_USER_CONTROL_CODE_LEFT:
return "left";
case CEC_USER_CONTROL_CODE_RIGHT:
return "right";
case CEC_USER_CONTROL_CODE_RIGHT_UP:
return "right+up";
case CEC_USER_CONTROL_CODE_RIGHT_DOWN:
return "right+down";
case CEC_USER_CONTROL_CODE_LEFT_UP:
return "left+up";
case CEC_USER_CONTROL_CODE_LEFT_DOWN:
return "left+down";
case CEC_USER_CONTROL_CODE_ROOT_MENU:
return "root menu";
case CEC_USER_CONTROL_CODE_SETUP_MENU:
return "setup menu";
case CEC_USER_CONTROL_CODE_CONTENTS_MENU:
return "contents menu";
case CEC_USER_CONTROL_CODE_FAVORITE_MENU:
return "favourite menu";
case CEC_USER_CONTROL_CODE_EXIT:
return "exit";
case CEC_USER_CONTROL_CODE_TOP_MENU:
return "top menu";
case CEC_USER_CONTROL_CODE_DVD_MENU:
return "dvd menu";
case CEC_USER_CONTROL_CODE_NUMBER_ENTRY_MODE:
return "number entry mode";
case CEC_USER_CONTROL_CODE_NUMBER11:
return "11";
case CEC_USER_CONTROL_CODE_NUMBER12:
return "12";
case CEC_USER_CONTROL_CODE_NUMBER0:
return "0";
case CEC_USER_CONTROL_CODE_NUMBER1:
return "1";
case CEC_USER_CONTROL_CODE_NUMBER2:
return "2";
case CEC_USER_CONTROL_CODE_NUMBER3:
return "3";
case CEC_USER_CONTROL_CODE_NUMBER4:
return "4";
case CEC_USER_CONTROL_CODE_NUMBER5:
return "5";
case CEC_USER_CONTROL_CODE_NUMBER6:
return "6";
case CEC_USER_CONTROL_CODE_NUMBER7:
return "7";
case CEC_USER_CONTROL_CODE_NUMBER8:
return "8";
case CEC_USER_CONTROL_CODE_NUMBER9:
return "9";
case CEC_USER_CONTROL_CODE_DOT:
return ".";
case CEC_USER_CONTROL_CODE_ENTER:
return "enter";
case CEC_USER_CONTROL_CODE_CLEAR:
return "clear";
case CEC_USER_CONTROL_CODE_NEXT_FAVORITE:
return "next favourite";
case CEC_USER_CONTROL_CODE_CHANNEL_UP:
return "channel up";
case CEC_USER_CONTROL_CODE_CHANNEL_DOWN:
return "channel down";
case CEC_USER_CONTROL_CODE_PREVIOUS_CHANNEL:
return "previous channel";
case CEC_USER_CONTROL_CODE_SOUND_SELECT:
return "sound select";
case CEC_USER_CONTROL_CODE_INPUT_SELECT:
return "input select";
case CEC_USER_CONTROL_CODE_DISPLAY_INFORMATION:
return "display information";
case CEC_USER_CONTROL_CODE_HELP:
return "help";
case CEC_USER_CONTROL_CODE_PAGE_UP:
return "page up";
case CEC_USER_CONTROL_CODE_PAGE_DOWN:
return "page down";
case CEC_USER_CONTROL_CODE_POWER:
return "power";
case CEC_USER_CONTROL_CODE_VOLUME_UP:
return "volume up";
case CEC_USER_CONTROL_CODE_VOLUME_DOWN:
return "volume down";
case CEC_USER_CONTROL_CODE_MUTE:
return "mute";
case CEC_USER_CONTROL_CODE_PLAY:
return "play";
case CEC_USER_CONTROL_CODE_STOP:
return "stop";
case CEC_USER_CONTROL_CODE_PAUSE:
return "pause";
case CEC_USER_CONTROL_CODE_RECORD:
return "record";
case CEC_USER_CONTROL_CODE_REWIND:
return "rewind";
case CEC_USER_CONTROL_CODE_FAST_FORWARD:
return "Fast forward";
case CEC_USER_CONTROL_CODE_EJECT:
return "eject";
case CEC_USER_CONTROL_CODE_FORWARD:
return "forward";
case CEC_USER_CONTROL_CODE_BACKWARD:
return "backward";
case CEC_USER_CONTROL_CODE_STOP_RECORD:
return "stop record";
case CEC_USER_CONTROL_CODE_PAUSE_RECORD:
return "pause record";
case CEC_USER_CONTROL_CODE_ANGLE:
return "angle";
case CEC_USER_CONTROL_CODE_SUB_PICTURE:
return "sub picture";
case CEC_USER_CONTROL_CODE_VIDEO_ON_DEMAND:
return "video on demand";
case CEC_USER_CONTROL_CODE_ELECTRONIC_PROGRAM_GUIDE:
return "electronic program guide";
case CEC_USER_CONTROL_CODE_TIMER_PROGRAMMING:
return "timer programming";
case CEC_USER_CONTROL_CODE_INITIAL_CONFIGURATION:
return "initial configuration";
case CEC_USER_CONTROL_CODE_SELECT_BROADCAST_TYPE:
return "select broadcast type";
case CEC_USER_CONTROL_CODE_SELECT_SOUND_PRESENTATION:
return "select sound presentation";
case CEC_USER_CONTROL_CODE_PLAY_FUNCTION:
return "play (function)";
case CEC_USER_CONTROL_CODE_PAUSE_PLAY_FUNCTION:
return "pause play (function)";
case CEC_USER_CONTROL_CODE_RECORD_FUNCTION:
return "record (function)";
case CEC_USER_CONTROL_CODE_PAUSE_RECORD_FUNCTION:
return "pause record (function)";
case CEC_USER_CONTROL_CODE_STOP_FUNCTION:
return "stop (function)";
case CEC_USER_CONTROL_CODE_MUTE_FUNCTION:
return "mute (function)";
case CEC_USER_CONTROL_CODE_RESTORE_VOLUME_FUNCTION:
return "restore volume";
case CEC_USER_CONTROL_CODE_TUNE_FUNCTION:
return "tune";
case CEC_USER_CONTROL_CODE_SELECT_MEDIA_FUNCTION:
return "select media";
case CEC_USER_CONTROL_CODE_SELECT_AV_INPUT_FUNCTION:
return "select AV input";
case CEC_USER_CONTROL_CODE_SELECT_AUDIO_INPUT_FUNCTION:
return "select audio input";
case CEC_USER_CONTROL_CODE_POWER_TOGGLE_FUNCTION:
return "power toggle";
case CEC_USER_CONTROL_CODE_POWER_OFF_FUNCTION:
return "power off";
case CEC_USER_CONTROL_CODE_POWER_ON_FUNCTION:
return "power on";
case CEC_USER_CONTROL_CODE_F1_BLUE:
return "F1 (blue)";
case CEC_USER_CONTROL_CODE_F2_RED:
return "F2 (red)";
case CEC_USER_CONTROL_CODE_F3_GREEN:
return "F3 (green)";
case CEC_USER_CONTROL_CODE_F4_YELLOW:
return "F4 (yellow)";
case CEC_USER_CONTROL_CODE_F5:
return "F5";
case CEC_USER_CONTROL_CODE_DATA:
return "data";
case CEC_USER_CONTROL_CODE_AN_RETURN:
return "return (Samsung)";
case CEC_USER_CONTROL_CODE_AN_CHANNELS_LIST:
return "channels list (Samsung)";
default:
return "unknown";
}
}
static const char *ToString(cec_logical_address la)
{
switch (la & 0xf)
{
case CECDEVICE_TV:
return "TV";
case CECDEVICE_RECORDINGDEVICE1:
return "Recording Device 1";
case CECDEVICE_RECORDINGDEVICE2:
return "Recording Device 2";
case CECDEVICE_TUNER1:
return "Tuner 1";
case CECDEVICE_PLAYBACKDEVICE1:
return "Playback Device 1";
case CECDEVICE_AUDIOSYSTEM:
return "Audio System";
case CECDEVICE_TUNER2:
return "Tuner 2";
case CECDEVICE_TUNER3:
return "Tuner 3";
case CECDEVICE_PLAYBACKDEVICE2:
return "Playback Device 2";
case CECDEVICE_RECORDINGDEVICE3:
return "Recording Device 3";
case CECDEVICE_TUNER4:
return "Tuner 4";
case CECDEVICE_PLAYBACKDEVICE3:
return "Playback Device 3";
case CECDEVICE_RESERVED1:
return "Reserved 1";
case CECDEVICE_RESERVED2:
return "Reserved 2";
case CECDEVICE_FREEUSE:
return "Free use";
case CECDEVICE_UNREGISTERED:
default:
return "Unregistered";
}
}
static cec_opcode GetResponseOpcode(cec_opcode opcode)
{
switch (opcode)
{
case CEC_OPCODE_REQUEST_ACTIVE_SOURCE:
return CEC_OPCODE_ACTIVE_SOURCE;
case CEC_OPCODE_GET_CEC_VERSION:
return CEC_OPCODE_CEC_VERSION;
case CEC_OPCODE_GIVE_PHYSICAL_ADDRESS:
return CEC_OPCODE_REPORT_PHYSICAL_ADDRESS;
case CEC_OPCODE_GET_MENU_LANGUAGE:
return CEC_OPCODE_SET_MENU_LANGUAGE;
case CEC_OPCODE_GIVE_DECK_STATUS:
return CEC_OPCODE_DECK_STATUS;
case CEC_OPCODE_GIVE_TUNER_DEVICE_STATUS:
return CEC_OPCODE_TUNER_DEVICE_STATUS;
case CEC_OPCODE_GIVE_DEVICE_VENDOR_ID:
return CEC_OPCODE_DEVICE_VENDOR_ID;
case CEC_OPCODE_GIVE_OSD_NAME:
return CEC_OPCODE_SET_OSD_NAME;
case CEC_OPCODE_MENU_REQUEST:
return CEC_OPCODE_MENU_STATUS;
case CEC_OPCODE_GIVE_DEVICE_POWER_STATUS:
return CEC_OPCODE_REPORT_POWER_STATUS;
case CEC_OPCODE_GIVE_AUDIO_STATUS:
return CEC_OPCODE_REPORT_AUDIO_STATUS;
case CEC_OPCODE_GIVE_SYSTEM_AUDIO_MODE_STATUS:
return CEC_OPCODE_SYSTEM_AUDIO_MODE_STATUS;
case CEC_OPCODE_SYSTEM_AUDIO_MODE_REQUEST:
return CEC_OPCODE_SET_SYSTEM_AUDIO_MODE;
default:
break;
}
return CEC_OPCODE_NONE;
}
#endif // __HDMI_CEC_TYPES_H__

287
libarmbox/hisilicon.h Normal file
View File

@@ -0,0 +1,287 @@
#ifndef _hisilicon_h
#define _hisilicon_h
#define HI_FORMAT_MAX_URL_LEN (2048)
#define HI_FORMAT_MAX_FILE_NAME_LEN (512)
#define HI_FORMAT_TITLE_MAX_LEN (512)
#define HI_FORMAT_LANG_LEN (64)
#define HI_FORMAT_MAX_LANGUAGE_NUM (4)
#define HI_FORMAT_SERVICE_DESCRIPT_LEN (64)
typedef uint8_t HI_U8;
typedef uint16_t HI_U16;
typedef uint32_t HI_U32;
typedef int8_t HI_S8;
typedef int16_t HI_S16;
typedef int32_t HI_S32;
typedef uint64_t HI_U64;
typedef int64_t HI_S64;
typedef void HI_VOID;
typedef char HI_CHAR;
typedef enum
{
HI_FALSE = 0,
HI_TRUE = 1,
} HI_BOOL;
typedef enum hiFORMAT_SUBTITLE_TYPE_E
{
HI_FORMAT_SUBTITLE_ASS = 0x0, /**< ASS subtitle */
HI_FORMAT_SUBTITLE_LRC, /**< LRC subtitle */
HI_FORMAT_SUBTITLE_SRT, /**< SRT subtitle */
HI_FORMAT_SUBTITLE_SMI, /**< SMI subtitle */
HI_FORMAT_SUBTITLE_SUB, /**< SUB subtitle */
HI_FORMAT_SUBTITLE_TXT, /**< RAW UTF8 subtitle */
HI_FORMAT_SUBTITLE_HDMV_PGS, /**< pgs subtitle */
HI_FORMAT_SUBTITLE_DVB_SUB, /**< DVB subtitle */
HI_FORMAT_SUBTITLE_DVD_SUB, /**< DVD subtitle */
HI_FORMAT_SUBTITLE_TTML, /**< TTML subtitle */
HI_FORMAT_SUBTITLE_WEBVTT,
HI_FORMAT_SUBTITLE_BUTT
} HI_FORMAT_SUBTITLE_TYPE_E;
typedef enum hiFORMAT_AUDIO_TYPE_E
{
HI_FORMAT_AUDIO_MP2 = 0x000, /**< MPEG audio layer 1, 2.*/
HI_FORMAT_AUDIO_MP3, /**< MPEG audio layer 1, 2, 3.*/
HI_FORMAT_AUDIO_AAC,
HI_FORMAT_AUDIO_AC3,
HI_FORMAT_AUDIO_DTS,
HI_FORMAT_AUDIO_VORBIS,
HI_FORMAT_AUDIO_DVAUDIO,
HI_FORMAT_AUDIO_WMAV1,
HI_FORMAT_AUDIO_WMAV2,
HI_FORMAT_AUDIO_MACE3,
HI_FORMAT_AUDIO_MACE6,
HI_FORMAT_AUDIO_VMDAUDIO,
HI_FORMAT_AUDIO_SONIC,
HI_FORMAT_AUDIO_SONIC_LS,
HI_FORMAT_AUDIO_FLAC,
HI_FORMAT_AUDIO_MP3ADU,
HI_FORMAT_AUDIO_MP3ON4,
HI_FORMAT_AUDIO_SHORTEN,
HI_FORMAT_AUDIO_ALAC,
HI_FORMAT_AUDIO_WESTWOOD_SND1,
HI_FORMAT_AUDIO_GSM,
HI_FORMAT_AUDIO_QDM2,
HI_FORMAT_AUDIO_COOK,
HI_FORMAT_AUDIO_TRUESPEECH,
HI_FORMAT_AUDIO_TTA,
HI_FORMAT_AUDIO_SMACKAUDIO,
HI_FORMAT_AUDIO_QCELP,
HI_FORMAT_AUDIO_WAVPACK,
HI_FORMAT_AUDIO_DSICINAUDIO,
HI_FORMAT_AUDIO_IMC,
HI_FORMAT_AUDIO_MUSEPACK7,
HI_FORMAT_AUDIO_MLP,
HI_FORMAT_AUDIO_GSM_MS, /**< as found in WAV.*/
HI_FORMAT_AUDIO_ATRAC3,
HI_FORMAT_AUDIO_VOXWARE,
HI_FORMAT_AUDIO_APE,
HI_FORMAT_AUDIO_NELLYMOSER,
HI_FORMAT_AUDIO_MUSEPACK8,
HI_FORMAT_AUDIO_SPEEX,
HI_FORMAT_AUDIO_WMAVOICE,
HI_FORMAT_AUDIO_WMAPRO,
HI_FORMAT_AUDIO_WMALOSSLESS,
HI_FORMAT_AUDIO_ATRAC3P,
HI_FORMAT_AUDIO_EAC3,
HI_FORMAT_AUDIO_SIPR,
HI_FORMAT_AUDIO_MP1,
HI_FORMAT_AUDIO_TWINVQ,
HI_FORMAT_AUDIO_TRUEHD,
HI_FORMAT_AUDIO_MP4ALS,
HI_FORMAT_AUDIO_ATRAC1,
HI_FORMAT_AUDIO_BINKAUDIO_RDFT,
HI_FORMAT_AUDIO_BINKAUDIO_DCT,
HI_FORMAT_AUDIO_DRA,
HI_FORMAT_AUDIO_DTS_EXPRESS,
HI_FORMAT_AUDIO_PCM = 0x100, /**< various PCM codecs. */
HI_FORMAT_AUDIO_PCM_BLURAY = 0x121,
HI_FORMAT_AUDIO_ADPCM = 0x130, /**< various ADPCM codecs. */
HI_FORMAT_AUDIO_AMR_NB = 0x160,/**< various AMR codecs. */
HI_FORMAT_AUDIO_AMR_WB,
HI_FORMAT_AUDIO_AMR_AWB,
HI_FORMAT_AUDIO_RA_144 = 0x170, /**< RealAudio codecs. */
HI_FORMAT_AUDIO_RA_288,
HI_FORMAT_AUDIO_DPCM = 0x180, /**< various DPCM codecs. */
HI_FORMAT_AUDIO_G711 = 0x190, /**< various G.7xx codecs. */
HI_FORMAT_AUDIO_G722,
HI_FORMAT_AUDIO_G7231,
HI_FORMAT_AUDIO_G726,
HI_FORMAT_AUDIO_G728,
HI_FORMAT_AUDIO_G729AB,
HI_FORMAT_AUDIO_MULTI = 0x1f0, /**< support multi codecs. */
HI_FORMAT_AUDIO_BUTT = 0x1ff,
} HI_FORMAT_AUDIO_TYPE_E;
typedef enum hiFORMAT_VIDEO_TYPE_E
{
HI_FORMAT_VIDEO_MPEG2 = 0x0, /**< MPEG2*/
HI_FORMAT_VIDEO_MPEG4, /**< MPEG4 DIVX4 DIVX5*/
HI_FORMAT_VIDEO_AVS, /**< AVS*/
HI_FORMAT_VIDEO_H263, /**< H263*/
HI_FORMAT_VIDEO_H264, /**< H264*/
HI_FORMAT_VIDEO_REAL8, /**< REAL*/
HI_FORMAT_VIDEO_REAL9, /**< REAL*/
HI_FORMAT_VIDEO_VC1, /**< VC-1*/
HI_FORMAT_VIDEO_VP6, /**< VP6*/
HI_FORMAT_VIDEO_VP6F, /**< VP6F*/
HI_FORMAT_VIDEO_VP6A, /**< VP6A*/
HI_FORMAT_VIDEO_MJPEG, /**< MJPEG*/
HI_FORMAT_VIDEO_SORENSON, /**< SORENSON SPARK*/
HI_FORMAT_VIDEO_DIVX3, /**< DIVX3, not supported*/
HI_FORMAT_VIDEO_RAW, /**< RAW*/
HI_FORMAT_VIDEO_JPEG, /**< JPEG added for VENC*/
HI_FORMAT_VIDEO_VP8, /**<VP8*/
HI_FORMAT_VIDEO_MSMPEG4V1, /**< MS private MPEG4 */
HI_FORMAT_VIDEO_MSMPEG4V2,
HI_FORMAT_VIDEO_MSVIDEO1, /**< MS video */
HI_FORMAT_VIDEO_WMV1,
HI_FORMAT_VIDEO_WMV2,
HI_FORMAT_VIDEO_RV10,
HI_FORMAT_VIDEO_RV20,
HI_FORMAT_VIDEO_SVQ1, /**< Apple video */
HI_FORMAT_VIDEO_SVQ3, /**< Apple video */
HI_FORMAT_VIDEO_H261,
HI_FORMAT_VIDEO_VP3,
HI_FORMAT_VIDEO_VP5,
HI_FORMAT_VIDEO_CINEPAK,
HI_FORMAT_VIDEO_INDEO2,
HI_FORMAT_VIDEO_INDEO3,
HI_FORMAT_VIDEO_INDEO4,
HI_FORMAT_VIDEO_INDEO5,
HI_FORMAT_VIDEO_MJPEGB,
HI_FORMAT_VIDEO_MVC,
HI_FORMAT_VIDEO_HEVC, /**< HEVC(H265)*/
HI_FORMAT_VIDEO_DV,
HI_FORMAT_VIDEO_HUFFYUV,
HI_FORMAT_VIDEO_DIVX, /**< DIVX,not supported*/
HI_FORMAT_VIDEO_REALMAGICMPEG4, /**< REALMAGIC MPEG4,not supported*/
HI_FORMAT_VIDEO_VP9, /**<VP9*/
HI_FORMAT_VIDEO_WMV3,
HI_FORMAT_VIDEO_AVS2,
HI_FORMAT_VIDEO_BUTT
} HI_FORMAT_VIDEO_TYPE_E;
typedef enum hiFORMAT_SOURCE_TYPE_E
{
HI_FORMAT_SOURCE_LOCAL = 0x0, /**< Local file */
HI_FORMAT_SOURCE_NET_VOD, /**< Net VOD file */
HI_FORMAT_SOURCE_NET_LIVE, /**< Net Live stream */
HI_FORMAT_SOURCE_BUTT
} HI_FORMAT_SOURCE_TYPE_E;
typedef enum hiFORMAT_STREAM_TYPE_E
{
HI_FORMAT_STREAM_ES = 0x0, /**< Element stream (ES) file */
HI_FORMAT_STREAM_TS, /**< TS file */
HI_FORMAT_STREAM_BUTT
} HI_FORMAT_STREAM_TYPE_E;
typedef struct hiFORMAT_AUD_INFO_S
{
HI_S32 s32StreamIndex; /**< Stream index. The invalid value is ::HI_FORMAT_INVALID_STREAM_ID. */
HI_U32 u32Format; /**< Audio encoding format. For details about the value definition, see ::HI_FORMAT_AUDIO_TYPE_E. */
HI_U32 u32Profile; /**< Audio encoding version, such as 0x160(WMAV1) and 0x161 (WMAV2). It is valid only for WMA encoding. */
HI_U32 u32SampleRate; /**< 8000,11025,441000,... */
HI_U16 u16BitPerSample; /**< Number of bits occupied by each audio sampling point such as 8 bits or 16 bits. */
HI_U16 u16Channels; /**< Number of channels, 1 or 2. *//**< CNcomment:ÉùµÀÊý, 1 or 2 */
HI_S32 s32SubStreamID; /**< Sub audio stream ID */
HI_U32 u32BlockAlign; /**< Number of bytes contained in a packet */
HI_U32 u32Bitrate; /**< Audio bit rate, in the unit of bit/s. */
HI_BOOL bBigEndian; /**< Big endian or little endian. It is valid only for the PCM format */
HI_CHAR aszLanguage[HI_FORMAT_LANG_LEN]; /**< Audio stream language */
HI_U32 u32ExtradataSize; /**< Length of the extended data */
HI_U8* pu8Extradata; /**< Extended data */
HI_VOID* pCodecContext; /**< Audio decode context */
HI_U32 u32Role; /**< Role descriptor value of mpeg dash. the most 8 bits is scheme value(refer to HI_FORMAT_ROLE_SCHEME_E), the left 24 bits is descriptor value, the descriptor value may be the bitwise '|' result of value define in HI_FORMAT_ROLE_VALUE_E*/
HI_U32 u32Accessibility; /**< Accessbilitydescriptor value of mpeg dash. the most 8 bits is scheme value(refer to HI_FORMAT_ROLE_SCHEME_E), the left 24 bits is descriptor value, the descriptor value type is number*/
HI_S64 s64Duration; /**< Duration of audio stream, in the unit of ms. */
HI_U32 u32CodecTag; /**< Codec tag of audio stream format, fourcc (LSB first, so "ABCD" -> ('D'<<24) + ('C'<<16) + ('B'<<8) + 'A'). */
} HI_FORMAT_AUD_INFO_S;
typedef struct hiFORMAT_VID_INFO_S
{
HI_S32 s32StreamIndex; /**< Stream index. The invalid value is ::HI_FORMAT_INVALID_STREAM_ID. */
HI_U32 u32Format; /**< Video encoding format. For details about the value definition, see ::HI_FORMAT_VIDEO_TYPE_E. */
HI_U16 u16RefFrameNum; /**< Number of reference frames. */
HI_U16 u16Profile; /**< Profile level. */
HI_U16 u16Width; /**< Width, in the unit of pixel. */
HI_U16 u16Height; /**< Height, in the unit of pixel. */
HI_U16 u16FpsInteger; /**< Integer part of the frame rate */
HI_U16 u16FpsDecimal; /**< Decimal part of the frame rate */
HI_U32 u32Bitrate; /**< Video bit rate, in the unit of bit/s. */
HI_U32 u32CodecVersion; /**< Version of codec. */
HI_U32 u32Rotate; /**< Video rotation angle, value is 90/180/270, default value is 0 */
HI_U32 u32Reversed;
HI_BOOL bEnableTVP;
HI_U32 u32ExtradataSize; /**< Length of the extended data */
HI_U8* pu8Extradata; /**< Extended data */
HI_VOID* pCodecContext; /**< video decode context */
HI_U32 u32Role; /**< Role descriptor value of mpeg dash. the most 8 bits is scheme value(refer to HI_FORMAT_ROLE_SCHEME_E), the left 24 bits is descriptor value, the descriptor value may be the bitwise '|' result of value define in HI_FORMAT_ROLE_VALUE_E*/
HI_U32 u32Accessibility; /**< Accessbilitydescriptor value of mpeg dash. the most 8 bits is scheme value(refer to HI_FORMAT_ROLE_SCHEME_E), the left 24 bits is descriptor value, the descriptor value type is number*/
HI_S64 s64Duration; /**< Duration of video stream, in the unit of ms. */
HI_BOOL bNoPts; /**<this stream has no pts info or pts is invalid> */
} HI_FORMAT_VID_INFO_S;
typedef struct hiFORMAT_SUB_INFO_S
{
HI_S32 s32StreamIndex; /**< Stream index. The invalid value is ::HI_FORMAT_INVALID_STREAM_ID. */
HI_U32 u32Format; /**< Subtitle format, For details about the value definition, see::HI_FORMAT_SUBTITLE_TYPE_E */
HI_U32 u32CharSet; /**< Encoding type of the subtitle, the value range is as follows:
1. The default value is 0.
2. The value of the u32CharSet is the identified byte encoding value if the IdentStream byte encoding function (for details about the definition, see hi_charset_common.h) is set.
3. If the ConvStream function (for details about the definition, see hi_charset_common.h) is set and the invoke interface is called to set the encoding type to be converted by implementing HI_FORMAT_INVOKE_SET_SOURCE_CODETYPE, the value of the u32CharSet is the configured encoding type */
HI_BOOL bExtSub; /**< Whether subtitles are external subtitles. When bExtSub is HI_TRUE, the subtitles are external. When bExtSub is HI_FALSE, the subtitles are internal. */
HI_U32 u32StreamNum; /**< contains stream number */
HI_CHAR paszLanguage[HI_FORMAT_MAX_LANGUAGE_NUM][HI_FORMAT_LANG_LEN]; /**< Subtitle language */
HI_U16 u16OriginalFrameWidth; /**< Width of the original image */
HI_U16 u16OriginalFrameHeight; /**< Height of the original image */
HI_U32 u32ExtradataSize; /**< Length of the extended data */
HI_U8* pu8Extradata; /**< Extended data */
HI_VOID* pCodecContext; /**< Audio decode context */
HI_U32 u32Role; /**< Role descriptor value of mpeg dash. the most 8 bits is scheme value(refer to HI_FORMAT_ROLE_SCHEME_E), the left 24 bits is descriptor value, the descriptor value may be the bitwise '|' result of value define in HI_FORMAT_ROLE_VALUE_E*/
HI_U32 u32Accessibility; /**< Accessibility descriptor value of mpeg dash. the most 8 bits is scheme value(refer to HI_FORMAT_ROLE_SCHEME_E), the left 24 bits is descriptor value, value type is number*/
HI_CHAR paszFileName[HI_FORMAT_MAX_URL_LEN]; /**< File name of external subtitle. */
} HI_FORMAT_SUB_INFO_S;
typedef struct hiFORMAT_PROGRAM_INFO_S
{
HI_U32 u32VidStreamNum; /**< Number of video streams */
HI_FORMAT_VID_INFO_S* pastVidStream; /**< Video stream information */
HI_U32 u32AudStreamNum; /**< Number of audio streams */
HI_FORMAT_AUD_INFO_S* pastAudStream; /**< Audio stream information */
HI_U32 u32SubStreamNum; /**< Number of subtitles */
HI_FORMAT_SUB_INFO_S* pastSubStream; /**< Subtitle information */
HI_CHAR aszServiceName[HI_FORMAT_SERVICE_DESCRIPT_LEN]; /**< Program service name info */
HI_CHAR aszServiceProvider[HI_FORMAT_SERVICE_DESCRIPT_LEN]; /**< Program service provider info */
HI_S64 s64ProgramDuration;
HI_S64 s64ProgramStartTime;
} HI_FORMAT_PROGRAM_INFO_S;
typedef struct hiFORMAT_FILE_INFO_S
{
HI_FORMAT_SOURCE_TYPE_E eSourceType; /**< File source type */
HI_FORMAT_STREAM_TYPE_E eStreamType; /**< File stream type */
HI_S64 s64FileSize; /**< File size, in the unit of byte. */
HI_S64 s64StartTime; /**< Start time of playing a file, in the unit is ms. */
HI_S64 s64Duration; /**< Total duration of a file, in the unit of ms. */
HI_U32 u32Bitrate; /**< File bit rate, in the unit of bit/s. */
HI_CHAR aszFileFormat[HI_FORMAT_TITLE_MAX_LEN]; /**< File demuxer info .Not used now*/
HI_U32 u32ProgramNum; /**< Actual number of programs */
HI_FORMAT_PROGRAM_INFO_S* pastProgramInfo; /**< Program information */
HI_BOOL bIsDivx; /**< If the stream is DIVX restricted stream,HI_TRUE yes,HI_FALSE no */
HI_BOOL bIsDrmFile;
} HI_FORMAT_FILE_INFO_S;
#endif

View File

@@ -1,6 +1,6 @@
#include <stdio.h>
#include <config.h>
#include "init_lib.h"
#include <stdio.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <sys/types.h>
@@ -9,20 +9,21 @@
#include <string.h>
#include <unistd.h>
#include "init.h"
#include "pwrmngr.h"
#include <proc_tools.h>
#include "lt_debug.h"
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_INIT, NULL, args)
#define lt_info(args...) _lt_info(TRIPLE_DEBUG_INIT, NULL, args)
#include "hal_debug.h"
#define hal_debug(args...) _hal_debug(HAL_DEBUG_INIT, NULL, args)
#define hal_info(args...) _hal_info(HAL_DEBUG_INIT, NULL, args)
static bool initialized = false;
void init_td_api()
void hal_api_init()
{
if (!initialized)
lt_debug_init();
lt_info("%s begin, initialized=%d, debug=0x%02x\n", __FUNCTION__, (int)initialized, debuglevel);
hal_debug_init();
hal_info("%s begin, initialized=%d, debug=0x%02x\n", __FUNCTION__, (int)initialized, debuglevel);
if (!initialized)
{
cCpuFreqManager f;
@@ -37,13 +38,17 @@ void init_td_api()
proc_put("/proc/stb/fb/dst_width", buffer, strlen(buffer));
sprintf(buffer, "%x", 1);
proc_put("/proc/stb/fb/dst_apply", buffer, strlen(buffer));
#if BOXMODEL_VUSOLO4K || BOXMODEL_VUDUO4K || BOXMODEL_VUDUO4KSE || BOXMODEL_VUULTIMO4K || BOXMODEL_VUUNO4KSE || BOXMODEL_VUUNO4K
sprintf(buffer, "%s", "enable");
proc_put("/proc/stb/frontend/fbc/fcc", buffer, strlen(buffer));
#endif
}
initialized = true;
lt_info("%s end\n", __FUNCTION__);
hal_info("%s end\n", __FUNCTION__);
}
void shutdown_td_api()
void hal_api_exit()
{
lt_info("%s, initialized = %d\n", __FUNCTION__, (int)initialized);
hal_info("%s, initialized = %d\n", __FUNCTION__, (int)initialized);
initialized = false;
}

View File

@@ -1,2 +0,0 @@
#warning using init_cs.h from libspark
#include "init_lib.h"

View File

@@ -1,5 +0,0 @@
#ifndef __INIT_TD_H
#define __INIT_TD_H
void init_td_api();
void shutdown_td_api();
#endif

View File

@@ -35,11 +35,11 @@
#include "playback_gst.h"
#include "lt_debug.h"
#define lt_debug(args...) _lt_debug(HAL_DEBUG_PLAYBACK, this, args)
#define lt_info(args...) _lt_info(HAL_DEBUG_PLAYBACK, this, args)
#define lt_debug_c(args...) _lt_debug(HAL_DEBUG_PLAYBACK, NULL, args)
#define lt_info_c(args...) _lt_info(HAL_DEBUG_PLAYBACK, NULL, args)
#include "hal_debug.h"
#define hal_debug(args...) _hal_debug(HAL_DEBUG_PLAYBACK, this, args)
#define hal_info(args...) _hal_info(HAL_DEBUG_PLAYBACK, this, args)
#define hal_debug_c(args...) _hal_debug(HAL_DEBUG_PLAYBACK, NULL, args)
#define hal_info_c(args...) _hal_info(HAL_DEBUG_PLAYBACK, NULL, args)
static const char * FILENAME = "[playback_gst.cpp]";
extern cVideo * videoDecoder;
@@ -52,18 +52,18 @@ extern cAudio * audioDecoder;
typedef enum
{
GST_PLAY_FLAG_VIDEO = (1 << 0),
GST_PLAY_FLAG_AUDIO = (1 << 1),
GST_PLAY_FLAG_TEXT = (1 << 2),
GST_PLAY_FLAG_VIS = (1 << 3),
GST_PLAY_FLAG_SOFT_VOLUME = (1 << 4),
GST_PLAY_FLAG_NATIVE_AUDIO = (1 << 5),
GST_PLAY_FLAG_NATIVE_VIDEO = (1 << 6),
GST_PLAY_FLAG_DOWNLOAD = (1 << 7),
GST_PLAY_FLAG_BUFFERING = (1 << 8),
GST_PLAY_FLAG_DEINTERLACE = (1 << 9),
GST_PLAY_FLAG_SOFT_COLORBALANCE = (1 << 10),
GST_PLAY_FLAG_FORCE_FILTERS = (1 << 11),
GST_PLAY_FLAG_VIDEO = (1 << 0),
GST_PLAY_FLAG_AUDIO = (1 << 1),
GST_PLAY_FLAG_TEXT = (1 << 2),
GST_PLAY_FLAG_VIS = (1 << 3),
GST_PLAY_FLAG_SOFT_VOLUME = (1 << 4),
GST_PLAY_FLAG_NATIVE_AUDIO = (1 << 5),
GST_PLAY_FLAG_NATIVE_VIDEO = (1 << 6),
GST_PLAY_FLAG_DOWNLOAD = (1 << 7),
GST_PLAY_FLAG_BUFFERING = (1 << 8),
GST_PLAY_FLAG_DEINTERLACE = (1 << 9),
GST_PLAY_FLAG_SOFT_COLORBALANCE = (1 << 10),
GST_PLAY_FLAG_FORCE_FILTERS = (1 << 11),
} GstPlayFlags;
@@ -72,10 +72,12 @@ GstElement * audioSink = NULL;
GstElement * videoSink = NULL;
gchar * uri = NULL;
GstTagList * m_stream_tags = NULL;
pthread_mutex_t mutex_tag_ist;
static int end_eof = 0;
#define HTTP_TIMEOUT 30
// taken from record.h
#define REC_MAX_APIDS 20
#define REC_MAX_APIDS 10
int real_apids[REC_MAX_APIDS];
gint match_sinktype(const GValue *velement, const gchar *type)
@@ -100,7 +102,7 @@ void processMpegTsSection(GstMpegtsSection* section)
for (guint i = 0; i < pmt->streams->len; ++i) {
const GstMpegtsPMTStream* stream = static_cast<const GstMpegtsPMTStream*>(g_ptr_array_index(pmt->streams, i));
if (stream->stream_type == 0x05 || stream->stream_type >= 0x80) {
lt_info_c( "%s:%s Audio Stream pid: %d\n", FILENAME, __FUNCTION__, stream->pid);
hal_info_c( "%s:%s Audio Stream pid: %d\n", FILENAME, __FUNCTION__, stream->pid);
real_apids[cnt] = stream->pid;
cnt++;
}
@@ -164,7 +166,7 @@ void playbinNotifySource(GObject *object, GParamSpec *param_spec, gpointer user_
if (!name.empty() && !value.empty())
{
GValue header;
lt_info_c( "%s:%s setting extra-header '%s:%s'\n", FILENAME, __FUNCTION__, name.c_str(), value.c_str());
hal_info_c( "%s:%s setting extra-header '%s:%s'\n", FILENAME, __FUNCTION__, name.c_str(), value.c_str());
memset(&header, 0, sizeof(GValue));
g_value_init(&header, G_TYPE_STRING);
g_value_set_string(&header, value.c_str());
@@ -172,7 +174,7 @@ void playbinNotifySource(GObject *object, GParamSpec *param_spec, gpointer user_
}
else
{
lt_info_c( "%s:%s Invalid header format %s\n", FILENAME, __FUNCTION__, _this->extra_headers.c_str());
hal_info_c( "%s:%s Invalid header format %s\n", FILENAME, __FUNCTION__, _this->extra_headers.c_str());
break;
}
}
@@ -188,8 +190,6 @@ void playbinNotifySource(GObject *object, GParamSpec *param_spec, gpointer user_
GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
{
gchar * sourceName;
// source
GstObject * source;
source = GST_MESSAGE_SRC(msg);
@@ -197,8 +197,6 @@ GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
if (!GST_IS_OBJECT(source))
return GST_BUS_DROP;
sourceName = gst_object_get_name(source);
switch (GST_MESSAGE_TYPE(msg))
{
case GST_MESSAGE_EOS:
@@ -214,18 +212,21 @@ GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
GError *err;
gst_message_parse_error(msg, &err, &debug);
g_free (debug);
lt_info_c( "%s:%s - GST_MESSAGE_ERROR: %s (%i) from %s\n", FILENAME, __FUNCTION__, err->message, err->code, sourceName );
gchar * sourceName = gst_object_get_name(source);
hal_info_c( "%s:%s - GST_MESSAGE_ERROR: %s (%i) from %s\n", FILENAME, __FUNCTION__, err->message, err->code, sourceName );
if ( err->domain == GST_STREAM_ERROR )
{
if ( err->code == GST_STREAM_ERROR_CODEC_NOT_FOUND )
{
if ( g_strrstr(sourceName, "videosink") )
lt_info_c( "%s:%s - GST_MESSAGE_ERROR: videosink\n", FILENAME, __FUNCTION__ ); //FIXME: how shall playback handle this event???
hal_info_c( "%s:%s - GST_MESSAGE_ERROR: videosink\n", FILENAME, __FUNCTION__ ); //FIXME: how shall playback handle this event???
else if ( g_strrstr(sourceName, "audiosink") )
lt_info_c( "%s:%s - GST_MESSAGE_ERROR: audioSink\n", FILENAME, __FUNCTION__ ); //FIXME: how shall playback handle this event???
hal_info_c( "%s:%s - GST_MESSAGE_ERROR: audioSink\n", FILENAME, __FUNCTION__ ); //FIXME: how shall playback handle this event???
}
}
g_error_free(err);
if(sourceName)
g_free(sourceName);
end_eof = 1; // NOTE: just to exit
@@ -241,8 +242,12 @@ GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
g_free (debug);
if ( inf->domain == GST_STREAM_ERROR && inf->code == GST_STREAM_ERROR_DECODE )
{
gchar * sourceName = gst_object_get_name(source);
if ( g_strrstr(sourceName, "videosink") )
lt_info_c( "%s:%s - GST_MESSAGE_INFO: videosink\n", FILENAME, __FUNCTION__ ); //FIXME: how shall playback handle this event???
hal_info_c( "%s:%s - GST_MESSAGE_INFO: videosink\n", FILENAME, __FUNCTION__ ); //FIXME: how shall playback handle this event???
if(sourceName)
g_free(sourceName);
}
g_error_free(inf);
break;
@@ -250,9 +255,16 @@ GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
case GST_MESSAGE_TAG:
{
GstTagList *tags, *result;
GstTagList *tags = NULL, *result = NULL;
gst_message_parse_tag(msg, &tags);
if(tags == NULL)
break;
if(!GST_IS_TAG_LIST(tags))
break;
pthread_mutex_lock (&mutex_tag_ist);
result = gst_tag_list_merge(m_stream_tags, tags, GST_TAG_MERGE_REPLACE);
if (result)
{
@@ -260,6 +272,8 @@ GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
{
gst_tag_list_unref(tags);
gst_tag_list_unref(result);
pthread_mutex_unlock (&mutex_tag_ist);
break;
}
if (m_stream_tags)
@@ -268,6 +282,8 @@ GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
gst_tag_list_unref(result);
}
pthread_mutex_unlock (&mutex_tag_ist);
const GValue *gv_image = gst_tag_list_get_value_index(tags, GST_TAG_IMAGE, 0);
if ( gv_image )
{
@@ -287,11 +303,12 @@ GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
int ret = write(fd, data, size);
gst_buffer_unmap(buf_image, &map);
close(fd);
lt_info_c("%s:%s - /tmp/.id3coverart %d bytes written\n", FILENAME, __FUNCTION__, ret);
hal_info_c("%s:%s - /tmp/.id3coverart %d bytes written\n", FILENAME, __FUNCTION__, ret);
}
}
gst_tag_list_unref(tags);
lt_debug_c( "%s:%s - GST_MESSAGE_INFO: update info tags\n", FILENAME, __FUNCTION__); //FIXME: how shall playback handle this event???
if (tags)
gst_tag_list_unref(tags);
hal_debug_c( "%s:%s - GST_MESSAGE_INFO: update info tags\n", FILENAME, __FUNCTION__); //FIXME: how shall playback handle this event???
break;
}
case GST_MESSAGE_ELEMENT:
@@ -312,7 +329,7 @@ GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
if(old_state == new_state)
break;
lt_info_c( "%s:%s - GST_MESSAGE_STATE_CHANGED: state transition %s -> %s\n", FILENAME, __FUNCTION__, gst_element_state_get_name(old_state), gst_element_state_get_name(new_state));
hal_info_c( "%s:%s - GST_MESSAGE_STATE_CHANGED: state transition %s -> %s\n", FILENAME, __FUNCTION__, gst_element_state_get_name(old_state), gst_element_state_get_name(new_state));
GstStateChange transition = (GstStateChange)GST_STATE_TRANSITION(old_state, new_state);
@@ -324,7 +341,7 @@ GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
case GST_STATE_CHANGE_READY_TO_PAUSED:
{
GstIterator *children;
GValue r = { 0, };
GValue r = G_VALUE_INIT;
if (audioSink)
{
@@ -338,22 +355,20 @@ GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
videoSink = NULL;
}
children = gst_bin_iterate_recurse(GST_BIN(m_gst_playbin));
if (gst_iterator_find_custom(children, (GCompareFunc)match_sinktype, &r, (gpointer)"GstDVBAudioSink"))
if (children && gst_iterator_find_custom(children, (GCompareFunc)match_sinktype, &r, (gpointer)"GstDVBAudioSink"))
{
audioSink = GST_ELEMENT_CAST(g_value_dup_object (&r));
g_value_unset (&r);
lt_info_c( "%s %s - audio sink created\n", FILENAME, __FUNCTION__);
hal_info_c( "%s %s - audio sink created\n", FILENAME, __FUNCTION__);
}
gst_iterator_free(children);
children = gst_bin_iterate_recurse(GST_BIN(m_gst_playbin));
if (gst_iterator_find_custom(children, (GCompareFunc)match_sinktype, &r, (gpointer)"GstDVBVideoSink"))
if (children && gst_iterator_find_custom(children, (GCompareFunc)match_sinktype, &r, (gpointer)"GstDVBVideoSink"))
{
videoSink = GST_ELEMENT_CAST(g_value_dup_object (&r));
g_value_unset (&r);
lt_info_c( "%s %s - video sink created\n", FILENAME, __FUNCTION__);
hal_info_c( "%s %s - video sink created\n", FILENAME, __FUNCTION__);
}
gst_iterator_free(children);
@@ -396,7 +411,7 @@ GstBusSyncReply Gst_bus_call(GstBus *bus, GstMessage *msg, gpointer user_data)
cPlayback::cPlayback(int num)
{
lt_info( "%s:%s\n", FILENAME, __FUNCTION__);
hal_info( "%s:%s\n", FILENAME, __FUNCTION__);
const gchar *nano_str;
guint major, minor, micro, nano;
@@ -404,6 +419,10 @@ cPlayback::cPlayback(int num)
gst_version (&major, &minor, &micro, &nano);
gst_mpegts_initialize();
pthread_mutex_init (&mutex_tag_ist, NULL);
if (nano == 1)
nano_str = "(CVS)";
else if (nano == 2)
@@ -411,7 +430,7 @@ cPlayback::cPlayback(int num)
else
nano_str = "";
lt_info( "%s:%s - This program is linked against GStreamer %d.%d.%d %s\n",
hal_info( "%s:%s - This program is linked against GStreamer %d.%d.%d %s\n",
FILENAME, __FUNCTION__,
major, minor, micro, nano_str);
@@ -426,16 +445,18 @@ cPlayback::cPlayback(int num)
cPlayback::~cPlayback()
{
lt_info( "%s:%s\n", FILENAME, __FUNCTION__);
hal_info( "%s:%s\n", FILENAME, __FUNCTION__);
//FIXME: all deleting stuff is done in Close()
pthread_mutex_lock (&mutex_tag_ist);
if (m_stream_tags)
gst_tag_list_free(m_stream_tags);
gst_tag_list_unref(m_stream_tags);
pthread_mutex_unlock (&mutex_tag_ist);
}
//Used by Fileplay
bool cPlayback::Open(playmode_t PlayMode)
{
lt_info("%s: PlayMode %d\n", __func__, PlayMode);
hal_info("%s: PlayMode %d\n", __func__, PlayMode);
if (PlayMode != PLAYMODE_TS)
{
@@ -451,7 +472,7 @@ bool cPlayback::Open(playmode_t PlayMode)
// used by movieplay
void cPlayback::Close(void)
{
lt_info( "%s:%s\n", FILENAME, __FUNCTION__);
hal_info( "%s:%s\n", FILENAME, __FUNCTION__);
Stop();
@@ -461,8 +482,9 @@ void cPlayback::Close(void)
// disconnect sync handler callback
GstBus * bus = gst_pipeline_get_bus(GST_PIPELINE (m_gst_playbin));
gst_bus_set_sync_handler(bus, NULL, NULL, NULL);
gst_object_unref(bus);
lt_info( "%s:%s - GST bus handler closed\n", FILENAME, __FUNCTION__);
if (bus)
gst_object_unref(bus);
hal_info( "%s:%s - GST bus handler closed\n", FILENAME, __FUNCTION__);
}
// close gst
@@ -473,7 +495,7 @@ void cPlayback::Close(void)
gst_object_unref(GST_OBJECT(audioSink));
audioSink = NULL;
lt_info( "%s:%s - GST audio Sink closed\n", FILENAME, __FUNCTION__);
hal_info( "%s:%s - GST audio Sink closed\n", FILENAME, __FUNCTION__);
}
if (videoSink)
@@ -481,12 +503,12 @@ void cPlayback::Close(void)
gst_object_unref(GST_OBJECT(videoSink));
videoSink = NULL;
lt_info( "%s:%s - GST video Sink closed\n", FILENAME, __FUNCTION__);
hal_info( "%s:%s - GST video Sink closed\n", FILENAME, __FUNCTION__);
}
// unref m_gst_playbin
gst_object_unref (GST_OBJECT (m_gst_playbin));
lt_info( "%s:%s - GST playbin closed\n", FILENAME, __FUNCTION__);
hal_info( "%s:%s - GST playbin closed\n", FILENAME, __FUNCTION__);
m_gst_playbin = NULL;
@@ -508,7 +530,7 @@ bool cPlayback::Start(std::string filename, std::string headers)
bool cPlayback::Start(char *filename, int /*vpid*/, int /*vtype*/, int /*apid*/, int /*ac3*/, int /*duration*/, std::string headers)
{
lt_info( "%s:%s\n", FILENAME, __FUNCTION__);
hal_info( "%s:%s\n", FILENAME, __FUNCTION__);
if (!headers.empty())
extra_headers = headers;
@@ -520,8 +542,11 @@ bool cPlayback::Start(char *filename, int /*vpid*/, int /*vtype*/, int /*apid*/,
mAudioStream = 0;
init_jump = -1;
gst_tag_list_unref(m_stream_tags);
pthread_mutex_lock (&mutex_tag_ist);
if (m_stream_tags)
gst_tag_list_unref(m_stream_tags);
m_stream_tags = NULL;
pthread_mutex_unlock (&mutex_tag_ist);
unlink("/tmp/.id3coverart");
@@ -562,10 +587,9 @@ bool cPlayback::Start(char *filename, int /*vpid*/, int /*vtype*/, int /*apid*/,
else
uri = g_filename_to_uri(filename, NULL, NULL);
lt_info("%s:%s - filename=%s\n", FILENAME, __FUNCTION__, filename);
hal_info("%s:%s - filename=%s\n", FILENAME, __FUNCTION__, filename);
guint flags = GST_PLAY_FLAG_AUDIO | GST_PLAY_FLAG_VIDEO | \
GST_PLAY_FLAG_TEXT | GST_PLAY_FLAG_NATIVE_VIDEO;
guint flags = GST_PLAY_FLAG_AUDIO | GST_PLAY_FLAG_VIDEO | GST_PLAY_FLAG_NATIVE_VIDEO;
/* increase the default 2 second / 2 MB buffer limitations to 5s / 5MB */
int m_buffer_size = 5*1024*1024;
@@ -575,7 +599,7 @@ bool cPlayback::Start(char *filename, int /*vpid*/, int /*vtype*/, int /*apid*/,
if(m_gst_playbin)
{
lt_info("%s:%s - m_gst_playbin\n", FILENAME, __FUNCTION__);
hal_info("%s:%s - m_gst_playbin\n", FILENAME, __FUNCTION__);
if(isHTTP)
{
@@ -594,7 +618,8 @@ bool cPlayback::Start(char *filename, int /*vpid*/, int /*vtype*/, int /*apid*/,
//gstbus handler
GstBus * bus = gst_pipeline_get_bus( GST_PIPELINE(m_gst_playbin) );
gst_bus_set_sync_handler(bus, Gst_bus_call, NULL, NULL);
gst_object_unref(bus);
if (bus)
gst_object_unref(bus);
first = true;
@@ -614,7 +639,7 @@ bool cPlayback::Start(char *filename, int /*vpid*/, int /*vtype*/, int /*apid*/,
}
else
{
lt_info("%s:%s - failed to create GStreamer pipeline!, sorry we can not play\n", FILENAME, __FUNCTION__);
hal_info("%s:%s - failed to create GStreamer pipeline!, sorry we can not play\n", FILENAME, __FUNCTION__);
playing = false;
return false;
@@ -627,7 +652,7 @@ bool cPlayback::Start(char *filename, int /*vpid*/, int /*vtype*/, int /*apid*/,
bool cPlayback::Play(void)
{
lt_info( "%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
hal_info( "%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
if(playing == true)
return true;
@@ -639,7 +664,7 @@ bool cPlayback::Play(void)
playing = true;
playstate = STATE_PLAY;
}
lt_info("%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
hal_info("%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
return playing;
}
@@ -648,7 +673,7 @@ bool cPlayback::Stop(void)
{
if(playing == false)
return false;
lt_info( "%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
hal_info( "%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
// stop
if(m_gst_playbin)
@@ -658,7 +683,7 @@ bool cPlayback::Stop(void)
playing = false;
lt_info( "%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
hal_info( "%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
playstate = STATE_STOP;
@@ -667,7 +692,7 @@ bool cPlayback::Stop(void)
bool cPlayback::SetAPid(int pid, bool /*ac3*/)
{
lt_info("%s: pid %i\n", __func__, pid);
hal_info("%s: pid %i\n", __func__, pid);
int to_audio = pid;
@@ -705,7 +730,7 @@ void cPlayback::trickSeek(int ratio)
bool cPlayback::SetSpeed(int speed)
{
lt_info( "%s:%s speed %d\n", FILENAME, __FUNCTION__, speed);
hal_info( "%s:%s speed %d\n", FILENAME, __FUNCTION__, speed);
if (!decoders_closed)
{
@@ -764,7 +789,7 @@ bool cPlayback::SetSpeed(int speed)
bool cPlayback::SetSlow(int slow)
{
lt_info( "%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
hal_info( "%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
if(playing == false)
return false;
@@ -809,12 +834,17 @@ bool cPlayback::GetPosition(int &position, int &duration)
if (audioSink || videoSink)
{
g_signal_emit_by_name(audioSink ? audioSink : videoSink, "get-decoder-time", &pts);
if (!GST_CLOCK_TIME_IS_VALID(pts)){
lt_info( "%s - %d failed\n", __FUNCTION__, __LINE__);
if (!GST_CLOCK_TIME_IS_VALID(pts))
{
hal_info( "%s - %d failed\n", __FUNCTION__, __LINE__);
}
}else{
}
else
{
if(!gst_element_query_position(m_gst_playbin, fmt, &pts))
lt_info( "%s - %d failed\n", __FUNCTION__, __LINE__);
{
hal_info( "%s - %d failed\n", __FUNCTION__, __LINE__);
}
}
position = pts / 1000000.0;
// duration
@@ -835,23 +865,25 @@ bool cPlayback::GetPosition(int &position, int &duration)
bool cPlayback::SetPosition(int position, bool absolute)
{
lt_info("%s: pos %d abs %d playing %d\n", __func__, position, absolute, playing);
hal_info("%s: pos %d abs %d playing %d\n", __func__, position, absolute, playing);
gint64 time_nanoseconds;
gint64 pos;
GstFormat fmt = GST_FORMAT_TIME;
GstState state;
if(m_gst_playbin)
{
gst_element_get_state(m_gst_playbin, &state, NULL, GST_CLOCK_TIME_NONE);
if ( (state == GST_STATE_PAUSED) && first)
{
init_jump = position;
first = false;
return false;
if(first){
GstState state;
gst_element_get_state(m_gst_playbin, &state, NULL, GST_CLOCK_TIME_NONE);
if ( (state == GST_STATE_PAUSED) && first)
{
init_jump = position;
first = false;
return false;
}
}
gint64 time_nanoseconds;
gint64 pos;
GstFormat fmt = GST_FORMAT_TIME;
if (!absolute)
{
gst_element_query_position(m_gst_playbin, fmt, &pos);
@@ -864,7 +896,7 @@ bool cPlayback::SetPosition(int position, bool absolute)
time_nanoseconds = position * 1000000.0;
}
gst_element_seek(m_gst_playbin, 1.0, GST_FORMAT_TIME, GST_SEEK_FLAG_FLUSH, GST_SEEK_TYPE_SET, time_nanoseconds, GST_SEEK_TYPE_NONE, GST_CLOCK_TIME_NONE);
gst_element_seek(m_gst_playbin, 1.0, GST_FORMAT_TIME, (GstSeekFlags)(GST_SEEK_FLAG_FLUSH | GST_SEEK_FLAG_ACCURATE), GST_SEEK_TYPE_SET, time_nanoseconds, GST_SEEK_TYPE_NONE, GST_CLOCK_TIME_NONE);
}
return true;
@@ -872,7 +904,10 @@ bool cPlayback::SetPosition(int position, bool absolute)
void cPlayback::FindAllPids(int *apids, unsigned int *ac3flags, unsigned int *numpida, std::string * language)
{
lt_info( "%s:%s\n", FILENAME, __FUNCTION__);
hal_info( "%s:%s\n", FILENAME, __FUNCTION__);
language->clear();
*numpida = 0;
if(m_gst_playbin)
{
@@ -880,14 +915,12 @@ void cPlayback::FindAllPids(int *apids, unsigned int *ac3flags, unsigned int *nu
// get audio
g_object_get (m_gst_playbin, "n-audio", &n_audio, NULL);
lt_info("%s: %d audio\n", __FUNCTION__, n_audio);
hal_info("%s: %d audio\n", __FUNCTION__, n_audio);
if(n_audio == 0)
return;
language->clear();
for (i = 0; i < n_audio; i++)
for (i = 0; i < n_audio && i < REC_MAX_APIDS; i++)
{
// apids
apids[i]= real_apids[i] ? real_apids[i] : i;
@@ -896,7 +929,8 @@ void cPlayback::FindAllPids(int *apids, unsigned int *ac3flags, unsigned int *nu
g_signal_emit_by_name (m_gst_playbin, "get-audio-pad", i, &pad);
GstCaps * caps = gst_pad_get_current_caps(pad);
gst_object_unref(pad);
if (pad)
gst_object_unref(pad);
if (!caps)
continue;
@@ -938,14 +972,15 @@ void cPlayback::FindAllPids(int *apids, unsigned int *ac3flags, unsigned int *nu
//return atPCM;
ac3flags[i] = 0;
gst_caps_unref(caps);
if (caps)
gst_caps_unref(caps);
//(ac3flags[i] > 2) ? ac3flags[i] = 1 : ac3flags[i] = 0;
g_signal_emit_by_name (m_gst_playbin, "get-audio-tags", i, &tags);
if (tags && GST_IS_TAG_LIST(tags))
if (tags)
{
if (gst_tag_list_get_string(tags, GST_TAG_LANGUAGE_CODE, &g_lang))
if (GST_IS_TAG_LIST(tags) && gst_tag_list_get_string(tags, GST_TAG_LANGUAGE_CODE, &g_lang))
{
std::string slang;
if (gst_tag_check_language_code(g_lang))
@@ -956,7 +991,7 @@ void cPlayback::FindAllPids(int *apids, unsigned int *ac3flags, unsigned int *nu
language[i] = "unk";
else
language[i] = slang.c_str();
lt_info("%s: language:%s\n", __FUNCTION__, language[i].c_str());
hal_info("%s: language:%s\n", __FUNCTION__, language[i].c_str());
g_free(g_lang);
}
gst_tag_list_free(tags);
@@ -974,7 +1009,7 @@ void cPlayback::getMeta()
bool cPlayback::SyncAV(void)
{
lt_info( "%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
hal_info( "%s:%s playing %d\n", FILENAME, __FUNCTION__, playing);
if(playing == false )
return false;
@@ -986,10 +1021,10 @@ void cPlayback::RequestAbort()
{
}
void cPlayback::FindAllSubs(uint16_t *, unsigned short *, uint16_t *numpida, std::string *)
void cPlayback::FindAllSubs(int * /*pids*/, unsigned int * /*supp*/, unsigned int *num, std::string * /*lang*/)
{
printf("%s:%s\n", FILENAME, __func__);
*numpida = 0;
*num = 0;
}
void cPlayback::GetChapters(std::vector<int> &positions, std::vector<std::string> &titles)
@@ -998,7 +1033,18 @@ void cPlayback::GetChapters(std::vector<int> &positions, std::vector<std::string
titles.clear();
}
bool cPlayback::SelectSubtitles(int pid)
void cPlayback::GetTitles(std::vector<int> &playlists, std::vector<std::string> &titles, int &current)
{
playlists.clear();
titles.clear();
current = 0;
}
void cPlayback::SetTitle(int /*title*/)
{
}
bool cPlayback::SelectSubtitles(int pid, std::string /*charset*/)
{
printf("%s:%s pid %i\n", FILENAME, __func__, pid);
return true;
@@ -1008,22 +1054,40 @@ void cPlayback::GetMetadata(std::vector<std::string> &keys, std::vector<std::str
{
keys.clear();
values.clear();
if (gst_tag_list_is_empty (m_stream_tags))
GstTagList *meta_list = NULL;
pthread_mutex_lock (&mutex_tag_ist);
if(m_stream_tags){
meta_list = gst_tag_list_copy(m_stream_tags);
}
pthread_mutex_unlock (&mutex_tag_ist);
if (meta_list == NULL)
return;
for (guint i = 0, icnt = gst_tag_list_n_tags(m_stream_tags); i < icnt; i++)
if (gst_tag_list_is_empty(meta_list)){
gst_tag_list_unref(meta_list);
return;
}
for (guint i = 0, icnt = gst_tag_list_n_tags(meta_list); i < icnt; i++)
{
const gchar *name = gst_tag_list_nth_tag_name(m_stream_tags, i);
const gchar *name = gst_tag_list_nth_tag_name(meta_list, i);
if (!name)
{
continue;
}
for (guint j = 0, jcnt = gst_tag_list_get_tag_size(m_stream_tags, name); j < jcnt; j++)
for (guint j = 0, jcnt = gst_tag_list_get_tag_size(meta_list, name); j < jcnt; j++)
{
const GValue *val;
val = gst_tag_list_get_value_index(m_stream_tags, name, j);
val = gst_tag_list_get_value_index(meta_list, name, j);
if (val == NULL)
continue;
if (G_VALUE_HOLDS_STRING(val))
{
@@ -1063,6 +1127,7 @@ void cPlayback::GetMetadata(std::vector<std::string> &keys, std::vector<std::str
}
}
gst_tag_list_unref(meta_list);
printf("%s:%s %d tags found\n", FILENAME, __func__, (int)keys.size());
}
@@ -1099,7 +1164,7 @@ int cPlayback::GetAPid(void)
{
gint current_audio = 0;
g_object_get (m_gst_playbin, "current-audio", &current_audio, NULL);
lt_info("%s: %d audio\n", __FUNCTION__, current_audio);
hal_info("%s: %d audio\n", __FUNCTION__, current_audio);
return real_apids[current_audio] ? real_apids[current_audio] : current_audio;
}
@@ -1107,7 +1172,7 @@ int cPlayback::GetVPid(void)
{
gint current_video = 0;
g_object_get (m_gst_playbin, "current-video", &current_video, NULL);
lt_info("%s: %d video\n", __FUNCTION__, current_video);
hal_info("%s: %d video\n", __FUNCTION__, current_video);
return current_video;
}

View File

@@ -16,8 +16,8 @@
*
*/
#ifndef __PLAYBACK_CS_H
#define __PLAYBACK_CS_H
#ifndef __PLAYBACK_GST_H__
#define __PLAYBACK_GST_H__
#include <string>
#include <stdint.h>
@@ -81,11 +81,13 @@ public:
int GetSubtitlePid(void);
bool SetPosition(int position, bool absolute = false);
void FindAllPids(int *apids, unsigned int *ac3flags, unsigned int *numpida, std::string *language);
void FindAllPids(uint16_t *apids, unsigned short *ac3flags, uint16_t *numpida, std::string *language) { FindAllPids((int*) apids, (unsigned int*) ac3flags, (unsigned int*) numpida, language); };
void FindAllSubs(int *pids, unsigned int *supported, unsigned int *numpida, std::string *language);
void FindAllSubs(uint16_t *pids, unsigned short *supported, uint16_t *numpida, std::string *language) { FindAllSubs((int*) pids, (unsigned int*) supported, (unsigned int*) numpida, language); };
bool SelectSubtitles(int pid, std::string charset = "");
void FindAllSubtitlePids(int *pids, unsigned int *numpids, std::string *language);
void FindAllTeletextsubtitlePids(int *pids, unsigned int *numpidt, std::string *tlanguage, int *mags, int *pages);
void RequestAbort(void);
void FindAllSubs(uint16_t *pids, unsigned short *supported, uint16_t *numpida, std::string *language);
bool SelectSubtitles(int pid);
uint64_t GetReadCount(void);
void GetChapters(std::vector<int> &positions, std::vector<std::string> &titles);
void GetMetadata(std::vector<std::string> &keys, std::vector<std::string> &values);
@@ -94,10 +96,12 @@ public:
std::string extra_headers;
std::string user_agent;
void GetTitles(std::vector<int> &playlists, std::vector<std::string> &titles, int &current);
void SetTitle(int title);
//
~cPlayback();
void getMeta();
};
#endif
#endif // __PLAYBACK_GST_H__

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,184 @@
/*
Copyright (C) 2018 TangoCash
License: GPLv2
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;
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.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef __HAL_PLAYBACK_H
#define __HAL_PLAYBACK_H
#include <string>
#include <vector>
#include <OpenThreads/Thread>
#include <OpenThreads/Condition>
#include "hisilicon.h"
typedef enum
{
PLAYMODE_TS = 0,
PLAYMODE_FILE
} playmode_t;
struct AVFormatContext;
struct errorInfo
{
std::string error_message;
std::string missing_codec;
};
class cPlayback
{
friend class CStreamInfo2;
friend class netlink_event;
private:
int m_video_fd;
int m_audio_fd;
bool enabled;
bool playing, first;
bool no_probe;
bool got_vpts_ts;
int nPlaybackSpeed;
int mAudioStream;
int mSubtitleStream;
int mTeletextStream;
int64_t vpts_ts;
bool Stop(void);
bool decoders_closed;
playmode_t pm;
std::string fn_ts;
std::string fn_xml;
off64_t last_size;
int init_jump;
const char *getVidFormatStr(uint32_t format);
const char *getAudFormatStr(uint32_t format);
const char *getSubFormatStr(uint32_t format);
public:
cPlayback(int num = 0);
~cPlayback();
bool Open(playmode_t PlayMode);
void Close(void);
bool Start(char *filename, int vpid, int vtype, int apid, int ac3, int duration, std::string headers = "", std::string filename2 = "");
bool Start(std::string filename, std::string headers = "", std::string filename2 = "");
bool SetAPid(int pid, bool ac3 = false);
bool SetVPid(int /*pid*/);
bool SetSubtitlePid(int pid);
bool SetTeletextPid(int pid);
int GetAPid(void)
{
return mAudioStream;
}
int GetVPid(void)
{
return 0;
}
int GetSubtitlePid(void)
{
return mSubtitleStream;
}
int GetTeletextPid(void);
bool SetSpeed(int speed);
bool GetSpeed(int &speed) const;
bool GetPosition(int &position, int &duration);
void GetPts(uint64_t &pts);
bool SetPosition(int position, bool absolute = false);
void FindAllPids(short unsigned int *apids, short unsigned int *ac3flags, short unsigned int *numpida, std::string *language);
void FindAllSubtitlePids(int *pids, unsigned int *numpids, std::string *language);
void FindAllTeletextsubtitlePids(int */*pids*/, unsigned int *numpidt, std::string */*tlanguage*/, int */*mags*/, int */*pages*/);
void FindAllSubs(short unsigned int *pids, short unsigned int *supported, short unsigned int *numpida, std::string *language);
bool SelectSubtitles(int pid, std::string charset = "");
void RequestAbort(void);
bool IsPlaying(void);
uint64_t GetReadCount(void);
void GetChapters(std::vector<int> &positions, std::vector<std::string> &titles);
void GetMetadata(std::vector<std::string> &keys, std::vector<std::string> &values);
AVFormatContext *GetAVFormatContext();
void ReleaseAVFormatContext();
void GetTitles(std::vector<int> &playlists, std::vector<std::string> &titles, int &current);
void SetTitle(int title);
};
class netlink_event : public OpenThreads::Thread
{
friend class cPlayback;
protected:
bool running;
private:
netlink_event();
~netlink_event();
static netlink_event *netlink_event_instance;
cPlayback *player;
int m_player_state;
enum
{
stIdle, stRunning, stStopped,
};
struct streamid
{
uint16_t programid;
uint16_t videostreamid;
uint16_t audiostreamid;
uint16_t subtitlestreamid;
} streamid;
int m_state;
bool m_paused;
bool m_buffering;
HI_FORMAT_FILE_INFO_S fileinfo;
struct nlmsghdr *nlh;
int m_bufferpercentage;
uint32_t m_seekable;
uint32_t m_download_progress;
int netlink_socket;
int receive_netlink_message();
errorInfo m_errorInfo;
void run();
void Receive();
public:
static netlink_event* getInstance();
uint64_t getDuration()
{
return fileinfo.s64Duration;
};
bool Start(cPlayback *player);
bool Stop();
};
#if 0 // for later use, maybe
class video_event : public OpenThreads::Thread
{
friend class cPlayback;
protected:
bool running;
private:
int m_video_fd;
void run();
void Receive();
public:
bool Start(int video_fd);
bool Stop();
};
#endif
#endif

View File

@@ -0,0 +1,889 @@
#define __USE_FILE_OFFSET64 1
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <unistd.h>
#include <sstream>
#include <audio_lib.h>
#include <video_lib.h>
extern "C" {
#include <common.h>
extern OutputHandler_t OutputHandler;
extern PlaybackHandler_t PlaybackHandler;
extern ContainerHandler_t ContainerHandler;
extern ManagerHandler_t ManagerHandler;
extern int32_t ffmpeg_av_dict_set( const char *key, const char *value, int32_t flags);
}
#include "playback_libeplayer3.h"
#include "hal_debug.h"
#define hal_debug(args...) _hal_debug(HAL_DEBUG_PLAYBACK, this, args)
#define hal_info(args...) _hal_info(HAL_DEBUG_PLAYBACK, this, args)
static Context_t *player = NULL;
extern cAudio *audioDecoder;
extern cVideo *videoDecoder;
OpenThreads::Mutex cPlayback::mutex;
//Used by Fileplay
bool cPlayback::Open(playmode_t PlayMode)
{
const char *aPLAYMODE[] =
{
"PLAYMODE_TS",
"PLAYMODE_FILE"
};
if (PlayMode != PLAYMODE_TS)
{
audioDecoder->closeDevice();
videoDecoder->closeDevice();
decoders_closed = true;
}
pm = PlayMode;
got_vpts_ts = false;
vpts_ts = 0;
fn_ts = "";
fn_xml = "";
last_size = 0;
nPlaybackSpeed = 0;
init_jump = -1;
avft = avformat_alloc_context();
if (!player)
{
player = (Context_t *) malloc(sizeof(Context_t));
}
if (player)
{
player->playback = &PlaybackHandler;
player->output = &OutputHandler;
player->container = &ContainerHandler;
player->manager = &ManagerHandler;
hal_info("%s - player output name: %s PlayMode: %s\n", __func__, player->output->Name, aPLAYMODE[PlayMode]);
}
//Registration of output devices
if (player && player->output)
{
player->output->Command(player, OUTPUT_ADD, (void *)"audio");
player->output->Command(player, OUTPUT_ADD, (void *)"video");
player->output->Command(player, OUTPUT_ADD, (void *)"subtitle");
}
return 0;
}
void cPlayback::Close(void)
{
hal_info("%s\n", __func__);
//Dagobert: movieplayer does not call stop, it calls close ;)
mutex.lock();
if(playing)
Stop();
mutex.unlock();
if (decoders_closed)
{
audioDecoder->openDevice();
videoDecoder->openDevice();
decoders_closed = false;
}
}
bool cPlayback::Start(std::string filename, std::string headers, std::string filename2)
{
return Start((char *) filename.c_str(), 0, 0, 0, 0, 0, headers,filename2);
}
bool cPlayback::Start(char *filename, int vpid, int vtype, int apid, int ac3, int, std::string headers, std::string filename2)
{
bool ret = false;
bool isHTTP = false;
no_probe = false;
hal_info("%s - filename=%s vpid=%u vtype=%d apid=%u ac3=%d\n", __func__, filename, vpid, vtype, apid, ac3);
init_jump = -1;
//create playback path
mAudioStream = 0;
mSubtitleStream = -1;
mTeletextStream = -1;
std::string file;
if (*filename == '/')
file = "file://";
file += filename;
if ((file.find(":31339/id=") != std::string::npos) || (file.find(":10000") != std::string::npos) || (file.find(":8001/") != std::string::npos)) // for LocalTV and Entertain-TV streaming
no_probe = true;
if (file.substr(0, 7) == "file://")
{
if (file.substr(file.length() - 3) == ".ts")
{
fn_ts = file.substr(7);
fn_xml = file.substr(7, file.length() - 9);
fn_xml += "xml";
no_probe = true;
}
}
else
isHTTP = true;
if(isHTTP && headers.empty())
{
size_t pos = file.find('#');
if (pos != std::string::npos)
{
headers = file.substr(pos + 1);
pos = headers.find("User-Agent=");
if (pos != std::string::npos)
headers.replace(pos+10, 1, ": ");
}
}
if(!headers.empty()){
const char hkey[] = "headers";
ffmpeg_av_dict_set(hkey, headers.c_str(), 0);
}
std::string szSecondFile;
char *file2 = NULL;
if(!filename2.empty()){
szSecondFile = filename2;
file2 = (char *) szSecondFile.c_str();
}
PlayFiles_t playbackFiles = { (char *) file.c_str(), file2, NULL, NULL, 0, 0, 0, 0};
if (player->playback->Command(player, PLAYBACK_OPEN, &playbackFiles) == 0)
{
if (pm == PLAYMODE_TS)
{
struct stat64 s;
if (!stat64(file.c_str(), &s))
last_size = s.st_size;
ret = true;
videoDecoder->Stop(false);
audioDecoder->Stop();
}
else
{
//AUDIO
if (player && player->manager && player->manager->audio)
{
char ** TrackList = NULL;
player->manager->audio->Command(player, MANAGER_LIST, &TrackList);
if (TrackList != NULL)
{
printf("AudioTrack List\n");
int i = 0;
for (i = 0; TrackList[i] != NULL; i += 2)
{
printf("\t%s - %s\n", TrackList[i], TrackList[i + 1]);
free(TrackList[i]);
free(TrackList[i + 1]);
}
free(TrackList);
}
}
//SUB
if (player && player->manager && player->manager->subtitle)
{
char ** TrackList = NULL;
player->manager->subtitle->Command(player, MANAGER_LIST, &TrackList);
if (TrackList != NULL)
{
printf("SubtitleTrack List\n");
int i = 0;
for (i = 0; TrackList[i] != NULL; i+=2)
{
printf("\t%s - %s\n", TrackList[i], TrackList[i + 1]);
free(TrackList[i]);
free(TrackList[i + 1]);
}
free(TrackList);
}
}
/*
//Teletext
if (player && player->manager && player->manager->teletext)
{
char ** TrackList = NULL;
player->manager->teletext->Command(player, MANAGER_LIST, &TrackList);
if (TrackList != NULL)
{
printf("TeletextTrack List\n");
int i = 0;
for (i = 0; TrackList[i] != NULL; i += 2)
{
printf("\t%s - %s\n", TrackList[i], TrackList[i + 1]);
free(TrackList[i]);
free(TrackList[i + 1]);
}
free(TrackList);
}
}
*/
//Chapters
if (player && player->manager && player->manager->chapter)
{
char ** TrackList = NULL;
player->manager->chapter->Command(player, MANAGER_LIST, &TrackList);
if (TrackList != NULL)
{
printf("Chapter List\n");
int i = 0;
for (i = 0; TrackList[i] != NULL; i += 2)
{
printf("\t%s - %s\n", TrackList[i], TrackList[i + 1]);
free(TrackList[i]);
free(TrackList[i + 1]);
}
free(TrackList);
}
}
playing = true;
first = true;
player->output->Command(player, OUTPUT_OPEN, NULL);
ret = (player->playback->Command(player, PLAYBACK_PLAY, NULL) == 0);
if (ret && !isHTTP)
playing = ret = (player->playback->Command(player, PLAYBACK_PAUSE, NULL) == 0);
}
}
return ret;
}
bool cPlayback::Stop(void)
{
hal_info("%s playing %d\n", __func__, playing);
if (player && player->playback)
player->playback->Command(player, PLAYBACK_STOP, NULL);
if (player && player->output)
player->output->Command(player, OUTPUT_CLOSE, NULL);
if (player && player->output)
{
player->output->Command(player, OUTPUT_DEL, (void *)"audio");
player->output->Command(player, OUTPUT_DEL, (void *)"video");
player->output->Command(player, OUTPUT_DEL, (void *)"subtitle");
}
if (player && player->playback)
player->playback->Command(player, PLAYBACK_CLOSE, NULL);
playing = false;
return true;
}
bool cPlayback::SetAPid(int pid, bool /* ac3 */)
{
hal_info("%s\n", __func__);
int i = pid;
if (pid != mAudioStream)
{
if (player && player->playback)
player->playback->Command(player, PLAYBACK_SWITCH_AUDIO, (void *)&i);
mAudioStream = pid;
}
return true;
}
bool cPlayback::SetVPid(int /*pid*/)
{
hal_info("%s\n", __func__);
return true;
}
bool cPlayback::SetSubtitlePid(int pid)
{
hal_info("%s\n", __func__);
int i = pid;
if (pid != mSubtitleStream)
{
if (player && player->playback)
player->playback->Command(player, PLAYBACK_SWITCH_SUBTITLE, (void *)&i);
mSubtitleStream = pid;
}
return true;
}
bool cPlayback::SetTeletextPid(int pid)
{
hal_info("%s\n", __func__);
//int i = pid;
if (pid != mTeletextStream)
{
//if (player && player->playback)
// player->playback->Command(player, PLAYBACK_SWITCH_TELETEXT, (void*)&i);
mTeletextStream = pid;
}
return true;
}
bool cPlayback::SetSpeed(int speed)
{
hal_info("%s playing %d speed %d\n", __func__, playing, speed);
if (!decoders_closed)
{
audioDecoder->closeDevice();
videoDecoder->closeDevice();
decoders_closed = true;
usleep(500000);
if (player && player->output && player->playback)
{
player->output->Command(player, OUTPUT_OPEN, NULL);
if (player->playback->Command(player, PLAYBACK_PLAY, NULL) == 0)
playing = true;
}
}
if (!playing)
return false;
if (player && player->playback)
{
int result = 0;
if(nPlaybackSpeed == 0 && speed > 1)
{
result = player->playback->Command(player, PLAYBACK_CONTINUE, NULL);
}
nPlaybackSpeed = speed;
if (speed > 1)
{
/* direction switch ? */
if (player->playback->BackWard)
{
int r = 0;
result = player->playback->Command(player, PLAYBACK_FASTBACKWARD, (void *)&r);
printf("result = %d\n", result);
}
result = player->playback->Command(player, PLAYBACK_FASTFORWARD, (void *)&speed);
}
else if (speed < 0)
{
/* direction switch ? */
if (player->playback->isForwarding)
{
result = player->playback->Command(player, PLAYBACK_CONTINUE, NULL);
printf("result = %d\n", result);
}
result = player->playback->Command(player, PLAYBACK_FASTBACKWARD, (void *)&speed);
}
else if (speed == 0)
{
/* konfetti: hmmm accessing the member isn't very proper */
if ((player->playback->isForwarding) || (!player->playback->BackWard))
player->playback->Command(player, PLAYBACK_PAUSE, NULL);
else
{
int _speed = 0; /* means end of reverse playback */
player->playback->Command(player, PLAYBACK_FASTBACKWARD, (void *)&_speed);
}
}
else
{
result = player->playback->Command(player, PLAYBACK_CONTINUE, NULL);
}
if (init_jump > -1)
{
SetPosition(init_jump, true);
init_jump = -1;
}
if (result != 0)
{
printf("returning false\n");
return false;
}
}
return true;
}
bool cPlayback::GetSpeed(int &speed) const
{
hal_debug("%s\n", __func__);
speed = nPlaybackSpeed;
return true;
}
void cPlayback::GetPts(uint64_t &pts)
{
if (player && player->playback)
player->playback->Command(player, PLAYBACK_PTS, (void *)&pts);
}
// in milliseconds
bool cPlayback::GetPosition(int &position, int &duration)
{
bool got_duration = false;
hal_debug("%s %d %d\n", __func__, position, duration);
/* hack: if the file is growing (timeshift), then determine its length
* by comparing the mtime with the mtime of the xml file */
if (pm == PLAYMODE_TS)
{
struct stat64 s;
if (!stat64(fn_ts.c_str(), &s))
{
if (!playing || last_size != s.st_size)
{
last_size = s.st_size;
time_t curr_time = s.st_mtime;
if (!stat64(fn_xml.c_str(), &s))
{
duration = (curr_time - s.st_mtime) * 1000;
if (!playing)
return true;
got_duration = true;
}
}
}
}
if (!playing)
return false;
if (player && player->playback && !player->playback->isPlaying)
{
hal_info("%s !!!!EOF!!!! < -1\n", __func__);
position = duration + 1000;
return false;
}
int64_t vpts = 0;
if (player && player->playback)
player->playback->Command(player, PLAYBACK_PTS, &vpts);
if (vpts <= 0)
{
//printf("ERROR: vpts==0");
}
else
{
/* workaround for crazy vpts value during timeshift */
if (!got_vpts_ts && pm == PLAYMODE_TS)
{
vpts_ts = vpts;
got_vpts_ts = true;
}
if (got_vpts_ts)
vpts -= vpts_ts;
/* end workaround */
/* len is in nanoseconds. we have 90 000 pts per second. */
position = vpts / 90;
}
if (got_duration)
return true;
int64_t length = 0;
if (player && player->playback)
player->playback->Command(player, PLAYBACK_LENGTH, &length);
if (length <= 0)
{
duration = duration + 1000;
}
else
{
duration = length * 1000;
}
return true;
}
bool cPlayback::SetPosition(int position, bool absolute)
{
hal_info("%s %d\n", __func__, position);
if (playing && first)
{
/* the calling sequence is:
* Start() - paused
* SetPosition() - which fails if not running
* SetSpeed() - to start playing
* so let's remember the initial jump position and later jump to it
*/
init_jump = position;
first = false;
return false;
}
int64_t pos = (position / 1000.0);
if (player && player->playback)
player->playback->Command(player, absolute ? PLAYBACK_SEEK_ABS : PLAYBACK_SEEK, (void *)&pos);
return true;
}
void cPlayback::FindAllPids(uint16_t *apids, unsigned short *ac3flags, uint16_t *numpida, std::string *language)
{
hal_info("%s\n", __func__);
const int max_numpida = 40;//MAX_PLAYBACK_PIDS defined in neutrino movieplayer.h
*numpida = 0;
if (player && player->playback && player->playback->isPlaying && player->manager && player->manager->audio)
{
char **TrackList = NULL;
player->manager->audio->Command(player, MANAGER_LIST, &TrackList);
if (TrackList != NULL)
{
printf("AudioTrack List\n");
int i = 0, j = 0;
for (i = 0, j = 0; TrackList[i] != NULL; i += 2, j++)
{
printf("\t%s - %s\n", TrackList[i], TrackList[i + 1]);
if (j < max_numpida)
{
int _pid = 0;
std::string _lang ;
std::istringstream iss(TrackList[i]) ;
iss >> _pid;
iss >> _lang;
if (_pid && !_lang.empty())
{
apids[j] = _pid;
// atUnknown, atMPEG, atMP3, atAC3, atDTS, atAAC, atPCM, atOGG, atFLAC
if (!strncmp("A_MPEG/L3", TrackList[i + 1], 9))
ac3flags[j] = 3;
if (!strncmp("A_MP3", TrackList[i + 1], 5))
ac3flags[j] = 4;
else if (!strncmp("A_AC3", TrackList[i + 1], 5))
ac3flags[j] = 1;
else if (!strncmp("A_EAC3", TrackList[i + 1], 6))
ac3flags[j] = 7;
else if (!strncmp("A_DTS", TrackList[i + 1], 5))
ac3flags[j] = 6;
else if (!strncmp("A_AAC", TrackList[i + 1], 5))
ac3flags[j] = 5;
else if (!strncmp("A_PCM", TrackList[i + 1], 5))
ac3flags[j] = 0; //todo
else if (!strncmp("A_VORBIS", TrackList[i + 1], 8))
ac3flags[j] = 0; //todo
else if (!strncmp("A_FLAC", TrackList[i + 1], 6))
ac3flags[j] = 0; //todo
else
ac3flags[j] = 0; //todo
std::string _language = "";
_language += _lang;
_language += " - ";
_language += "(";
_language += TrackList[i + 1];
_language += ")";
language[j] = _language;
}
}
free(TrackList[i]);
free(TrackList[i + 1]);
}
free(TrackList);
*numpida = j;
}
}
}
void cPlayback::FindAllSubtitlePids(int *pids, unsigned int *numpids, std::string *language)
{
hal_info("%s\n", __func__);
int max_numpids = *numpids;
*numpids = 0;
if (player && player->manager && player->manager->subtitle)
{
char **TrackList = NULL;
player->manager->subtitle->Command(player, MANAGER_LIST, &TrackList);
if (TrackList != NULL)
{
printf("SubtitleTrack List\n");
int i = 0, j = 0;
for (i = 0, j = 0; TrackList[i] != NULL; i += 2, j++)
{
printf("\t%s - %s\n", TrackList[i], TrackList[i + 1]);
if (j < max_numpids)
{
int _pid = 0;
std::string _lang ;
std::istringstream iss(TrackList[i]) ;
iss >> _pid;
iss >> _lang;
if (_pid && !_lang.empty())
{
pids[j] = _pid;
language[j] = _lang;
}
}
free(TrackList[i]);
free(TrackList[i + 1]);
}
free(TrackList);
*numpids = j;
}
}
}
void cPlayback::FindAllTeletextsubtitlePids(int */*pids*/, unsigned int *numpids, std::string */*language*/, int */*mags*/, int */*pages*/)
{
hal_info("%s\n", __func__);
//int max_numpids = *numpids;
*numpids = 0;
/* if (player && player->manager && player->manager->teletext)
{
char **TrackList = NULL;
player->manager->teletext->Command(player, MANAGER_LIST, &TrackList);
if (TrackList != NULL)
{
printf("Teletext List\n");
int i = 0, j = 0;
for (i = 0, j = 0; TrackList[i] != NULL; i += 2)
{
int type = 0;
printf("\t%s - %s\n", TrackList[i], TrackList[i + 1]);
if (j < max_numpids)
{
int _pid;
if (2 != sscanf(TrackList[i], "%d %*s %d %*d %*d", &_pid, &type))
continue;
if (type != 2 && type != 5) // return subtitles only
continue;
pids[j] = _pid;
language[j] = std::string(TrackList[i]);
j++;
}
free(TrackList[i]);
free(TrackList[i + 1]);
}
free(TrackList);
*numpids = j;
}
} */
}
int cPlayback::GetTeletextPid(void)
{
hal_info("%s\n", __func__);
int pid = -1;
/* if (player && player->manager && player->manager->teletext)
{
char **TrackList = NULL;
player->manager->teletext->Command(player, MANAGER_LIST, &TrackList);
if (TrackList != NULL)
{
printf("Teletext List\n");
int i = 0;
for (i = 0; TrackList[i] != NULL; i += 2)
{
int type = 0;
printf("\t%s - %s\n", TrackList[i], TrackList[i+1]);
if (pid < 0)
{
if (2 != sscanf(TrackList[i], "%*d %d %*s %d %*d %*d", &pid, &type))
continue;
if (type != 1)
pid = -1;
}
free(TrackList[i]);
free(TrackList[i + 1]);
}
free(TrackList);
}
} */
printf("teletext pid id %d (0x%x)\n", pid, pid);
return pid;
}
/* dummy functions for subtitles */
void cPlayback::FindAllSubs(int * /*pids*/, unsigned int * /*supp*/, unsigned int *num, std::string * /*lang*/)
{
*num = 0;
}
bool cPlayback::SelectSubtitles(int /*pid*/, std::string /*charset*/)
{
return false;
}
void cPlayback::GetChapters(std::vector<int> &positions, std::vector<std::string> &titles)
{
positions.clear();
titles.clear();
if (player && player->manager && player->manager->chapter)
{
char **TrackList = NULL;
player->manager->chapter->Command(player, MANAGER_LIST, &TrackList);
if (TrackList != NULL)
{
printf("%s: Chapter List\n", __func__);
int i = 0;
for (i = 0; TrackList[i] != NULL; i += 2)
{
printf("\t%s - %s\n", TrackList[i], TrackList[i + 1]);
int pos = atoi(TrackList[i]);
std::string title(TrackList[i + 1]);
positions.push_back(pos);
titles.push_back(title);
free(TrackList[i]);
free(TrackList[i + 1]);
}
free(TrackList);
}
}
}
void cPlayback::GetTitles(std::vector<int> &playlists, std::vector<std::string> &titles, int &current)
{
playlists.clear();
titles.clear();
current = 0;
}
void cPlayback::SetTitle(int /*title*/)
{
}
void cPlayback::GetMetadata(std::vector<std::string> &keys, std::vector<std::string> &values)
{
keys.clear();
values.clear();
char **metadata = NULL;
if (player && player->playback)
{
player->playback->Command(player, PLAYBACK_METADATA, &metadata);
if (metadata)
{
for (char **m = metadata; *m;)
{
keys.push_back(*m);
free(*m++);
values.push_back(*m);
free(*m++);
}
free(metadata);
}
}
}
cPlayback::cPlayback(int num __attribute__((unused)))
{
hal_info("%s\n", __func__);
playing = false;
decoders_closed = false;
first = false;
player = NULL;
}
cPlayback::~cPlayback()
{
hal_info("%s\n", __func__);
RequestAbort();
mutex.lock();
if (player)
{
free(player);
player = NULL;
}
mutex.unlock();
}
void cPlayback::RequestAbort()
{
if (player && player->playback)
{
hal_info("%s\n", __func__);
mutex.lock();
if (player && player->playback && player->playback->isPlaying)
{
Stop();
player->playback->abortRequested = 1;
}
else if(player->playback->isHttp && !player->playback->isPlaying &&!player->playback->abortRequested)
{
player->playback->abortRequested = 1;
}
mutex.unlock();
}
}
bool cPlayback::IsPlaying()
{
if (player && player->playback)
return player->playback->isPlaying;
return false;
}
uint64_t cPlayback::GetReadCount()
{
if (player && player->playback)
{
return player->playback->readCount;
}
return 0;
}
AVFormatContext *cPlayback::GetAVFormatContext()
{
if (player && player->container && player->container->selectedContainer)
{
player->container->selectedContainer->Command(player, CONTAINER_GET_AVFCONTEXT, avft);
}
return avft;
}
void cPlayback::ReleaseAVFormatContext()
{
avft->streams = NULL;
avft->nb_streams = NULL;
}
#if 0
bool cPlayback::IsPlaying(void) const
{
hal_info("%s\n", __func__);
/* konfetti: there is no event/callback mechanism in libeplayer2
* so in case of ending playback we have no information on a
* terminated stream currently (or did I oversee it?).
* So let's ask the player the state.
*/
if (playing)
{
return player->playback->isPlaying;
}
return playing;
}
#endif

View File

@@ -0,0 +1,92 @@
#ifndef __PLAYBACK_LIBEPLAYER3_H__
#define __PLAYBACK_LIBEPLAYER3_H__
#include <string>
#include <vector>
#include <OpenThreads/Mutex>
typedef enum
{
PLAYMODE_TS = 0,
PLAYMODE_FILE
} playmode_t;
struct AVFormatContext;
class cPlayback
{
friend class CStreamInfo2;
private:
static OpenThreads::Mutex mutex;
bool enabled;
bool playing, first;
bool no_probe;
bool got_vpts_ts;
int nPlaybackSpeed;
int mAudioStream;
int mSubtitleStream;
int mTeletextStream;
int64_t vpts_ts;
bool Stop(void);
bool decoders_closed;
playmode_t pm;
std::string fn_ts;
std::string fn_xml;
off64_t last_size;
int init_jump;
AVFormatContext *avft;
public:
cPlayback(int num = 0);
~cPlayback();
bool Open(playmode_t PlayMode);
void Close(void);
bool Start(char *filename, int vpid, int vtype, int apid, int ac3, int duration, std::string headers = "", std::string filename2 = "");
bool Start(std::string filename, std::string headers = "", std::string filename2 = "");
bool SetAPid(int pid, bool ac3 = false);
bool SetVPid(int /*pid*/);
bool SetSubtitlePid(int pid);
bool SetTeletextPid(int pid);
int GetAPid(void) { return mAudioStream; }
int GetVPid(void) { return 0; }
int GetSubtitlePid(void) { return mSubtitleStream; }
int GetTeletextPid(void);
bool SetSpeed(int speed);
bool GetSpeed(int &speed) const;
bool GetPosition(int &position, int &duration);
void GetPts(uint64_t &pts);
bool SetPosition(int position, bool absolute = false);
void FindAllPids(uint16_t *apids, unsigned short *ac3flags, uint16_t *numpida, std::string *language);
void FindAllSubs(int *pids, unsigned int *supported, unsigned int *numpida, std::string *language);
void FindAllSubs(uint16_t *pids, unsigned short *supported, uint16_t *numpida, std::string *language) { FindAllSubs((int*) pids, (unsigned int*) supported, (unsigned int*) numpida, language); };
bool SelectSubtitles(int pid, std::string charset = "");
void FindAllSubtitlePids(int *pids, unsigned int *numpids, std::string *language);
void FindAllTeletextsubtitlePids(int */*pids*/, unsigned int *numpidt, std::string */*tlanguage*/, int */*mags*/, int */*pages*/);
void RequestAbort(void);
bool IsPlaying(void);
uint64_t GetReadCount(void);
void GetChapters(std::vector<int> &positions, std::vector<std::string> &titles);
void GetMetadata(std::vector<std::string> &keys, std::vector<std::string> &values);
AVFormatContext *GetAVFormatContext();
void ReleaseAVFormatContext();
void GetTitles(std::vector<int> &playlists, std::vector<std::string> &titles, int &current);
void SetTitle(int title);
#if 0
// Functions that are not used by movieplayer.cpp:
bool GetOffset(off64_t &offset);
bool IsPlaying(void) const;
bool IsEnabled(void) const;
void *GetHandle(void);
void *GetDmHandle(void);
int GetCurrPlaybackSpeed(void) const;
void PlaybackNotify(int Event, void *pData, void *pTag);
void DMNotify(int Event, void *pTsBuf, void *Tag);
#endif
};
#endif // __PLAYBACK_LIBEPLAYER3_H__

View File

@@ -1,102 +0,0 @@
#include <stdio.h>
#include "pwrmngr.h"
#include "lt_debug.h"
#include <fcntl.h>
#include <unistd.h>
#include <sys/ioctl.h>
#include <sys/stat.h>
#include <sys/types.h>
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_PWRMNGR, this, args)
void cCpuFreqManager::Up(void) { lt_debug("%s\n", __FUNCTION__); }
void cCpuFreqManager::Down(void) { lt_debug("%s\n", __FUNCTION__); }
void cCpuFreqManager::Reset(void) { lt_debug("%s\n", __FUNCTION__); }
/* those function dummies return true or "harmless" values */
bool cCpuFreqManager::SetDelta(unsigned long) { lt_debug("%s\n", __FUNCTION__); return true; }
#if HAVE_SPARK_HARDWARE || HAVE_DUCKBOX_HARDWARE
unsigned long cCpuFreqManager::GetCpuFreq(void) {
int freq = 0;
if (FILE *pll0 = fopen("/proc/cpu_frequ/pll0_ndiv_mdiv", "r")) {
char buffer[120];
while(fgets(buffer, sizeof(buffer), pll0)) {
if (1 == sscanf(buffer, "SH4 = %d MHZ", &freq))
break;
}
fclose(pll0);
return 1000 * 1000 * (unsigned long) freq;
}
return 0;
}
#else
unsigned long cCpuFreqManager::GetCpuFreq(void) { lt_debug("%s\n", __FUNCTION__); return 0; }
#endif
unsigned long cCpuFreqManager::GetDelta(void) { lt_debug("%s\n", __FUNCTION__); return 0; }
//
cCpuFreqManager::cCpuFreqManager(void) { lt_debug("%s\n", __FUNCTION__); }
bool cPowerManager::SetState(PWR_STATE) { lt_debug("%s\n", __FUNCTION__); return true; }
bool cPowerManager::Open(void) { lt_debug("%s\n", __FUNCTION__); return true; }
void cPowerManager::Close(void) { lt_debug("%s\n", __FUNCTION__); }
//
bool cPowerManager::SetStandby(bool Active, bool Passive)
{
lt_debug("%s(%d, %d)\n", __FUNCTION__, Active, Passive);
return true;
}
bool cCpuFreqManager::SetCpuFreq(unsigned long f)
{
#if HAVE_SPARK_HARDWARE || HAVE_DUCKBOX_HARDWARE
if (f) {
FILE *pll0 = fopen ("/proc/cpu_frequ/pll0_ndiv_mdiv", "w");
if (pll0) {
f /= 1000000;
fprintf(pll0, "%lu\n", (f/10 << 8) | 3);
fclose (pll0);
return false;
}
}
#else
/* actually SetCpuFreq is used to determine if the system is in standby
this is an "elegant" hack, because:
* during a recording, cpu freq is kept "high", even if the box is sent to standby
* the "SetStandby" call is made even if a recording is running
On the TD, setting standby disables the frontend, so we must not do it
if a recording is running.
For now, the values in neutrino are hardcoded:
* f == 0 => max => not standby
* f == 50000000 => min => standby
*/
lt_debug("%s(%lu) => set standby = %s\n", __FUNCTION__, f, f?"true":"false");
#if 0
int fd = open("/dev/stb/tdsystem", O_RDONLY);
if (fd < 0)
{
perror("open tdsystem");
return false;
}
if (f)
{
ioctl(fd, IOC_AVS_SET_VOLUME, 31); /* mute AVS to avoid ugly noise */
ioctl(fd, IOC_AVS_STANDBY_ENTER);
}
else
{
ioctl(fd, IOC_AVS_SET_VOLUME, 31); /* mute AVS to avoid ugly noise */
ioctl(fd, IOC_AVS_STANDBY_LEAVE);
/* unmute will be done by cAudio::do_mute(). Ugly, but prevents pops */
// ioctl(fd, IOC_AVS_SET_VOLUME, 0); /* max gain */
}
close(fd);
#endif
#endif
return true;
}
//
cPowerManager::cPowerManager(void) { lt_debug("%s\n", __FUNCTION__); }
cPowerManager::~cPowerManager() { lt_debug("%s\n", __FUNCTION__); }

View File

@@ -1,53 +0,0 @@
#ifndef __PWRMNGR_H__
#define __PWRMNGR_H__
// -- cCpuFreqManager ----------------------------------------------------------
class cCpuFreqManager {
private:
unsigned long startCpuFreq;
unsigned long delta;
public:
void Up(void);
void Down(void);
void Reset(void);
//
bool SetCpuFreq(unsigned long CpuFreq);
bool SetDelta(unsigned long Delta);
unsigned long GetCpuFreq(void);
unsigned long GetDelta(void);
//
cCpuFreqManager(void);
};
// -- cPowerManageger ----------------------------------------------------------
typedef enum
{
PWR_INIT = 1,
PWR_FULL_ACTIVE, /* all devices/clocks up */
PWR_ACTIVE_STANDBY,
PWR_PASSIVE_STANDBY,
PWR_INVALID
} PWR_STATE;
class cPowerManager {
private:
bool init;
bool opened;
PWR_STATE powerState;
//
static void ApplicationCallback(void *, void *, signed long, void *, void *) {}
bool SetState(PWR_STATE PowerState);
public:
bool Open(void);
void Close(void);
//
bool SetStandby(bool Active, bool Passive);
//
cPowerManager(void);
virtual ~cPowerManager();
};
#endif // __PWRMNGR_H__

View File

@@ -1,3 +1,19 @@
/*
* (C)
*
* 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.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <errno.h>
#include <fcntl.h>
#include <malloc.h>
@@ -8,14 +24,15 @@
#include <cstdio>
#include <cstring>
#include <pthread.h>
#include <aio.h>
#include "record_lib.h"
#include "lt_debug.h"
#define lt_debug(args...) _lt_debug(TRIPLE_DEBUG_RECORD, this, args)
#define lt_info(args...) _lt_info(TRIPLE_DEBUG_RECORD, this, args)
#include "hal_debug.h"
#define hal_debug(args...) _hal_debug(HAL_DEBUG_RECORD, this, args)
#define hal_info(args...) _hal_info(HAL_DEBUG_RECORD, this, args)
/* helper functions to call the cpp thread loops */
/* helper function to call the cpp thread loop */
void *execute_record_thread(void *c)
{
cRecord *obj = (cRecord *)c;
@@ -32,7 +49,7 @@ void *execute_writer_thread(void *c)
cRecord::cRecord(int num, int bs_dmx, int bs)
{
lt_info("%s %d\n", __func__, num);
hal_info("%s %d\n", __func__, num);
dmx = NULL;
record_thread_running = false;
file_fd = -1;
@@ -46,14 +63,14 @@ cRecord::cRecord(int num, int bs_dmx, int bs)
cRecord::~cRecord()
{
lt_info("%s: calling ::Stop()\n", __func__);
hal_info("%s: calling ::Stop()\n", __func__);
Stop();
lt_info("%s: end\n", __func__);
hal_info("%s: end\n", __func__);
}
bool cRecord::Open(void)
{
lt_info("%s\n", __func__);
hal_info("%s\n", __func__);
exit_flag = RECORD_STOPPED;
return true;
}
@@ -62,13 +79,13 @@ bool cRecord::Open(void)
// unused
void cRecord::Close(void)
{
lt_info("%s: \n", __func__);
hal_info("%s: \n", __func__);
}
#endif
bool cRecord::Start(int fd, unsigned short vpid, unsigned short *apids, int numpids, uint64_t)
{
lt_info("%s: fd %d, vpid 0x%03x\n", __func__, fd, vpid);
hal_info("%s: fd %d, vpid 0x%03x\n", __func__, fd, vpid);
int i;
if (!dmx)
@@ -90,7 +107,7 @@ bool cRecord::Start(int fd, unsigned short vpid, unsigned short *apids, int nump
{
exit_flag = RECORD_FAILED_READ;
errno = i;
lt_info("%s: error creating thread! (%m)\n", __func__);
hal_info("%s: error creating thread! (%m)\n", __func__);
delete dmx;
dmx = NULL;
return false;
@@ -101,10 +118,10 @@ bool cRecord::Start(int fd, unsigned short vpid, unsigned short *apids, int nump
bool cRecord::Stop(void)
{
lt_info("%s\n", __func__);
hal_info("%s\n", __func__);
if (exit_flag != RECORD_RUNNING)
lt_info("%s: status not RUNNING? (%d)\n", __func__, exit_flag);
hal_info("%s: status not RUNNING? (%d)\n", __func__, exit_flag);
exit_flag = RECORD_STOPPED;
if (record_thread_running)
@@ -113,7 +130,7 @@ bool cRecord::Stop(void)
/* We should probably do that from the destructor... */
if (!dmx)
lt_info("%s: dmx == NULL?\n", __func__);
hal_info("%s: dmx == NULL?\n", __func__);
else
delete dmx;
dmx = NULL;
@@ -121,7 +138,7 @@ bool cRecord::Stop(void)
if (file_fd != -1)
close(file_fd);
else
lt_info("%s: file_fd not open??\n", __func__);
hal_info("%s: file_fd not open??\n", __func__);
file_fd = -1;
return true;
}
@@ -132,12 +149,12 @@ bool cRecord::ChangePids(unsigned short /*vpid*/, unsigned short *apids, int num
int j;
bool found;
unsigned short pid;
lt_info("%s\n", __func__);
hal_info("%s\n", __func__);
if (!dmx) {
lt_info("%s: DMX = NULL\n", __func__);
hal_info("%s: DMX = NULL\n", __func__);
return false;
}
pids = dmx->getPesPids();
pids = dmx->pesfds;
/* the first PID is the video pid, so start with the second PID... */
for (std::vector<pes_pids>::const_iterator i = pids.begin() + 1; i != pids.end(); ++i) {
found = false;
@@ -168,12 +185,12 @@ bool cRecord::ChangePids(unsigned short /*vpid*/, unsigned short *apids, int num
bool cRecord::AddPid(unsigned short pid)
{
std::vector<pes_pids> pids;
lt_info("%s: \n", __func__);
hal_info("%s: \n", __func__);
if (!dmx) {
lt_info("%s: DMX = NULL\n", __func__);
hal_info("%s: DMX = NULL\n", __func__);
return false;
}
pids = dmx->getPesPids();
pids = dmx->pesfds;
for (std::vector<pes_pids>::const_iterator i = pids.begin(); i != pids.end(); ++i) {
if ((*i).pid == pid)
return true; /* or is it an error to try to add the same PID twice? */
@@ -209,12 +226,12 @@ void cRecord::WriterThread()
void cRecord::RecordThread()
{
lt_info("%s: begin\n", __func__);
hal_info("%s: begin\n", __func__);
char threadname[17];
strncpy(threadname, "RecordThread", sizeof(threadname));
threadname[16] = 0;
prctl (PR_SET_NAME, (unsigned long)&threadname);
int readsize = bufsize/16;
int readsize = bufsize / 16;
int buf_pos = 0;
int count = 0;
int queued = 0;
@@ -222,20 +239,20 @@ void cRecord::RecordThread()
struct aiocb a;
buf = (uint8_t *)malloc(bufsize);
lt_info("BUFSIZE=0x%x READSIZE=0x%x\n", bufsize, readsize);
hal_info("BUFSIZE=0x%x READSIZE=0x%x\n", bufsize, readsize);
if (!buf)
{
exit_flag = RECORD_FAILED_MEMORY;
lt_info("%s: unable to allocate buffer! (out of memory)\n", __func__);
hal_info("%s: unable to allocate buffer! (out of memory)\n", __func__);
if (failureCallback)
failureCallback(failureData);
lt_info("%s: end\n", __func__);
hal_info("%s: end\n", __func__);
pthread_exit(NULL);
}
int val = fcntl(file_fd, F_GETFL);
if (fcntl(file_fd, F_SETFL, val|O_APPEND))
lt_info("%s: O_APPEND? (%m)\n", __func__);
hal_info("%s: O_APPEND? (%m)\n", __func__);
memset(&a, 0, sizeof(a));
a.aio_fildes = file_fd;
@@ -250,20 +267,22 @@ void cRecord::RecordThread()
if (buf_pos < bufsize)
{
if (overflow_count) {
lt_info("%s: Overflow cleared after %d iterations\n", __func__, overflow_count);
hal_info("%s: Overflow cleared after %d iterations\n", __func__, overflow_count);
overflow_count = 0;
}
int toread = bufsize - buf_pos;
if (toread > readsize)
toread = readsize;
ssize_t s = dmx->Read(buf + buf_pos, toread, 50);
lt_debug("%s: buf_pos %6d s %6d / %6d\n", __func__, buf_pos, (int)s, bufsize - buf_pos);
hal_debug("%s: buf_pos %6d s %6d / %6d\n", __func__,
buf_pos, (int)s, bufsize - buf_pos);
if (s < 0)
{
if (errno != EAGAIN && (errno != EOVERFLOW || !overflow))
{
lt_info("%s: read failed: %m\n", __func__);
hal_info("%s: read failed: %m\n", __func__);
exit_flag = RECORD_FAILED_READ;
state = REC_STATUS_OVERFLOW;
break;
}
}
@@ -288,12 +307,13 @@ void cRecord::RecordThread()
overflow_count = 0;
overflow = true;
if (!(overflow_count % 10))
lt_info("%s: buffer full! Overflow? (%d)\n", __func__, ++overflow_count);
hal_info("%s: buffer full! Overflow? (%d)\n", __func__, ++overflow_count);
state = REC_STATUS_SLOW;
}
r = aio_error(&a);
if (r == EINPROGRESS)
{
lt_debug("%s: aio in progress, free: %d\n", __func__, bufsize - buf_pos);
hal_debug("%s: aio in progress, free: %d\n", __func__, bufsize - buf_pos);
continue;
}
// not calling aio_return causes a memory leak --martii
@@ -301,11 +321,11 @@ void cRecord::RecordThread()
if (r < 0)
{
exit_flag = RECORD_FAILED_FILE;
lt_debug("%s: aio_return = %d (%m)\n", __func__, r);
hal_debug("%s: aio_return = %d (%m)\n", __func__, r);
break;
}
else
lt_debug("%s: aio_return = %d, free: %d\n", __func__, r, bufsize - buf_pos);
hal_debug("%s: aio_return = %d, free: %d\n", __func__, r, bufsize - buf_pos);
if (posix_fadvise(file_fd, 0, 0, POSIX_FADV_DONTNEED))
perror("posix_fadvise");
if (queued)
@@ -319,7 +339,7 @@ void cRecord::RecordThread()
r = aio_write(&a);
if (r)
{
lt_info("%s: aio_write %d (%m)\n", __func__, r);
hal_info("%s: aio_write %d (%m)\n", __func__, r);
exit_flag = RECORD_FAILED_FILE;
break;
}
@@ -327,7 +347,7 @@ void cRecord::RecordThread()
dmx->Stop();
while (true) /* write out the unwritten buffer content */
{
lt_debug("%s: run-out write, buf_pos %d\n", __func__, buf_pos);
hal_debug("%s: run-out write, buf_pos %d\n", __func__, buf_pos);
r = aio_error(&a);
if (r == EINPROGRESS)
{
@@ -338,7 +358,7 @@ void cRecord::RecordThread()
if (r < 0)
{
exit_flag = RECORD_FAILED_FILE;
lt_info("%s: aio_result: %d (%m)\n", __func__, r);
hal_info("%s: aio_result: %d (%m)\n", __func__, r);
break;
}
if (!queued)
@@ -368,7 +388,7 @@ void cRecord::RecordThread()
if ((exit_flag != RECORD_STOPPED) && failureCallback)
failureCallback(failureData);
lt_info("%s: end\n", __func__);
hal_info("%s: end\n", __func__);
pthread_exit(NULL);
}

View File

@@ -1,9 +1,8 @@
#ifndef __RECORD_TD_H
#define __RECORD_TD_H
#ifndef __RECORD_LIB_H__
#define __RECORD_LIB_H__
#include <pthread.h>
#include <semaphore.h>
#include "dmx_lib.h"
#include "dmx_hal.h"
#define REC_STATUS_OK 0
#define REC_STATUS_SLOW 1
@@ -54,4 +53,5 @@ class cRecord
void RecordThread();
void WriterThread();
};
#endif
#endif // __RECORD_LIB_H__

File diff suppressed because it is too large Load Diff

View File

@@ -1,9 +1,9 @@
#ifndef _VIDEO_TD_H
#define _VIDEO_TD_H
#ifndef __VIDEO_LIB_H__
#define __VIDEO_LIB_H__
#include <linux/dvb/video.h>
#include "../common/cs_types.h"
#include "dmx_lib.h"
#include "cs_types.h"
#include "dmx_hal.h"
typedef struct cs_vs_format_t
{
@@ -27,9 +27,11 @@ typedef enum {
COLORFORMAT_YUV,
COLORFORMAT_CVBS,
COLORFORMAT_SVIDEO,
COLORFORMAT_HDMI_AUTO,
COLORFORMAT_HDMI_RGB,
COLORFORMAT_HDMI_YCBCR444,
COLORFORMAT_HDMI_YCBCR422
COLORFORMAT_HDMI_YCBCR422,
COLORFORMAT_HDMI_YCBCR420
} COLOR_FORMAT;
typedef enum {
@@ -73,8 +75,12 @@ typedef enum {
} DISPLAY_AR;
typedef enum {
DISPLAY_AR_MODE_PANSCAN = 0,
DISPLAY_AR_MODE_LETTERBOX,
/* FIX for HD51 mix-up of letterbox / panscan
Standard is 1. PANSCAN 2. LETTERBOX
If next drivers are correct please revert
this and pzapit.cpp */
DISPLAY_AR_MODE_LETTERBOX = 0,
DISPLAY_AR_MODE_PANSCAN,
DISPLAY_AR_MODE_NONE,
DISPLAY_AR_MODE_PANSCAN2
} DISPLAY_AR_MODE;
@@ -119,7 +125,7 @@ typedef enum {
} VIDEO_STD;
typedef enum {
VIDEO_HDMI_CEC_MODE_OFF = 0,
VIDEO_HDMI_CEC_MODE_OFF = 0,
VIDEO_HDMI_CEC_MODE_TUNER = 3,
VIDEO_HDMI_CEC_MODE_RECORDER = 1
} VIDEO_HDMI_CEC_MODE;
@@ -131,27 +137,25 @@ typedef enum
VIDEO_CONTROL_SATURATION,
VIDEO_CONTROL_HUE,
VIDEO_CONTROL_SHARPNESS,
VIDEO_CONTROL_BLOCK_NOISE_REDUCTION,
VIDEO_CONTROL_MOSQUITO_NOISE_REDUCTION,
VIDEO_CONTROL_DIGITAL_CONTOUR_REMOVAL,
VIDEO_CONTROL_AUTO_FLESH,
VIDEO_CONTROL_GREEN_BOOST,
VIDEO_CONTROL_BLUE_BOOST,
VIDEO_CONTROL_DYNAMIC_CONTRAST,
VIDEO_CONTROL_SCALER_SHARPNESS,
VIDEO_CONTROL_ZAPPING_MODE,
VIDEO_CONTROL_MAX = VIDEO_CONTROL_SHARPNESS
} VIDEO_CONTROL;
struct cec_message
{
unsigned char address;
unsigned char length;
unsigned char data[256];
}__attribute__((packed));
#define cec_rx_message cec_message
struct addressinfo
{
unsigned char logical;
unsigned char physical[2];
unsigned char type;
};
class cDemux;
class cPlayback;
class cVideo
{
friend class cDemux;
friend class cPlayback;
friend class cDemux;
private:
/* video device */
int fd;
@@ -175,15 +179,20 @@ class cVideo
int contrast;
int saturation;
int hue;
int sharpness;
int block_noise_reduction;
int mosquito_noise_reduction;
int digital_contour_removal;
int auto_flesh;
int green_boost;
int blue_boost;
int dynamic_contrast;
int scaler_sharpness;
int zapping_mode;
/* used internally by dmx */
int64_t GetPTS(void);
unsigned char physicalAddress[2];
bool standby_cec_activ,autoview_cec_activ;
unsigned char deviceType, logicalAddress;
int hdmiFd;
public:
/* constructor & destructor */
cVideo(int mode, void *, void *, unsigned int unit = 0);
@@ -228,11 +237,7 @@ class cVideo
bool SetCECMode(VIDEO_HDMI_CEC_MODE);
void SetCECAutoView(bool);
void SetCECAutoStandby(bool);
void GetCECAddressInfo();
void SendCECMessage(struct cec_message &message);
void SetCECState(bool state);
void ReportPhysicalAddress();
void ShowPicture(const char * fname, const char *_destname = NULL);
bool ShowPicture(const char * fname);
void StopPicture();
void Standby(unsigned int bOn);
void Pig(int x, int y, int w, int h, int osd_w = 1064, int osd_h = 600, int startx = 0, int starty = 0, int endx = 1279, int endy = 719);
@@ -251,4 +256,4 @@ class cVideo
bool GetScreenImage(unsigned char * &data, int &xres, int &yres, bool get_video = true, bool get_osd = false, bool scale_to_video = false);
};
#endif
#endif // __VIDEO_LIB_H__

View File

@@ -1,10 +1,9 @@
noinst_LTLIBRARIES = libduckbox.la
AM_CPPFLAGS = -D__STDC_FORMAT_MACROS -D__STDC_CONSTANT_MACROS
AM_CPPFLAGS += \
AM_CPPFLAGS = \
-I$(top_srcdir)/common \
-I$(top_srcdir)/include \
-I$(top_srcdir)/libeplayer3/include
-I$(top_srcdir)/libeplayer3-sh4/include
AM_CXXFLAGS = -fno-rtti -fno-exceptions -fno-strict-aliasing
@@ -23,5 +22,6 @@ libduckbox_la_SOURCES = \
audio_mixer.cpp \
init.cpp \
playback_libeplayer3.cpp \
pwrmngr.cpp \
record.cpp
AM_CPPFLAGS += -D__STDC_FORMAT_MACROS -D__STDC_CONSTANT_MACROS -D__STDC_LIMIT_MACROS

View File

@@ -1,31 +0,0 @@
/* compatibility header for tripledragon. I'm lazy, so I just left it
as "cs_api.h" so that I don't need too many ifdefs in the code */
#ifndef __CS_API_H_
#define __CS_API_H_
#include "init_lib.h"
typedef void (*cs_messenger) (unsigned int msg, unsigned int data);
inline void cs_api_init()
{
init_td_api();
};
inline void cs_api_exit()
{
shutdown_td_api();
};
#define cs_malloc_uncached malloc
#define cs_free_uncached free
// Callback function helpers
void cs_register_messenger(cs_messenger messenger);
static inline void cs_deregister_messenger(void) { return; };
/* compat... HD1 seems to be version 6. everything newer ist > 6... */
static inline unsigned int cs_get_revision(void) { return 1; };
static inline unsigned int cs_get_chip_type(void) { return 0; };
extern int cnxt_debug;
#endif //__CS_API_H_

View File

@@ -1 +0,0 @@
../libspark/dmx_cs.h

View File

@@ -1 +0,0 @@
../libspark/dmx_lib.h

View File

@@ -31,6 +31,8 @@ hw_caps_t *get_hwcaps(void)
int fd = open("/proc/stb/info/model", O_RDONLY);
caps.display_can_set_brightness = 0;
caps.display_can_deepstandby = 0;
caps.display_has_statusline = 0;
caps.can_cpufreq = 1;
if (fd != -1) {
len = read(fd, buf, sizeof(buf) - 1);
close(fd);
@@ -46,6 +48,9 @@ hw_caps_t *get_hwcaps(void)
caps.can_cec = 1;
caps.has_fan = 0;
caps.has_CI = 2;
caps.display_can_set_brightness = 1;
caps.display_type = HW_DISPLAY_LINE_TEXT;
caps.display_xres = 12;
}
else if (!strncmp(buf, "ufs912", 6)) {
strcpy(caps.boxvendor, "DUCKBOX");
@@ -57,6 +62,8 @@ hw_caps_t *get_hwcaps(void)
caps.has_fan = 0;
caps.has_CI = 2;
caps.display_can_set_brightness = 1;
caps.display_type = HW_DISPLAY_LINE_TEXT;
caps.display_xres = 16;
}
else if (!strncmp(buf, "ufs913", 6)) {
strcpy(caps.boxvendor, "DUCKBOX");
@@ -68,6 +75,8 @@ hw_caps_t *get_hwcaps(void)
caps.has_fan = 0;
caps.has_CI = 2;
caps.display_can_set_brightness = 1;
caps.display_type = HW_DISPLAY_LINE_TEXT;
caps.display_xres = 16;
}
else if (!strncmp(buf, "ufs922", 6)) {
strcpy(caps.boxvendor, "DUCKBOX");
@@ -78,6 +87,9 @@ hw_caps_t *get_hwcaps(void)
caps.can_cec = 0;
caps.has_fan = 1;
caps.has_CI = 2;
caps.display_can_set_brightness = 1;
caps.display_type = HW_DISPLAY_LINE_TEXT;
caps.display_xres = 16;
}
else if (!strncmp(buf, "ufs910", 6)) {
strcpy(caps.boxvendor, "DUCKBOX");
@@ -89,6 +101,8 @@ hw_caps_t *get_hwcaps(void)
caps.has_fan = 0;
caps.has_CI = 2;
caps.display_can_set_brightness = 1;
caps.display_type = HW_DISPLAY_LINE_TEXT;
caps.display_xres = 16;
}
else if (!strncmp(buf, "hdbox", 5)) {
strcpy(caps.boxvendor, "DUCKBOX");
@@ -99,6 +113,9 @@ hw_caps_t *get_hwcaps(void)
caps.can_cec = 0;
caps.has_fan = 0;
caps.has_CI = 2;
caps.display_can_set_brightness = 1;
caps.display_type = HW_DISPLAY_LINE_TEXT;
caps.display_xres = 12;
}
else if (!strncmp(buf, "octagon1008", 11)) {
strcpy(caps.boxvendor, "DUCKBOX");
@@ -109,6 +126,9 @@ hw_caps_t *get_hwcaps(void)
caps.can_cec = 0;
caps.has_fan = 0;
caps.has_CI = 2;
caps.display_can_set_brightness = 1;
caps.display_type = HW_DISPLAY_LINE_TEXT;
caps.display_xres = 8;
}
else if (!strncmp(buf, "hs7110", 6)) {
strcpy(caps.boxvendor, "DUCKBOX");
@@ -174,6 +194,9 @@ hw_caps_t *get_hwcaps(void)
caps.can_cec = 0;
caps.has_fan = 1;
caps.has_CI = 2;
caps.display_can_set_brightness = 1;
caps.display_type = HW_DISPLAY_LINE_TEXT;
caps.display_xres = 14;
}
else if (!strncmp(buf, "cuberevo-250hd", 4)) {
strcpy(caps.boxvendor, "DUCKBOX");
@@ -260,10 +283,14 @@ hw_caps_t *get_hwcaps(void)
strcpy(caps.boxname, buf);
caps.can_shutdown = 1;
caps.has_HDMI = 1;
caps.has_SCART = 2;
caps.can_cec = 0;
caps.has_SCART = 1;
caps.has_SCART_input = 1;
caps.can_cec = 1;
caps.has_fan = 0;
caps.has_CI = 2;
caps.display_can_set_brightness = 1;
caps.display_type = HW_DISPLAY_LINE_TEXT;
caps.display_xres = 8;
}
else if (!strncmp(buf, "arivalink200", 12)) {
strcpy(caps.boxvendor, "DUCKBOX");

Some files were not shown because too many files have changed in this diff Show More