Saturday, March 11, 2017

Cable2LAN: Real-time Media Streaming with ffmpeg



Ever Want to consume Cable TV anywhere in the house?  I did, and can...now

Living Under Uncomfortable Circumstances

Recently, I have started to watch Cable TV in an attempt to keep myself better informed about what is going on in the world.  I like it...but I like being in front of my computer even more. Sadly, I can't really watch TV and work on my PC at the same time because my Cable TV decoder is attached to the television in my living room.  

My PC is located in my home office, some distance away.  To compound the issue, my local cable provider does not allow for multiple decoders on a single cable link.  So, as a kind of compromise, what I've done is start to listen to the TV as I work on my PC, kinda like treating the TV as if it were a radio.  This solution is far from perfect. To hear the TV in my home office, I have to crank up the volume to the point where everyone in the house is also forced to listen, whether they want to or not.  This makes early morning or late night listening impossible, and that's pretty much when I want Cable TV.


The Perfect Solution

The perfect solution would be one where I connect my Cable TV decoder to silver, a $27.00 media player whose story I have already documented in a previous blog entry, and silver would process and forward CableTV to my office PC over my home LAN.  silver is physically located in the same console as my Cable TV decoder and it is my home theatre multimedia player, which makes it a good choice for this project.   

Decisions, decisions

In this project, I had to make the following system architecture decisions:

1) Which Client PC Media Player to use?
2) Which Server Operating System to use?
3) Which Server Multimedia Capture Hardware to use?
4) Which Server Transcoding Software to use?
5) Which Server Streaming Strategy to use?
6) Which LAN Transport Protocol to use?


 

Obstacles

As I worked on this project, I also had to overcome following provisioning and configuration obstacles:

A) Ignorance of how to "do sound" on Linux (this is my first time)
B) Diagnosing and overcoming missing firmware files (WinTV)
C) Diagnosing and overcoming obsolete firmware files (WinTV)   

D) Overcoming missing system level libraries, modules and so on (Ubuntu)
E) Overcoming missing applications (ffmpeg)
F) Overcoming obsolete applications (
ffmpeg)
G) Overcoming missing application-specific supporting libraries (ALSA for
ffmpeg)
H)  Overcoming how to compile custom software (
ffmpeg)
I) Overcoming incomplete documentation (
ffmpeg)
J) Overcoming obsolete advice (Internet)
K) Overcoming aged and/or obsolete hardware (silver)
 

1) Which Client PC Media Player?


Videolan (VLC)
My choice for Client Media Player was Videolan (VLC), which is available from http://www.videolan.org.

Why I Chose VLC
I chose VLC as the client side Media Player for a few reasons.  First, I am already very familiar with this application.  I have been using it for many years.  Second, it was the recommended player for this kind of project in posting after posting.  Third, I already have it installed on my PC.  Fourth, it is very robust application that can handle a lot of different media types with great elegance.  

Installing VLC
Installing VLC is very smooth and easy to install, especially if you are using Windows on your client, which is my situation

OK, it looks like VLC is properly installed and configured.
 

2) Which Server Operating System?


Ubuntu 14.04.5 LTS 
My choice for Server Operating System was Ubuntu, specifically Ubuntu 14.04.5 LTS, which is available from http://www.ubuntu.com.

Why I Chose Linux

At the time I rescued silver from the scrap heap, the latest stable release of was Ubuntu was 14.04.5 LTS, so that's what silver is running 99% of the time.  When silver does run Windows, it's running Windows XP, which is an unsupported Operating System at the time of this writing.  .  Not only is Windows XP no longer supported by Microsoft, I could find no free software in the Windows ecosystem that could help me accomplish the goals of this project.  By contrast, a multitude of potential software solutions exist within the Linux ecosystem.

(You may want to choose a more modern version of LTS Ubuntu for your implementation, like Ubuntu 16.04.1 LTS [Xenial Xerus] because it may be more WinTV "friendly".  But when I first built silver in 2015 version 14.04.5 was the latest Long Term Support (LTS) version of Ubuntu.  Xenial Xerus was released on July 21, 2016).

Installing Ubuntu 14.04.5 LTS

Installing Ubuntu 14.04.5 is a pretty straightforward process.  It is very well documented, with both text and video documentation readily available.

OK, it looks like Linux is properly installed and configured.

3) Which Multimedia Capture Hardware?


Hauppauge WinTV HVR-1110
Making the choice of hardware multimedia capture card was easy because I already had one hanging around.  I bought my CableTV card at least 10 years ago for $5.00.  It was sitting in a cardboard box on the floor outside a second hand computer store in the New Capital Computer Plaza in Hong Kong among all of the other bits and pieces that the store basically thought was worthless.  Curious, I picked it up because I wanted to tinker with it...but I never got around to it because my lifestyle and TV consumption habits were different then.  I almost never watched TV.  Now I do.

There are hundreds of different types of WinTV cards available cheap on eBayThe CableTV card I bought second-hand for $5.00 was a Hauppauge Company WinTV HVR-1110.  Retail purchases are also possible.  Even though the exact card I used seems to be no longer listed on the manufacturer site, a related card (the HVR-1100) still is.

