{"id":77,"date":"2011-09-02T00:03:28","date_gmt":"2011-09-01T22:03:28","guid":{"rendered":"https:\/\/blogs.gentoo.org\/mgorny\/?p=77"},"modified":"2011-09-02T00:30:44","modified_gmt":"2011-09-01T22:30:44","slug":"building-mozilla-plugins-without-mozilla","status":"publish","type":"post","link":"https:\/\/blogs.gentoo.org\/mgorny\/2011\/09\/02\/building-mozilla-plugins-without-mozilla\/","title":{"rendered":"Building Mozilla plugins without Mozilla"},"content":{"rendered":"<p>As of Firefox 6.0, Mozilla no longer supports building it against shared xulrunner. You may or may not already noticed that. For some users, this simply means that your next <code>--depclean<\/code> will unmerge last install of xulrunner. For some others, this means you will be building two copies of the same thing \u2014 one for Firefox, and the other for a few packages depending on xulrunner.<\/p>\n<p>One especially painful case here are browser plugins. Right now, their ebuilds mostly depend on the whole xulrunner being built while that&#8217;s not exactly true for the packages itself. In fact, building Netscape plugins requires only headers to exist \u2014 no linkage is necessary, all necessary symbols are provided by the browser itself (and if they aren&#8217;t, the plugin probably won&#8217;t work anyway).<\/p>\n<p>For all that, I really don&#8217;t see a reason to waste like 1 hour compiling an awfully large package just to use its headers for a few minutes and then have no real use for it. That&#8217;s why I decided to try establishing a tiny package containing headers and pkg-config files necessary to build plugins.<\/p>\n<h2>How packages build Mozilla plugins?<\/h2>\n<p>Most of browser plugins are actually clear NPAPI plugins. In simplest words that means that they need four standard, well-established <code>np*<\/code> headers to be built. These could be found, for example, in the <a rel=\"external\" href=\"http:\/\/code.google.com\/p\/npapi-sdk\/\">npapi-sdk<\/a> package.<\/p>\n<p>And in fact, some projects actually bundle that four headers. That&#8217;s the best case because it means that a particular plugin has no xulrunner\/mozilla dependency. It just builds the plugin against bundled headers and we don&#8217;t have to worry about supplying them to it.<\/p>\n<p>When packages rely on external NPAPI headers, the pain begins. All these years, Mozilla upstream didn&#8217;t really establish a clear way of finding them. Each package has its own autoconf for it, less or more complex, and less or more wrong.<\/p>\n<p>A good example here is <a rel=\"external\" href=\"http:\/\/www.videolan.org\/\">VLC<\/a>. It provides a quite painless method looking either for <code>libxul<\/code> or one of <code>*-plugin<\/code> pkg-config packages. Not sure, however, if most of names used there really existed but <code>mozilla-plugin<\/code> is the one most commonly used.<\/p>\n<p>Either way, that test always nicely succeeds with xulrunner and lets VLC find its headers. If we establishing a tiny NPAPI header package, and just use <code>mozilla-plugin<\/code> pkg-config file in it, VLC will build fine against it. Sadly, if <code>libxul<\/code> is in the system, VLC will use it and link the plugin with it \u2014 for no reason.<\/p>\n<p><a rel=\"external\" href=\"http:\/\/www.gnu.org\/software\/gnash\/\">gnash<\/a> is another good example here. Although the code may look a little scary, it uses <code>mozilla-plugin<\/code> pkg-config and doesn&#8217;t link against anything.<\/p>\n<p>On the other hand, <a rel=\"external\" href=\"http:\/\/code.google.com\/p\/gecko-mediaplayer\/\">gecko-mediaplayer<\/a> is an awful example here. It&#8217;s using a lot of random pkg-config checks, and relies on features based on xulrunner pkg-config version. Mostly impossible to handle clearly; we need to inject additional, hacky pkg-config file to satisfy their checks \u2014 probably for no good reason.<\/p>\n<p><a rel=\"external\" href=\"http:\/\/icedtea.classpath.org\">IcedTea-web<\/a> is a totally different case here. Unlike packages mentioned before, this one uses a larger set of xulrunner headers; though still requires no linkage. After building it against a number of xulrunner headers, the plugin works fine in <a rel=\"external\" href=\"http:\/\/www.opera.com\/\">Opera<\/a>.<\/p>\n<h2>Creating the header package<\/h2>\n<p>Considering the above, a simple npapi-sdk package is not enough. We at least need to install <code>mozilla-plugin.pc<\/code>; installing <code>libxul.pc<\/code> satisfies configure checks on more packages but breaks VLC (as it tries to link with non-existent xulrunner libraries). If we hack the latter and remove <code>Libs:<\/code> from it, VLC builds fine.<\/p>\n<p>Right now, I&#8217;m testing a simple <a rel=\"external\" href=\"http:\/\/git.overlays.gentoo.org\/gitweb\/?p=dev\/mgorny.git;a=tree;f=net-misc\/mozilla-plugin-sdk\">mozilla-plugin-sdk<\/a> package. It installs the complete set of xulrunner headers along with the two forementioned pkg-config files, satisfying all Mozilla plugins I&#8217;ve tried. Sadly, due to number of headers the package is awfully large.<\/p>\n<p>The next step would be probably stripping unnecessary headers out of the package. I already started using <code>makedepend<\/code> to check which headers are actually used by Netscape plugins. Any further tips would be appreciated.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>As of Firefox 6.0, Mozilla no longer supports building it against shared xulrunner. You may or may not already noticed that. For some users, this simply means that your next &#8211;depclean will unmerge last install of xulrunner. For some others, this means you will be building two copies of the same thing \u2014 one for &hellip; <a href=\"https:\/\/blogs.gentoo.org\/mgorny\/2011\/09\/02\/building-mozilla-plugins-without-mozilla\/\" class=\"more-link\">Continue reading<span class=\"screen-reader-text\"> &#8220;Building Mozilla plugins without Mozilla&#8221;<\/span><\/a><\/p>\n","protected":false},"author":137,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"jetpack_publicize_message":"","jetpack_is_tweetstorm":false,"jetpack_publicize_feature_enabled":true},"categories":[1],"tags":[],"jetpack_publicize_connections":[],"jetpack_featured_media_url":"","_links":{"self":[{"href":"https:\/\/blogs.gentoo.org\/mgorny\/wp-json\/wp\/v2\/posts\/77"}],"collection":[{"href":"https:\/\/blogs.gentoo.org\/mgorny\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blogs.gentoo.org\/mgorny\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blogs.gentoo.org\/mgorny\/wp-json\/wp\/v2\/users\/137"}],"replies":[{"embeddable":true,"href":"https:\/\/blogs.gentoo.org\/mgorny\/wp-json\/wp\/v2\/comments?post=77"}],"version-history":[{"count":3,"href":"https:\/\/blogs.gentoo.org\/mgorny\/wp-json\/wp\/v2\/posts\/77\/revisions"}],"predecessor-version":[{"id":80,"href":"https:\/\/blogs.gentoo.org\/mgorny\/wp-json\/wp\/v2\/posts\/77\/revisions\/80"}],"wp:attachment":[{"href":"https:\/\/blogs.gentoo.org\/mgorny\/wp-json\/wp\/v2\/media?parent=77"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blogs.gentoo.org\/mgorny\/wp-json\/wp\/v2\/categories?post=77"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blogs.gentoo.org\/mgorny\/wp-json\/wp\/v2\/tags?post=77"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}