Today we want to present you our latest project Pipelight, which allows to run your favorite Silverlight application directly inside your Linux browser. The project combines the effort by Erich E. Hoover with a new browser plugin that embeds Silverlight directly in any Linux browser supporting the Netscape Plugin API (Firefox, Chrome / Chromium, Midori, Opera, …). He worked on a set of Wine patches to get Playready DRM protected content working inside Wine and afterwards created an Ubuntu package called Netflix Desktop. This package allows one to use Silverlight inside a Windows version of Firefox, which works as a temporary solution but is not really user-friendly and moreover requires Wine to translate all API calls of the browser. To solve this problem we created Pipelight.
Pipelight consists out of two parts: A Linux library which is loaded into the browser and a Windows program started in Wine. The Windows program, called
pluginloader.exe, simply simulates a browser and loads the Silverlight DLLs. When you open a page with a Silverlight application the library will send all commands from the browser through a pipe to the Windows process and act like a bridge between your browser and Silverlight. The used pipes do not have any big impact on the speed of the rendered video since all the video and audio data is not send through the pipe. Only the initialization parameters and (sometimes) the network traffic is send through them. As a user you will not notice anything from that "magic" and you can simply use Silverlight the same way as on Windows, like you can see on the following screenshot:
You can easily try it out on your own with our prepared and ready to use PPA. Just follow the instructions in the next section. If you are interested in story behind the project and how all the things work internally, you just need to scroll down a bit.
UPDATE 2013-11-14: Version 0.2.2 is now available.
UPDATE 2013-10-31: Version 0.2.1 is now available, take a look at https://launchpad.net/pipelight/+announcement/12115 for the changes.
UPDATE 2013-10-15: Version 0.2.0 is now available, take a look at https://launchpad.net/pipelight/+announcement/12054 for the changes.
UPDATE 2013-09-16: Version 0.1-4 is now available, take a look at https://launchpad.net/pipelight/+announcement/11996 for the changes.
UPDATE 2013-09-08: Version 0.1-3 is now available.
UPDATE 2013-08-28: Version 0.1-2 is now available, take a look at https://launchpad.net/pipelight/+announcement/11868 for the changes.
Table of contents
1. Download / Installation instructions
The instructions have been moved to a separate page.
2. Help, its not working / I found a bug!
This section has been moved to a different page.
3. Story behind the project
When we started our project there was no Silverlight 5 DRM support in Wine, only Silverlight 4 could be used by applying the patches of Erich E. Hoover. Unfortunately since the release of his patches, some of the streaming websites like Maxdome upgraded to Silverlight 5 so our first goal was to get version 5 to work. Whenever you probably have used Wine before, you might have noticed the whole bunch of "fixme" and "stub" messages scrolling down when executing native Windows programs. These messages are caused by the fact that Wine is still far away from being a complete replacement for Windows. Of course it would be possible to solve all these issues and get everything working on Wine, but this would need infinite amounts of resources and moreover is an increasingly difficult task, especially because not all Windows API commands are documented exactly. Besides these obvious messages which show that there is something missing, there are also cases where there isn't any visible output.
At the beginning we first focused on the most obvious output messages, and tried to write quick & dirty implementations for the the missing functions. In most cases it seemed to be a success at first, for example when new error messages appeared at a later point in the program. But even after fixing more of them, nothing had changed. We continued trying different methods to find the issue and at one point even were convinced, that the newer versions of Silverlight must have some kind of active protection against Wine and/or virtual machines. We still don't know if this is probably the case, but nevertheless Michael by accident discovered the crucial point where it failed in our previous attempts.
We always though the errors were related to the kind of DRM protection which was used, but as it turns out they weren't. Just to try out the effect Michael modified the value of one of the arguments passed to the Silverlight applet -
enableGPUAcceleration to false - and although we didn't expect this would change anything, suddenly Silverlight 5 DRM worked almost perfectly. The only remaining problem - one of the streaming pages didn't have any sound - finally was solved by a smart guess of Erich E. Hoover, who suggested to try another patch file which just adds a single word in one of the million lines of code! A string comparison did not work as expected and Silverlight was unable to select the correct audio steam.
Our second goal was to find a way to circumvent simulating a whole browser environment and just to execute the Silverlight plugin. As Silverlight uses the NPAPI interface (except for IE) and nearly every modern browser (both Windows and Linux) supports this plugin API, we decided to write some kind of wrapper plugin. Since it's not directly possible to load a Win32 DLL in an Linux process, we created on the one side a Linux compatible NPAPI plugin (internally just a shared library) and on the other side a Windows program which simulates some kind of "browser" to load the Silverlight library. Here the term browser just means that we are providing the browser side part of the NPAPI to Silverlight.
It didn't take very long until we had the first version finished, but as usual, nothing worked at the beginning. After another additional day of debugging we finally figured out what was wrong: Silverlight assumes that the COM-Library is already initialized when loading the plugin! This is not part of the API, but if you take a look at the source code of Webkit (this file - line 65), you will see that there are 21 work arounds for plugins which do not behave according to the API (which seems to be the majority of the plugins). Nevertheless after adding one simple line of code we got Silverlight to start:
As a next step we continued implementing more and more features of the API till it worked with all our testing websites. The last and most difficult step was to embed the window directly into the native browser, which required additional patching of Wine. The final version is now able to transparently redirect and convert most API calls between the browser and plugin, such that it is possible to use Silverlight just like any other NPAPI browser plugin.
The main advantage over the previous solution to run Firefox in Wine is that this approach runs much more smooth and doesn't require as much resources. Moreover it might be easier to just watch movies in your favorite browser than switching each time you want to watch something.
If you are programmer yourself you may also be interested in the technical details and how everything works internally. In this section we will describe the way Pipelight works from a programmers perspective. Please note that we cannot describe here everything completely in detail, but as its open source software, you can easily take a look at it yourself.
Like in any other open source project patches and bug fixes are welcome. Just open a new bug report here and add your patch file as attachment under extras. We will take a look at it and decide whether we apply it to the repository or if the patch needs further improvements.
If you have questions or just want to know more about the internals of Pipelight, you are free to join our IRC channel #pipelight on Freenode.
4.1. Quick overview
The project is split in two parts: a shared library which is loaded into your Linux browser and a pluginloader which is executed in Wine. The shared library offers the Netscape Plugin API (NPAPI) to the browsers and acts like all other plugins, except the fact that it does not provide the API functions directly. When the library is loaded by the browsers it starts the pluginloader in Wine and sends all API calls to the plugin through a pipe. The loader will listen for this calls and send them to the Silverlight plugin. All handles, interfaces and objects which are only available at one side are recreated as fake objects on the other side, so that we can capture all calls and redirect them through the pipe. The real handles are replaced by fake 64 bit IDs during the transmission, which allows us to load 32 bit plugins into 64 bit browsers and vice versa without having to pay attention at the size of the real handles. The only real difference in the API between Linux and Windows is the handling of drawing and input events, which requires additional code inside the pluginloader.
The communication itself is done using using two pipes and a very simple protocol. Whenever the browser wants the plugin to execute some specific function, it writes all required information into one end of the first pipe. The plugin decodes and dispatches the request and sends back the response in the second pipe. This method even works if the plugin itself wants to call back a browser function by just using stack recursion.
In early version of Pipelight (or when setting
embed=false in the configuration file) the plugin is loaded in a separate window. We have developed a Wine patch adding Xembed-client support which allows us to embed the window directly into the native browser. The alternative method is still available as a fallback - in some cases it might be even useful, for example when you want to resize the applet window.
4.2. Which file corresponds to which methods?
The following summary should give you a quick introduction where in the sources you can find which specific component:
configloader.cis used to parse and load the configuration file
basicplugin.cis responsible for starting Wine and dispatching events coming in from a pipe
pluginfunctions.ccontains all the NP_* and NPP_* plugin functions called by your Linux browser
npclass.cacts as a proxy for non-existent NPClass objects on the Linux side (those created by the Silverlight plugin)
pluginloader.ccontains the main function (loading Silverlight) and dispatching events coming from the Linux side
npnfunctions.cprovides the browser API used by Silverlight
npclass.cis just a dummy file containing functions which should never be called (if Silverlight behaves according to the documentation)
communication.ccontains most of the pipe communication functions used by the rest of the plugin
handlemanager.cis responsible for converting handles to IDs and contains functions to send handles across the pipe
4.3. Patch status
The Wine patch status has been moved to a separate page.
We've had a lot of luck - finding the Silverlight 5 issue by accident - and the help of other great people - a big thanks to Erich E. Hoover for his cooperation and Joachim Carlsen for testing and finding bugs! This allowed us to get this whole project finished in just two weeks. Of course such a project will never be finished completely as there might be some rare cases where Silverlight doesn't behave according to the specification (we already found several such cases) or uses some less-usual API command which is not implemented yet, but we are planning to extend this project step by step until it is suitable to fit most of the use-cases.
Until now we already have confirmed the following sites (VOD and other applications) to work almost perfectly using Silverlight 5.1 and Pipelight (ordered by language):
- multiple languages
- Magister (used for school websites in the Netherlands)
- Yelo TV
- and many more…
The following pages only work with Silverlight 5.0 - its not a big deal to downgrade but you should note that older versions probably contain some security issues when using them on untrusted sites. For some distributions there are detailed instructions available how to do that: Ubuntu, …
- multiple languages
Of course this list is far from being complete - it will be extended when we get some feedback of other users. If you give Pipelight a try please share your opinion and tell us what you think about it! You can either comment directly in this blog or ask a question / fill a bug at Launchpad. If you have a site which works with Pipelight and is not included in the above list, please drop us a comment. Even if you find a site which doesn't work just contact us and we will try to find out whats going wrong.