Et voila! (if everything works, as it did for me)
If you run into an issue where “libraries can’t be found”, you are probably missing the zlib library. I have posted a defect for this here.
Tags: ant, c, ffmpeg, Java, mingw, msys, xuggle
If people aren’t complaining about Flash and HTML5 they are falling back to NoSQL vs RDBMS. There is a time and a place for everything, just remember that tidbit. So to get on with it, I would like to state that I am mostly a Windows user and I love Windows 7.. It f#@king rocks! I also use Google Chrome as my primary browser on both OSX and Windows. I recently loaded the latest dev build of Chrome that contains a streamlined Flash Player and I can say that it is awesome.
To test, I started up a Red5 instance with some mp4 and vp6 videos to see what the CPU usage would be and here is the result: Red5 = 0% to 7% and Chrome = 3% to 6% (average 3%)
The playback was smooth as silk and the audio was perfect. Next up for comparison, I tried IE and FF:
IE 8 with FP10.1 = 5% to 11% (average 5%)
Firefox 3.6 with FP 10.1 = 14% to 66% (average 40%)
Tags: chrome, firefox, flash, html5, ie8, Java, mp4, Red5
Since I’ve seen nothing which addresses the processing delays that I noticed in ffmpeg when generating thumbnail images, I figured I should share some important optimizations. I used to specify this command line when generating the images from a movie source (f4v in this case):
ffmpeg -y -i mymovie.f4v -an -ss 00:05:00 -t 00:00:00.01 -sameq -r 1 -vframes 1 -deinterlace -f mjpeg mythumbnail.jpg
This will take about one minute to generate the image of the video frame which is five seconds into the clip. This seems really extreme and is even worse when you try to increase the start location; for instance 45 seconds in, takes about an hour.
So, I knew there had to be a better way and I monkeyed around with the options:
ffmpeg -y -ss 00:05:00 -i mymovie.f4v -an -t 00:00:00.01 -sameq -r 1 -vframes 1 -deinterlace -f mjpeg mythumbnail.jpg
There is only one change between these lines, the placement of the “ss” option. This change causes the command to complete in less than a second, no matter what our start time is. Quite an increase in processing for something so simple! I hope this helps a few of you out there.
Tags: f4v, ffmpeg, jpg, thumbnail
The game my company has been working on for months is finally approved in the AppStore! Get your copy now! Click here
If you are using a desktop like I am and you dont “hibernate” your system, then you may want to turn this feature off. I have 12 Gb of RAM so this saves ~9 Gb on my C: drive. Heres how you save the space:
1. Click on Windows 7 Start Button 2. Go to All Programs-> Accessories 3. Now right on Command Prompt and select “Run as Administrator” from context menu. 4. Type "powercfg -h off" without the quotes
Thats all and hopefully it helps someone else out there…
Tags: hiberfil.sys, windows
Red5 now supports “native” RTMPS in addition to RTMPT over SSL. To use this feature you will need to use the current trunk version until 0.9 RC3 or Final are released. A big shout-out goes to Kevin Green for providing the original patch. Using this communication channel, your data will be secured throughout the process from connection to shutdown using TLS/SSL and should provide the secure features you need until RTMPE is ready.

Red5NativeRTMPS
nc = new NetConnection(); nc.client = this; nc.proxyType = "best";
For this example I used a free opensource ssl cert provided by godaddy.
Step by step process:
1. Create your key
keytool -keysize 2048 -genkey -alias red5 -keyalg RSA -keystore keystore
Enter keystore password:
Re-enter new password:
What is your first and last name?
[Unknown]: ssl.red5.org
What is the name of your organizational unit?
[Unknown]: Dev
What is the name of your organization?
[Unknown]: Red5
What is the name of your City or Locality?
[Unknown]: Henderson
What is the name of your State or Province?
[Unknown]: Nevada
What is the two-letter country code for this unit?
[Unknown]: US
Is CN=ssl.red5.org, OU=Dev, O=Red5, L=Henderson, ST=Nevada, C=US correct?
[no]: yes
Enter key password for <red5>
(RETURN if same as keystore password):
2. Create a CSR
keytool -certreq -keyalg RSA -alias red5 -file red5.csr -keystore keystore Enter keystore password:
3. Submit your CSR to your SSL certificate provider. Godaddy process is described below.
4. After your receive your certificate, import the root cert into your keystore file
keytool -import -alias root -keystore keystore -trustcacerts -file valicert_class2_root.crt Enter keystore password: Certificate already exists in system-wide CA keystore under alias <valicertclass2ca> Do you still want to add it to your own keystore? [no]: yes Certificate was added to keystore
5. Import the cross certificates
keytool -import -alias cross -keystore keystore -trustcacerts -file gd_cross_intermediate.crt Enter keystore password: Certificate was added to keystore
6. Import the intermediate certificates
keytool -import -alias intermed -keystore keystore -trustcacerts -file gd_intermediate.crt Enter keystore password: Certificate was added to keystore
7. Import your certificate
keytool -import -alias red5 -keystore keystore -trustcacerts -file ssl.red5.org.crt Enter keystore password: Certificate reply was installed in keystore
8. Setup RTMPS in your red5/conf/red5-core.xml. You may notice that some of the rtmp variables are used here, that is only for ease of setup; you could set them to whatever you prefer.
<bean id="rtmpsMinaIoHandler"
class="org.red5.server.net.rtmps.RTMPSMinaIoHandler">
<property name="handler" ref="rtmpHandler" />
<property name="codecFactory" ref="rtmpCodecFactory" />
<property name="rtmpConnManager" ref="rtmpMinaConnManager" />
<property name="keyStorePassword" value="${rtmps.keystorepass}" />
<property name="keystoreFile" value="conf/keystore" />
</bean>
<bean id="rtmpsTransport" class="org.red5.server.net.rtmp.RTMPMinaTransport" init-method="start" destroy-method="stop">
<property name="ioHandler" ref="rtmpsMinaIoHandler" />
<property name="connectors">
<list>
<bean class="java.net.InetSocketAddress">
<constructor-arg index="0" type="java.lang.String" value="${rtmps.host}" />
<constructor-arg index="1" type="int" value="${rtmps.port}" />
</bean>
</list>
</property>
<property name="receiveBufferSize" value="${rtmp.receive_buffer_size}" />
<property name="sendBufferSize" value="${rtmp.send_buffer_size}" />
<property name="eventThreadsCore" value="${rtmp.event_threads_core}" />
<property name="eventThreadsMax" value="${rtmp.event_threads_max}" />
<property name="eventThreadsQueue" value="${rtmp.event_threads_queue}" />
<property name="eventThreadsKeepalive" value="${rtmp.event_threads_keepalive}" />
<property name="jmxPollInterval" value="1000" />
<property name="tcpNoDelay" value="${rtmp.tcp_nodelay}" />
</bean>
Additional security info can be found here
The testing player source can be found here