But here's what's weird about that situation. The HVR-1100 is a rectangular shaped card...



...and the HVR-1110 is a triangular shaped card...


...so why is a picture of the HVR-1110 featured on the web page for the HVR-1100?



Confusion reigns! Aside from the obvious cosmetic differences, the components on these cards are also not the same.  They are quite different.  The differences between the WinTV HVR-1100 and the WinTV HVR-1110 is discussed here, and here's a screenshot:



Believe me, this situation is not super helpful to someone trying to get this card working. 

However, we need not worry...Linux to the rescue!  The WinTV HVR-1110 features a Philips SAA7131 A/V decoder & bridge, along with an NXP TDA10046 digital demodulator, which is a Digital Signal Processor (DSP) chip.  Thankfully, these chips are natively supported by the Linux operating system via the saa7130/34 driver.  Despite its identity crisis, the WinTV HVR-1110 works "out of the box" (almost) under Linux.  Hurrah for open source developers!

I should also mention that the WinTV HVR-1110 has also been given a new lease on life at Linux TV, a website devoted to watching TV under Linux.  For this project, Linux TV was a (nearly) perfect resource for finding information, configuration tips and leads to the software needed for this project.  

This is a good thing, because Hauppage no longer provides specific information about the WinTV HVR-1110 on its website, and the Windows XP version of the software used by the WinTV HVR-1110 provided by Hauppauge Company is now outdated by definition.  Lastly, the software only allows for watching TV on the host computer.  This is not what I want to do.  

On the other hand, Linux TV identifies and supports the HVR-1110 without confusion.  As part of this project, I also updated the Linux TV HVR-1110 entry to reflect a simple six step process for installing and provisioning the HVR-1110 under Linux Ubuntu 14.04.5.

Installing the WinTV HVR-1110

Installing the WinTV card in silver was like installing any other PCI card.  Uneventful.  Here's what the back rail of my WinTV HVR-1110 card looked like:



The connectors on the back rail of the HVR-1110 are:


  • FM in
  • TV in
  • S-Video in
  • VIDEO in
  • RCA LEFT in
  • RCA RIGHT in

After the card installation, silver restarted smoothly.  But the WinTV card didn't appear to be functioning.  MythTV, a DVR software that runs on the host PC, didn't work, even though I spent hours trying to get it to work.  No luck.  

After rooting around on the Internet, I learned how to investigate the startup process of the WinTV HVR-1110.   Armed with the knowledge that the card was natively supported by the Linux kernel saa7134 driver, I used grep to scan the output of dmesg for clues about what was going on.  Here's the command I issued, and what I saw:


The last two lines reveal what is going on.  They indicate that the WinTV HVR-1110 card had, partially or wholly, failed to initialize due to a missing firmware file.  The file in question is dvb-fe-tda10045.fw:

[   30.460094] saa7134 Firmware load for dvb-fe-tda10046.fw failed with error -2
[   30.460120] saa7134 Firmware load for dvb-fe-tda10045.fw failed with error -2
 


According to my understanding, here's how the WinTV HVR-1110 startup process goes: 

    1. During the system boot process, the Linux kernel loads the saa7134 driver

    2. The saa7134 driver tries to load a file called dvb-fe-tda10045.fw 

    3. The dvb-fe-tda10045.fw file is for the onboard TDA10046H DSP chip

    4. If it cannot find the firmware file, the saa7134 driver issues an error

    5. The activation of the WinTV HVR-1110 then partially or completely fails

Q: Could it be that the dvb-fe-tda10045.fw file was on my system, but in the wrong place?  

This used to happen in the old days of Linux when the filesystem layout varied between distributions.  So, I checked for the presence of the indicated firmware file by searching the entire filesystem of silver via the following command, and got the following result:

root@silver:/# find . -name "dvb-fe-tda10045.fw"
root@silver:/#


The lack of output indicates that there was no dvb-fe-tda10045.fw file anywhere in the filesystem of silver, so the next stage of the project was an online fishing expedition for a version of the dvb-fe-tda10045.fw file that was compatible with my WinTV card.  A closely correlated problem was to figure out where to put the dvb-fe-tda10045.fw file so that the saa7134 driver could find it, to be able to load it and apply it.

Turning to the Internet, I found this post:


Unfortunately, this turned out to be a false trail.  The RPM mentioned in that post contains an obsolete or incompatible version of the dvb-fe-tda10045.fw file.  It is the wrong version for my WinTV HVR-1110 card. Here's what happened when I used files from the above RPM, and what the resulting error looked like.  I am including this so anyone following this article can avoid wasting time with like I did:



As it turned out, the DSP was still not being programmedJust below that secction of the dmesg log, (which looked encouraging - no obvious errors) I found this:

[   25.996041] tda1004x: setting up plls for 48MHz sampling clock
[   28.012042] tda1004x: found firmware revision 0 -- invalid
[   28.012048] tda1004x: trying to boot from eeprom
[   30.344057] tda1004x: timeout waiting for DSP ready
[   30.384360] tda1004x: found firmware revision 0 -- invalid
[   30.384366] tda1004x: waiting for firmware upload...
 


