|
RealProducer Scripts
The streaming video webcasts that we do are not a trivial matter: keeping the server up was a bit of a challenge at first, but I came up with a set of scripts that makes it operate itself mostly unattended. Here is how video gets from us to you:
|
Here are the shell scripts that make all that work. The whole setup is pretty much held together with spit and bubblegum, but it's been working pretty well for me. Please let me know if you find this useful, or make any improvements...
| rtsp-ping | This is a script that probes whether a realvideo stream is alive. ``RTSP'' is the HTTP-like protocol that realserver uses. This script knows how to generate the proper headers to ask whether the given URL has data on it. |
| realprod-initd | This is the /etc/rc.d/init.d/ script that launches realproducer: this is where all the arguments to the video encoder are specified, including quality settings and the password. |
| realprod.conf | This is a configuration file passed to realproducer. By using this file instead of sticking just to command-line arguments, you can get finer grained control over things like frame rate, and the exact audio and video codecs used. |
| realprod-nanny | Since realproducer, well, kind of
sucks, it occasionally loses its mind and wedges (or
otherwise stops communicating with the server) without
actually exiting or crashing. So
realprod-nanny is a script
that periodically probes the server: if there is not a live
stream where one is supposed to be, then it kills and
restarts realproducer (by running
|
| realprod-nanny-initd | This is the /etc/rc.d/init.d/ script that launches realprod-nanny. |
RealProducer communicates with RealServer over some or all of the following ports:
| TCP: | 554, 7070, 8080 |
| UDP: | 6970-6999 |
So at the least, your firewall has to allow those to pass between the encoder and the server.
But if you're doing NAT (Network Address Translation, meaning that the machines on the inside of the firewall have a different idea of what their IP addresses are than what the outside world sees) then life is harder.
The bottom line is, you can't use the Linux ipchains package if you want to use RealProducer through the firewall, no matter how many ports you open up. However, OpenBSD's ipf package works fine. (I have not tried ipfw.)
The reason is this: say you have three machines:
| internal net: | external net: | |||
| encoder: | 172.28.1.5 | 166.88.23.5 | ||
| firewall: | 172.28.1.1 | 166.88.23.1 | ||
| server: | 209.133.35.83 |
So firewall is doing 1:1 NAT for encoder, so that encoder itself thinks that it has the address ``172.28.1.5'', but the outside world thinks that it has the address ``166.88.23.5''.
If you do this on Linux, then the packets that arrive at server from encoder will have a source address of 166.88.23.1 (the external address of firewall.) If you use OpenBSD, they will have a source address of 166.88.23.5 (the external address of encoder.)
For most protocols, either way works; but for Real, only the latter works. I don't know why.
My only guess is that somehow, Real is encoding its vision of the address of the encoder machine in the protocol data itself, instead of getting it out of the TCP and UDP layer. So the firewall doesn't know how to reach into the data and rewrite those IPs. I can't imagine why the software would be doing this, but that's the only explanation I can come up with for the observed behavior.
Here's how you make it work:
On the firewall machine, set up the ethernet interface that is attached to the outside world to bind to multiple addresses in /etc/hostname.xl0 (or whichever it is):
inet 166.88.23.1 0xffffff00 NONE
inet alias 166.88.23.5 0xffffffff NONE
Set up a bidirectional mapping in /etc/ipnat.rules:
bimap xl0 172.28.1.5/32 -> 166.88.23.5/32
In /etc/ipf.rules, let your encoder send packets out to the Real ports, and also get replies back (that's what ``keep state'' is):
pass out proto tcp from 172.28.1.5 to 209.133.35.83 port = 554 keep state
pass out proto tcp from 172.28.1.5 to 209.133.35.83 port = 4040 keep state
pass out proto udp from 172.28.1.5 to 209.133.35.83 keep state
And that's about it. I would rather have had all of my machines running the same operating system, for simplicity and ease of upgrades, but the only sensible thing was to use OpenBSD for my firewall, because the Linux firewall code was simply not up to the job.
<rant> I understand that the development Linux kernels have a brand new firewall package in them. Great, this is the third rewrite of the Linux firewall code in three years (with a third incompatible syntax, mind you.) It's as if whoever is responsible is treating this as a learning process or something. What they should do is just port the BSD code to Linux, since it's more powerful, older, widely used, and stable. But the free Unixes believe in nothing if not the doctrine of ``Not Invented Here.'' </rant>
Thanks again to our friends at
|