Screenshot of playing nsv stream in flash
This morning I was successful in playing a live NSV stream with FlashPlayer via Red5. I used NSVCap encoding VP62 and AAC. The code is implemented using the new Red5 plug-in system and will be released with 0.9.0 (soon). Huge thank yous go out to Andy Shaules and Wittawas Nakkasem for their help developing this feature.
We are now worm-safe, for now. Thanks Influxis!
In Java, something which has always caught my eye or bugs me to no end is a large “if” block. Normally I refactor these into a “switch” to make it cleaner and easier to read, but in the case of String comparison it becomes more difficult. To diverge for a moment, I would point out that you can use a string’s hash code for a switch but you must know it ahead of final compilation (pita). So to get back to the point of this post, I want to show a little code I used today to remove an unruly looking if statement. This is the original code from Red5 (code shortened for brevity):
if (action.equals(ACTION_CREATE_STREAM)
|| action.equals(ACTION_DELETE_STREAM)
|| action.equals(ACTION_RELEASE_STREAM)
|| action.equals(ACTION_PUBLISH)
|| action.equals(ACTION_PLAY)
|| action.equals(ACTION_SEEK)
|| action.equals(ACTION_PAUSE)
|| action.equals(ACTION_PAUSE_RAW)
|| action.equals(ACTION_CLOSE_STREAM)
|| action.equals(ACTION_RECEIVE_VIDEO)
|| action.equals(ACTION_RECEIVE_AUDIO)) {
//do something
}
This section has always bugged me, so I decided to make a collection containing all these strings. There may be 11 calls to String.equals in this block alone! Our “optimization” has a problem and it is that the “Constants” class containing the actions is an interface and as we all know you cant execute methods in an interface, or can we?
public static final List<String> STREAM_ACTION_LIST = new ArrayList<String>(11){
{
//Add all the stream actions to make lookup simpler
add(ACTION_CREATE_STREAM);
add(ACTION_DELETE_STREAM);
add(ACTION_RELEASE_STREAM);
add(ACTION_PUBLISH);
add(ACTION_PLAY);
add(ACTION_SEEK);
add(ACTION_PAUSE);
add(ACTION_PAUSE_RAW);
add(ACTION_CLOSE_STREAM);
add(ACTION_RECEIVE_VIDEO);
add(ACTION_RECEIVE_AUDIO);
}
};
Using a class initializer we can accomplish what we want! If you use this, dont forget to replace the brace characters.
So now the old if block becomes this:
if (STREAM_ACTION_LIST.contains(action)) {
//do something
}
Tags: Java, optimization, Red5
A new feature has been added to Red5 to allow any number of Mina IoFilters to be added to a connection at the Server or Application level. The particular filter detailed here is one that simply counts the connections and rejects any that exceed the set maximum number. This post details setting the filter at the Application level, but if you want it at the server level simply add the below bean definitions to your global webapp configuration located here: red5/webapps/red5-default.xml.
To add the filter you must first edit your applications red5-web.xml and add your beans:
<!-- Limits connections on a per-session basis -->
<bean id="connectionFilter" class="org.gregoire.red5.ConnectionShapeFilter">
<property name="maxConnections" value="2"/>
</bean>
Next create a “config” bean to inform the server about your filter bean names:
<bean id="config" class="org.red5.server.adapter.Config">
<!-- List of filter bean names to be loaded -->
<property name="filterNames">
<list>
<value>connectionFilter</value>
</list>
</property>
</bean>
One important thing to note is that since classes in the main server are creating the connections, your filter classes must be found by the URLClassloader. The URLClassloader created by the server uses jar files within Red5′s lib directory, so put your filter classes here (red5/lib) inside a jar. Once your classes are in-place, start your server and the filters will take effect.
An example Eclipse / FlexBuilder project can be found here.
Tags: iofilter, Java, mina, Red5