So, the dvb-fe-tda10045.fw firmware file I had obtained was invalid or incompatible.  Bummer. Looking around on the Internet once again, I found the following post:



Following the instructions in the post, I got the following output:

root@silver:~# apt-get install linux-firmware-nonfree
Reading package lists... Done
Building dependency tree
Reading state information... Done
The following NEW packages will be installed:
  linux-firmware-nonfree
0 upgraded, 1 newly installed, 0 to remove and 26 not upgraded.
Need to get 2,436 kB of archives.
After this operation, 8,249 kB of additional disk space will be used.
Get:1 http://hk.archive.ubuntu.com/ubuntu/ trusty-updates/multiverse linux-firmware-nonfree all 1.14ubuntu3 [2,436 kB]
Fetched 2,436 kB in 3s (656 kB/s)
Selecting previously unselected package linux-firmware-nonfree.
(Reading database ... 219485 files and directories currently installed.)
Preparing to unpack .../linux-firmware-nonfree_1.14ubuntu3_all.deb ...
Unpacking linux-firmware-nonfree (1.14ubuntu3) ...
Setting up linux-firmware-nonfree (1.14ubuntu3) ...
root@silver:~#


The output of issuing the command wasn't exactly clear as to what actually happened with silver, so I manually double-checked whether or not the dvb-fe-tda10045.fw had been changed:

root@silver:~/WinTV# ls -l ./lib/firmware/dvb-fe-tda10045.fw
-rw-r--r-- 1 root root 30555 Nov 20  2006 ./lib/firmware/dvb-fe-tda10045.fw
root@silver:~/WinTV# ls -l /lib/firmware/dvb-fe-tda10045.fw
-rw-r--r-- 1 root root 30555 Mar 10 23:08 /lib/firmware/dvb-fe-tda10045.fw


The files were the same size, but now had different dates.  Interesting.   

I renamed the original file dvb-fe-tda10045.fw-obsolete and copied the new dvb-fe-tda10045.fw into the /lib/firmware directory.  I then rebooted silver to see what would happen.  When it came back online, I found messages in dmesg that confirmed that the DSP on my WinTV HVR-1110 card had been properly programmed with a compatible dvb-fe-tda10045.fw firmware file:

First, the saa7134 device driver appeared to be successfully loaded and registered:

root@silver:~# dmesg | grep "saa"
[   25.932079] saa7134 0000:03:02.0: DVB: registering adapter 0 frontend 0 (Philips TDA10046H DVB-T)...

Second, the device adapter0 device appeared in the sdb subdirectory of the /dev directory:

root@silver:~# ls /dev/dvb/
adapter0
 


Third, the NXP TDA10046 digital demodulator appeared to have been successfully programmed:

root@silver:~# dmesg | grep "tda1004x"
[   26.020071] tda1004x: setting up plls for 48MHz sampling clock
[   26.332041] tda1004x: found firmware revision 20 -- ok 


UPDATE (2017-03-24):  Firmware of version 29 can be found at the following website:
https://sites.google.com/site/klaasdc/linux-dvb-firmware

So far so good.  

Finally, I performed some checks to see if silver now recognized the WinTV HVR-1110 card, and also gain as much information about the WinTV HVR-1110 setup as possible.  

First, I looked at the the proc filesystem on silver, which showed the WinTV HVR-1110 card being listed as SAA7134 device 01-00 (this means the WinTV HR-1110 ALSA address was hw:1,0):

root@silver:~# cat /proc/asound/pcm
00-00: ALC662 rev1 Analog : ALC662 rev1 Analog : playback 1 : capture 1
00-01: ALC662 rev1 Digital : ALC662 rev1 Digital : playback 1
00-02: ALC662 rev1 Alt Analog : ALC662 rev1 Alt Analog : capture 1
01-00: SAA7134 PCM : SAA7134 PCM : capture 1

 
Next, I ran the arecord -l program on silver, which reconfirmed the availability of the SAA7134 device as card 1, device 0 (confirming the ALSA hw:1,0 address once again):

root@silver:~# arecord -l
**** List of CAPTURE Hardware Devices ****
card 0: Intel [HDA Intel], device 0: ALC662 rev1 Analog [ALC662 rev1 Analog]
  Subdevices: 0/1
  Subdevice #0: subdevice #0
card 0: Intel [HDA Intel], device 2: ALC662 rev1 Alt Analog [ALC662 rev1 Alt Analog]
  Subdevices: 1/1
  Subdevice #0: subdevice #0
card 1: SAA7134 [SAA7134], device 0: SAA7134 PCM [SAA7134 PCM]
  Subdevices: 1/1
  Subdevice #0: subdevice #0


OK, it looks like the WinTV HVR-1110 is properly configured and installed.

Which Server Transcoding Software?


ffmpeg
In terms of transcoding software, my choice was ffmpeg.  This software is available at: https://ffmpeg.org.

Why I chose ffmpeg
Choosing ffmpeg was pretty easy.  There are innumerable postings online discussing how to use ffmpeg to convert multimedia.  The only problems with ffmpeg is that it is very complex; it's documentation is not terribly complete; and that it has a fairly arcane command line invocation.  That said, there's nothing else I've come across with an equivalent universe of functionality. It is truly the "swiss army knife" of multimedia.  And it's free.

Installing ffmpeg
Unfortunately, ffmpeg is not easily available in Ubuntu 14.04.5 LTS as evidenced by the following command and response:

root@silver:~# apt-get install ffmpeg
Reading package lists... Done
Building dependency tree
Reading state information... Done
Package ffmpeg is not available, but is referred to by another package.
This may mean that the package is missing, has been obsoleted, or
is only available from another source

E: Package 'ffmpeg' has no installation candidate

But there was hope, according to this web page:




Once the installation was complete, a list of valid ffmpeg input devices could be displayed via the ffmpeg -devices command:

root@silver:~# ffmpeg -devices
ffmpeg version 3.2.4 Copyright (c) 2000-2017 the FFmpeg developers
  built with gcc 4.8 (Ubuntu 4.8.4-2ubuntu1~14.04.3)
  configuration:
  libavutil      55. 34.101 / 55. 34.101
  libavcodec     57. 64.101 / 57. 64.101
  libavformat    57. 56.101 / 57. 56.101
  libavdevice    57.  1.100 / 57.  1.100
  libavfilter     6. 65.100 /  6. 65.100
  libswscale      4.  2.100 /  4.  2.100
  libswresample   2.  3.100 /  2.  3.100
Devices:
 D. = Demuxing supported
 .E = Muxing supported
 --
 D  dv1394          DV1394 A/V grab
 DE fbdev           Linux framebuffer
 D  lavfi           Libavfilter virtual input device
 DE oss             OSS (Open Sound System) playback
  E v4l2            Video4Linux2 output device
 D  video4linux2,v4l2 Video4Linux2 device grab


Wait a second.  The ALSA driver isn't listed!  

Was this another waste of time?  Maybe!  The strange thing was, the ffmpeg version was right (3.2.4), the latest version.  But the alsa device wasn't listed.  Hmmm.  Well, one way to make sure that ALSA input device support is included in ffmpeg is to compile it from source with the right flags, which is what I ended up doing.  I recompiled and installed my own custom version of ffmpeg from source.

Compiling ffmpeg from Source

There's a wonderful tutorial on the ffmpeg bug tracking website that covers how to compile and install ffmpeg.  I recommend it in the case(s) where your ffmpeg version is unavailable, obsolete or missing missing critical functionality.  Unfortunately, I qualified for all three of these situations at various times while working on this project. 

Thankfully, the tutorial was invaluable, easy to follow and boiled down to this:

1) Download ffmpeg from the ffmpeg download area

root@silver:~# wget http://ffmpeg.org/releases/ffmpeg-3.2.4.tar.bz2
--2017-03-12 14:17:14--  http://ffmpeg.org/releases/ffmpeg-3.2.4.tar.bz2
Resolving ffmpeg.org (ffmpeg.org)... 79.124.17.100
Connecting to ffmpeg.org (ffmpeg.org)|79.124.17.100|:80... connected.
HTTP request sent, awaiting response... 200 OK
Length: 9612274 (9.2M) [application/x-bzip2]
Saving to: ‘ffmpeg-3.2.4.tar.bz2’

100%[======================================================================>]
9,612,274    743KB/s   in 14s

2017-03-12 14:17:29 (681 KB/s) - ‘ffmpeg-3.2.4.tar.bz2’ saved [9612274/9612274]

2) Expand the ffmpeg archive

root@silver:~# tar -xjvf ffmpeg-3.2.4.tar.bz2
.
.
.
(a lot of output here)
 
3) Rename the directory from ffmpeg-3.2.4 to ffmpeg

root@silver:~# mv ffmpeg-3.2.4 ffmpeg

4)  Enter the ffmpeg directory

root@silver:~# cd ffmpeg

5)  Run the ./configure -- program with flags

root@silver:~/ffmpeg# ./configure --enable-gpl --enable-libx264 --enable-libmp3lame \
--enable-nonfree --enable-libfdk-aac --enable-libv4l2
.
.
.
(a lot of output here)




Checking the ffmpeg configuration output for ALSA Support
What's important about this step is the fact that ALSA support is included, as indicated by the presence of the corresponding input device in the output:

Enabled indevs:
alsa                      fbdev                     lavfi

oss                       v4l2                      x11grab_xcb
dv1394

Checking the ffmpeg configuration output for MP3 Support
Another thing that's important is to ensure that libmp3lame support (to produce mp3 audio) is included, as indicated by the presence of this external library in the output:

External libraries:
iconv                     libxcb                    libxcb_shm

sdl2                      xlib                      zlib
libmp3lame                libxcb_shape              libxcb_xfixes
 


6) Run the make program

root@silver:~/ffmpeg# make
.
.
.
(a lot of output here)
.
(depending on your computer, this may take a while)
.
(it took between 30 and 40 minutes on my 1.6Ghz Celeron)
.
(also, don't worry about note and warning messages)


7) Run the make install program
.
.
.
(a lot of output here)

Valiating your ffmpeg Binary
Validating that you you now have an ffmpeg program capable of input via an alsa device can be checked within the ffmpeg program itself:

root@silver:~# ffmpeg -devices | grep alsa
ffmpeg version 3.2.4 Copyright (c) 2000-2017 the FFmpeg developers
  built with gcc 4.8 (Ubuntu 4.8.4-2ubuntu1~14.04.3)
  configuration: --enable-libmp3lame
  libavutil      55. 34.101 / 55. 34.101
  libavcodec     57. 64.101 / 57. 64.101
  libavformat    57. 56.101 / 57. 56.101
  libavdevice    57.  1.100 / 57.  1.100
  libavfilter     6. 65.100 /  6. 65.100
  libswscale      4.  2.100 /  4.  2.100
  libswresample   2.  3.100 /  2.  3.100
 DE alsa            ALSA audio outpu


Similarly, v
alidating that you you now have an ffmpeg program capable of transcoding via the libmp3lame library can also be checked within the ffmpeg program itself:

root@silver:~# ffmpeg -codecs | grep lame
ffmpeg version 3.2.4 Copyright (c) 2000-2017 the FFmpeg developers
  built with gcc 4.8 (Ubuntu 4.8.4-2ubuntu1~14.04.3)
  configuration: --enable-libmp3lame
  libavutil      55. 34.101 / 55. 34.101
  libavcodec     57. 64.101 / 57. 64.101
  libavformat    57. 56.101 / 57. 56.101
  libavdevice    57.  1.100 / 57.  1.100
  libavfilter     6. 65.100 /  6. 65.100
  libswscale      4.  2.100 /  4.  2.100
  libswresample   2.  3.100 /  2.  3.100

 DEA.L. mp3                  MP3 (MPEG audio layer 3) (decoders: mp3 mp3float ) (encoders: libmp3lame )


OK, it looks like ffmpeg is properly installed and configured.

Which Server Transport Protocol?



Realtime Transport Protocol (RTP)


Why I chose RTP
This choice was also easy, because it came for free.  RTP is engineered to transport a multitude of different multimedia formats, including MP3 (audio) and MP4 (video+audio), and it works "out of the box" with both Linux, ffmpeg and VLC.

Installing RTP
RTP does not need to be installed.   It is natively supported by Linux, VLC and ffmpeg.


OK, it looks like RTP s properly installed and configured.


Streaming the PC Microphone Over a Local Area Network


To test whether or not ffmpeg was working and could stream the microphone input over the LAN, two things were needed:

1) An RCA to DIN 3.5mm Adapter

2) Configuration information


To connect the Cable TV decoder to silver, and see if the microphone could be streamed over the LAN via ffmpeg and RTP, an adaptor was needed to convert the RCA connectors on the Cable TV decoder to the little microphone plug typically used by a PC for microphone input.  There is a specialized cable for this purpose.  I happen to have one.  It looks like this:



Once I connected the RCA output (RED=RIGHT, WHITE=LEFT) of the Cable TV box to the microphone jack of silver, I was ready to test my solution.  

I did so by running the following command:

#./ffmpeg -f alsa -i hw:0,0 -acodec libmp3lame -ab 330K -f rtp rtp://234.5.5.5:1234
 


Let me explain the parameters of this command:

-f alsa

Use the ALSA sound system to capture the incoming signal

-i hw:0,0

Capture the incoming signal from the hardware device (in this case, the microphone) located at hardware id 0,0

-acodec libmp3lame

Use the libmp3lame codec to transcode the signal from whatever it is received in (in this case, PCM) to mp3 format

-ab 330K

Set the audio bitrate (anything above 192K is high definition audio)

-f  rtp 

Format the output signal for delivery via the RTP protocol

rtp://234.5.5.5:1234

Deliver the RTP formatted information to the LAN via the supplied broadcast address.

This is what I heardMy microphone streaming solution worked!

2017003-23-UPDATE:  After a reboot, I noticed that I need to unplug and replug the rear microphone to get the computer to shift its attention from the front panel microphone jack to the rear panel microphone jack.  This may be a BIOS setting.  If I don't do this, ffmpeg streams and VLC connects perfectly, but there is no sound!

Streaming the WinTV HVR-1110 Over a Local Area Network


Streaming Cable TV Over the LAN


The final challenge of this project is to get the WinTV HVR-1110 video signal streamed over the LAN.  

First, I did a little detective work, because I felt I still needed to get the device names associated with the HVR-1110, this can be accomplished with the v412-ctl command:

root@silver:/# v4l2-ctl --list-devices
Hauppauge WinTV-HVR1110 DVB-T/H (PCI:0000:03:02.0):
        /dev/video0
        /dev/radio0
        /dev/vbi0


Next, I needed to know what formats were supported by the devices:

root@silver:~# ffmpeg -f v4l2 -list_formats all -i /dev/video0
ffmpeg version 3.2.4 Copyright (c) 2000-2017 the FFmpeg developers
  built with gcc 4.8 (Ubuntu 4.8.4-2ubuntu1~14.04.3)
  configuration: --enable-libmp3lame
  libavutil      55. 34.101 / 55. 34.101
  libavcodec     57. 64.101 / 57. 64.101
  libavformat    57. 56.101 / 57. 56.101
  libavdevice    57.  1.100 / 57.  1.100
  libavfilter     6. 65.100 /  6. 65.100
  libswscale      4.  2.100 /  4.  2.100
  libswresample   2.  3.100 /  2.  3.100
[video4linux2,v4l2 @ 0x3672380] Raw    :        gray :      8-bit Greyscale :
[video4linux2,v4l2 @ 0x3672380] Raw    :    rgb555le : 16-bit A/XRGB 1-5-5-5 :
[video4linux2,v4l2 @ 0x3672380] Raw    :    rgb555be : 16-bit A/XRGB 1-5-5-5 BE :
[video4linux2,v4l2 @ 0x3672380] Raw    :    rgb565le :     16-bit RGB 5-6-5 :
[video4linux2,v4l2 @ 0x3672380] Raw    :    rgb565be :  16-bit RGB 5-6-5 BE :
[video4linux2,v4l2 @ 0x3672380] Raw    :       bgr24 :     24-bit BGR 8-8-8 :
[video4linux2,v4l2 @ 0x3672380] Raw    :       rgb24 :     24-bit RGB 8-8-8 :
[video4linux2,v4l2 @ 0x3672380] Raw    :        bgr0 : 32-bit BGRA/X 8-8-8-8 :
[video4linux2,v4l2 @ 0x3672380] Raw    :        0rgb : 32-bit A/XRGB 8-8-8-8 :
[video4linux2,v4l2 @ 0x3672380] Raw    :     yuyv422 :           YUYV 4:2:2 :
[video4linux2,v4l2 @ 0x3672380] Raw    :     uyvy422 :           UYVY 4:2:2 :
[video4linux2,v4l2 @ 0x3672380] Raw    :     yuv422p :     Planar YVU 4:2:2 :
[video4linux2,v4l2 @ 0x3672380] Raw    :     yuv420p :     Planar YUV 4:2:0 :
[video4linux2,v4l2 @ 0x3672380] Raw    :     yuv420p :     Planar YVU 4:2:0 :
/dev/video0: Immediate exit requested


The Mysteriously NOT Working Command

Strangely, the following command did NOT work, even though it should have:

root@silver:~# ffmpeg -re -i /dev/video0 -vcodec mpeg4 -an -sdp_file CableTV.sdp -f rtp rtp://234.5.5.6:1234

Here's what the options mean:

(these options are explained in much greater detail at the ffmpeg documentation project):

-re

Read input at native frame rate. Mainly used to simulate a grab device, or live input stream (e.g. when reading from a file). Should not be used with actual grab devices or live input streams (where it can cause packet loss). By default ffmpeg attempts to read the input(s) as fast as possible. This option will slow down the reading of the input(s) to the native frame rate of the input(s). It is useful for real-time output (e.g. live streaming).

-i /dev/video0

Specifies the video input as the input signal

-vcodec mpeg4

Use the mpeg4 video codec to transcode the incoming signal to MPEG4 format

-an

Disable audio recording

-sdp_file CableTV.sdp

Create an .sdp file as specified

-f rtp
 
Format the result for transport using the RTP protocol
 
rtp://234.5.5.6:1234

Send the end result to the following RTP address

Yes, it created the a CableTV.sdp file, but VLC was unable to open it for some reason:


 

The Working Command


Eventually, I figured out a command that worked.  Here it is:

root@silver:~# ffmpeg -re -i /dev/video0 -vcodec mpeg4 -an -f rtp rtp://234.5.5.6:1234


Here's what the options mean:

(these options are explained in much greater detail at the ffmpeg documentation project):

-re

Read input at native frame rate. Mainly used to simulate a grab device, or live input stream (e.g. when reading from a file). Should not be used with actual grab devices or live input streams (where it can cause packet loss). By default ffmpeg attempts to read the input(s) as fast as possible. This option will slow down the reading of the input(s) to the native frame rate of the input(s). It is useful for real-time output (e.g. live streaming).

-i /dev/video0

Specifies the video input as the input signal

-vcodec mpeg4

Use the mpeg4 video codec to transcode the incoming signal to MPEG4 format

-an

Disable audio recording

-f rtp

Format the result for transport using the RTP protocol
 
rtp://234.5.5.6:1234

Send the end result to the following RTP address

Capturing the SDP File Information:
 
When I issued that command, I got the following output on the Ubuntu Linux screen:

root@silver:~# ffmpeg -re -i /dev/video0 -vcodec mpeg4 -an -f rtp rtp://234.5.5.6:1234
ffmpeg version 3.2.4 Copyright (c) 2000-2017 the FFmpeg developers
  built with gcc 4.8 (Ubuntu 4.8.4-2ubuntu1~14.04.3)
  configuration: --enable-libmp3lame
  libavutil      55. 34.101 / 55. 34.101
  libavcodec     57. 64.101 / 57. 64.101
  libavformat    57. 56.101 / 57. 56.101
  libavdevice    57.  1.100 / 57.  1.100
  libavfilter     6. 65.100 /  6. 65.100
  libswscale      4.  2.100 /  4.  2.100
  libswresample   2.  3.100 /  2.  3.100
Input #0, video4linux2,v4l2, from '/dev/video0':
  Duration: N/A, start: 226676.542810, bitrate: 92160 kb/s
    Stream #0:0: Video: rawvideo (I420 / 0x30323449), yuv420p, 640x480, 92160 kb/s, 25 fps, 25 tbr, 1000k tbn, 1000k tbc
Output #0, rtp, to 'rtp://234.5.5.6:1234':
  Metadata:
    encoder         : Lavf57.56.101
    Stream #0:0: Video: mpeg4, yuv420p, 640x480, q=2-31, 200 kb/s, 25 fps, 90k tbn, 25 tbc
    Metadata:
      encoder         : Lavc57.64.101 mpeg4
    Side data:
      cpb: bitrate max/min/avg: 0/0/200000 buffer size: 0 vbv_delay: -1
SDP:
v=0
o=- 0 0 IN IP4 127.0.0.1
s=No Name
c=IN IP4 234.5.5.6
t=0 0
a=tool:libavformat 57.56.101
m=video 1234 RTP/AVP 96
b=AS:200
a=rtpmap:96 MP4V-ES/90000
a=fmtp:96 profile-level-id=1


Stream mapping:
  Stream #0:0 -> #0:0 (rawvideo (native) -> mpeg4 (native))
Press [q] to stop, [?] for help
frame=17442 fps= 25 q=31.0 size=   22841kB time=00:11:37.64 bitrate= 268.2kbits/s speed=   1x

 

I found the SDP information in the output, copied it to memory, pasted it into an editor and saved what resulted to a CableTV.sdp file on my PC.   

To do this, I used gvim.


What's the difference?

The CableTV.sdp file created by ffmpeg is a little bit different than the cut/paste file I manually created.  Here's where things are different:

root@silver:~# diff ./CableTV.sdp /mnt/media/Music/TEST/CableTV.sdp
1,11c1,11
< SDP:
< v=0
< o=- 0 0 IN IP4 127.0.0.1
< s=No Name
< c=IN IP4 234.5.5.6
< t=0 0
< a=tool:libavformat 57.56.101
< m=video 1234 RTP/AVP 96
< b=AS:200
< a=rtpmap:96 MP4V-ES/90000
< a=fmtp:96 profile-level-id=1
---
> v=0
> o=- 0 0 IN IP4 127.0.0.1
> s=No Name
> c=IN IP4 234.5.5.6
> t=0 0
> a=tool:libavformat 57.56.101
> m=video 1234 RTP/AVP 96
> b=AS:200
> a=rtpmap:96 MP4V-ES/90000
> a=fmtp:96 profile-level-id=1
>
 


It appears that ffmpeg prepends the string 'SDP:' to the top of the CableTV.sdp file.

This, or something else (maybe the ^M charaters), is  confusing VLC.  Despite much fooling around, I was never able to figure out why (I removed the SDP: header and/or the ^M characters at the end of each line, neither approach worked).

Victory

PC Configuration and Testing


On my PC, here's what CableTV.sdp looked like when I was done.  After I created it, the file was automatically associated with VLC, which looked very encouraging:

 

Breath bated, I double-clicked on the CableTV.sdp file and here's what I saw:


Great success!

With:

  • ffmpeg process #1 streaming sound from the PC microphone
  • ffmpeg process #2 streaming video from the WinTV HVR-1110

I was able to consume CableTV media as I pleased (audio or video or audio+video), which was the aim of this project.

UPDATE (2017-03-24):  The video capture stopped working.  Somehow, some of the firmware for the tda10046 was reverted back to version 0, which the card recognizes as "invalid":

root@silver:~/WinTV/lib/firmware/29# dmesg | grep tda1004*
[   25.248042] tda1004x: setting up plls for 48MHz sampling clock
[   27.544039] tda1004x: timeout waiting for DSP ready
[   27.584044] tda1004x: found firmware revision 0 -- invalid
[   27.584050] tda1004x: trying to boot from eeprom
[   29.920045] tda1004x: timeout waiting for DSP ready
[   29.960041] tda1004x: found firmware revision 0 -- invalid
[   29.960047] tda1004x: waiting for firmware upload...
[   43.904039] tda1004x: found firmware revision 29 -- ok

 

Thankfully, I retained a copy of the firmware in the /root subdirectory, so I was able to simply copy the files over into /lib/firmware once again:

root@silver:~/WinTV/lib/firmware# ls -l
total 8
drwxr-xr-x 2 root root 4096 Mar 18 14:09 0
drwxr-xr-x 2 root root 4096 Mar 18 14:11 29
root@silver:~/WinTV/lib/firmware# cd 29

root@silver:~/WinTV/lib/firmware/29# ls -l *tda*
-rw-r--r-- 1 root root 30555 Mar 18 14:10 dvb-fe-tda10045.fw
-rw-r--r-- 1 root root 30555 Mar 18 14:10 dvb-fe-tda10045.fw-obsolete
-rw-r--r-- 1 root root 24602 Mar 18 14:10 dvb-fe-tda10046.fw
-rw-r--r-- 1 root root 24878 Mar 18 14:10 dvb-fe-tda10048-1.0.fw
root@silver:~/WinTV/lib/firmware/29# cp *tda* /lib/firmware/


A reboot later revealed:

root@silver:~/WinTV/lib/firmware# dmesg | grep tda1*
[   20.560044] tda829x 0-004b: setting tuner address to 61
[   20.652053] tda829x 0-004b: type set to tda8290+75a
[   24.732023] tda1004x: setting up plls for 48MHz sampling clock
[   25.040114] tda1004x: found firmware revision 29 -- ok
 

 

NOTEA potential future update to this project is to consolidate all of the A/V to the WinTV HVR-1110 inputs.  It does have Yellow (video), Red (right audio) and White (left audio) connectors, so it should be able to accept everything, making the microphone connection unnecessary.  This may necessitate recompiling the Linux driver (see Appendix A)If I ever do this, I will come back and update this article as Appendix B.


References:


Bentham, D (2008) saa7134: Hauppauge HVR-1110, support for radio and analog audio in [Online] Available from: https://linuxtv.org/hg/v4l-dvb/rev/40d58d92d183 (Accessed: 2017-03-11).

ffmpeg (n.d.) FFmpeg Documentation [Online], Available from: https://www.ffmpeg.org/ffmpeg.html (Accessed: 2017-03-11).

ffmpeg Wiki (n.d.) Compile FFmpeg on Ubuntu, Debian or Mint [Online], Available from: http://trac.ffmpeg.org/wiki/CompilationGuide/Ubuntu (Accessed: 2017-03-11).

Linux TV (n.d) Hauppauge WinTV-HVR-1110 [Online], Available from:  https://www.linuxtv.org/wiki/index.php/Hauppauge_WinTV-HVR-1110 (Accessed: 2017-03-11).


Luca (2010) RTP Streaming with ffmpeg [Online], Available from: http://lucabe72.blogspot.hk/2010/04/rtp-streaming-with-ffmpeg.html (Accessed 2017-03-11).

OhHeyItsLou Tutorials (2011) Tutorial: How to Configure, Compile & Install ffmpeg and x264 from source for all Ubuntu & Debian Distros [Online], Available from: http://ohheyitslou.blogspot.hk/2011/12/this-tutorial-details-necessary-steps.html (Accessed: 2017-03-12).

Plumridge, R. (n.d.) Stream Live Audio from a Microphone in Near Real Time in Ubuntu [Online], Available from: https://prupert.wordpress.com/2010/08/02/stream-live-audio-from-a-microphone-in-near-real-time-in-ubuntu (Accessed: 2017-03-11).


Appendix A:  Potential Necessary Changes to Enable Stereo RCA Input to WinTV HVR-1110

This may be a lead for later, because it looks like a change to some of the source code of saa7134-cards.c might be required for RCA audio in to work properly, according to the Linux TV website:

--- a/linux/drivers/media/video/saa7134/saa7134-cards.c Sun Sep 28 22:10:03 2008 -0300
+++ b/linux/drivers/media/video/saa7134/saa7134-cards.c Sun Sep 28 19:29:51 2008 +0000
@@ -3299,6 +3299,7 @@
  },
  [SAA7134_BOARD_HAUPPAUGE_HVR1110] = {
   /* Thomas Genty <tomlohave@gmail.com> */
+  /* David Bentham <db260179@hotmail.com> */
   .name           = "Hauppauge WinTV-HVR1110 DVB-T/Hybrid",
   .audio_clock    = 0x00187de7,
   .tuner_type     = TUNER_PHILIPS_TDA8290,
@@ -3307,23 +3308,26 @@
   .radio_addr     = ADDR_UNSET,
   .tuner_config   = 1,
   .mpeg           = SAA7134_MPEG_DVB,
+  .gpiomask       = 0x0200100,
   .inputs         = {{
    .name = name_tv,
    .vmux = 1,
    .amux = TV,
    .tv   = 1,
-  },{
-   .name   = name_comp1,
-   .vmux   = 3,
-   .amux   = LINE2, /* FIXME: audio doesn't work on svideo/composite */
-  },{
-   .name   = name_svideo,
-   .vmux   = 8,
-   .amux   = LINE2, /* FIXME: audio doesn't work on svideo/composite */
-  }},
+   .gpio = 0x0000100,
+  }, {
+   .name = name_comp1,
+   .vmux = 3,
+   .amux = LINE1,
+  }, {
+   .name = name_svideo,
+   .vmux = 8,
+   .amux = LINE1,
+  } },
   .radio = {
    .name = name_radio,
-   .amux   = TV,
+   .amux = TV,
+   .gpio = 0x0200100,
   },
  },
  [SAA7134_BOARD_CINERGY_HT_PCMCIA] = {

2 comments:

  1. Thanks for this detailed writeup and explanations. I have followed your instructions, the only problem being that the sdp file is not being played by vlc, nor is the network stream.

    My card is a Hauppage 1265 - digital card. And the list of devices show up correctly etc.

    ReplyDelete
  2. One more question. The tc tuner card when scanned, shows 8 service ids. Thru the ffmpeg command how do i select the program?

    When i run with mencoder, the generated file is perfect. But so far, no success with ffmpeg, all invalid files:
    mencoder -v dvb://1 -o test.mpg -oac copy -ovc lavc
    (1 here being the 1st service id)

    ReplyDelete