summarylogtreecommitdiffstats
diff options
context:
space:
mode:
authorfrancoism902021-10-23 20:11:17 +0200
committerfrancoism902021-10-23 20:11:17 +0200
commiteb697dedfb8a97728bf76ab4ab5a1dc9b4b037c6 (patch)
treeab3c88ed1c21dbd18158c884e036caff2ccb0283
downloadaur-eb697dedfb8a97728bf76ab4ab5a1dc9b4b037c6.tar.gz
Initial commit
-rw-r--r--.SRCINFO106
-rw-r--r--0001-Use-remoting-name-for-GDK-application-names.patch57
-rw-r--r--0002-Add-missing-default-scheme.patch14
-rw-r--r--PKGBUILD297
-rw-r--r--firefox-branded-icons.patch50
-rw-r--r--firefox-developer-edition.desktop340
-rw-r--r--firefox-install-dir.patch43
-rw-r--r--firefox-kde.patch282
-rw-r--r--identity-icons-brand.svg3
-rw-r--r--mozilla-bmo1005535.patch30
-rw-r--r--mozilla-bmo1504834-part1.patch121
-rw-r--r--mozilla-bmo1504834-part2.patch112
-rw-r--r--mozilla-bmo1504834-part3.patch64
-rw-r--r--mozilla-bmo1504834-part4.patch40
-rw-r--r--mozilla-bmo1626236.patch85
-rw-r--r--mozilla-bmo531915.patch29
-rw-r--r--mozilla-bmo849632.patch35
-rw-r--r--mozilla-bmo998749.patch29
-rw-r--r--mozilla-fix-top-level-asm.patch66
-rw-r--r--mozilla-kde.patch1931
-rw-r--r--mozilla-nongnome-proxies.patch44
-rw-r--r--mozilla-ntlm-full-path.patch28
-rw-r--r--mozilla-sandbox-fips.patch40
23 files changed, 3846 insertions, 0 deletions
diff --git a/.SRCINFO b/.SRCINFO
new file mode 100644
index 000000000000..2d0b8a18cac9
--- /dev/null
+++ b/.SRCINFO
@@ -0,0 +1,106 @@
+pkgbase = firefox-developer-edition-kde
+ pkgdesc = Developer Edition of the popular Firefox web browser.
+ pkgver = 94.0b9
+ pkgrel = 1
+ url = https://www.mozilla.org/firefox/channel/#developer
+ arch = x86_64
+ license = MPL
+ license = GPL
+ license = LGPL
+ makedepends = unzip
+ makedepends = zip
+ makedepends = diffutils
+ makedepends = python-setuptools
+ makedepends = yasm
+ makedepends = mesa
+ makedepends = imake
+ makedepends = inetutils
+ makedepends = xorg-server-xvfb
+ makedepends = libpulse
+ makedepends = inetutils
+ makedepends = autoconf2.13
+ makedepends = rust
+ makedepends = clang
+ makedepends = llvm
+ makedepends = jack
+ makedepends = nodejs
+ makedepends = cargo
+ makedepends = mercurial
+ makedepends = llvm
+ makedepends = python-psutil
+ makedepends = cbindgen
+ makedepends = nasm
+ makedepends = lld
+ makedepends = python-zstandard
+ makedepends = dump_syms
+ depends = gtk3
+ depends = libxt
+ depends = mime-types
+ depends = dbus-glib
+ depends = ffmpeg
+ depends = ttf-font
+ depends = libpulse
+ depends = nss
+ depends = hicolor-icon-theme
+ depends = kmozillahelper
+ depends = nspr
+ depends = hunspell
+ optdepends = networkmanager: Location detection via available WiFi networks
+ optdepends = libnotify: Notification integration
+ optdepends = pulseaudio: Audio support
+ optdepends = speech-dispatcher: Text-to-Speech
+ optdepends = hunspell-en_US: Spell checking, American English
+ provides = firefox-developer-edition
+ conflicts = firefox-developer-edition
+ options = !emptydirs
+ options = !makeflags
+ options = !strip
+ source = https://archive.mozilla.org/pub/firefox/releases/94.0b9/source/firefox-94.0b9.source.tar.xz
+ source = https://archive.mozilla.org/pub/firefox/releases/94.0b9/source/firefox-94.0b9.source.tar.xz.asc
+ source = firefox-install-dir.patch
+ source = 0001-Use-remoting-name-for-GDK-application-names.patch
+ source = 0002-Add-missing-default-scheme.patch
+ source = firefox-developer-edition.desktop
+ source = identity-icons-brand.svg
+ source = mozilla-nongnome-proxies.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-nongnome-proxies.patch
+ source = mozilla-kde.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-kde.patch
+ source = mozilla-ntlm-full-path.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-ntlm-full-path.patch
+ source = mozilla-sandbox-fips.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-sandbox-fips.patch
+ source = mozilla-bmo1005535.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-bmo1005535.patch
+ source = mozilla-bmo1504834-part1.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-bmo1504834-part1.patch
+ source = mozilla-bmo1504834-part2.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-bmo1504834-part2.patch
+ source = mozilla-bmo1504834-part3.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-bmo1504834-part3.patch
+ source = mozilla-bmo1504834-part4.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-bmo1504834-part4.patch
+ source = mozilla-fix-top-level-asm.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-fix-top-level-asm.patch
+ source = mozilla-bmo849632.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-bmo849632.patch
+ source = mozilla-bmo998749.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-bmo998749.patch
+ source = mozilla-bmo1626236.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-bmo1626236.patch
+ source = mozilla-bmo531915.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/mozilla-bmo531915.patch
+ source = firefox-branded-icons.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/firefox/firefox-branded-icons.patch
+ source = firefox-kde.patch::https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master/firefox/firefox-kde.patch
+ validpgpkeys = 14F26682D0916CDD81E37B6D61B7B526D98F0353
+ sha512sums = 3a752f0ef8816427dddbe64f26c16da12fa430dfbc94bf44945d54fd0d581a5191d8a8f0e6aaf0e078697b71b6badc386276af27c8282dcea408bc011851404c
+ sha512sums = SKIP
+ sha512sums = b66dbe7f262d036e5a5b895ab5b0dbb03313bca18b0823c001ef2dbaeb1a33169b57db0cf4dfd268499f28913845119902b5d62e8a6a9cc4820eb0ee2f322a1e
+ sha512sums = 624a2531b4b85b1ad2286f0a6529313d9ae8a543b9f799a1f06d564db003f126e7bb3b5a35c6ab2f28d0e495a399d97476df8436914ba637cf627b52c3ab6f8d
+ sha512sums = 2a46f450fa230b964bc105087d578574bebccc18c337d89860740caeb00ea798c69edc70b256d87437dc4e791d1d223dbb1b70531c32333d6b23fa3550d1d941
+ sha512sums = 96d56ed8d14dd16cd44df5dc156d81a4426280cdd8bd61e71831b7555c4d4a256fca523ce53852f6f98a546bf20d92b9c63aeeaff7a06174b8da7a8028394397
+ sha512sums = b579b73176c72a5ecf36e3f63bba08fdb8041ae99d54e5cab906660fed6a9cf2311f7ca1ec1649e451cc6d5a4b1e6060b974b1d7befe9c8df3c5a89c50383c17
+ sha512sums = dcdaba2b51f8e7dc4fbfeb7c707581a136d8727a64352fb09f40e62c1bba03f66d4770d21bd9ea0b9a249314fd4ce273bb42efb7108db39bbbadf1d0ddb8e3aa
+ sha512sums = 70e0098da963540eb685184bf24e32c4b7ecb28a373d6c1792961bf3142f964af247c94774be0ae1e014c9e43bf4aee439cb45dcf882ad234bdb00709b3e71d9
+ sha512sums = a8d1da2d85cd59c9254cd10800957eebb2e60818968739c9711d53d651a72b7a895b3cf973e24c019ec996a1ad7e2f3e28448e4e3a43761ee00b53284274e400
+ sha512sums = 4716b5e450231ba375c26177a8983c8689054df0e8889488455bb1e045ec584f7bf7b7d0779c49fca43e2a05bcf25391dc7f825fadaa1079b283d9679083854f
+ sha512sums = c46a5e05a7cfa6acceae7b3474b5fa26727b32369b1bbd93fcdb0bd3aa2b42192b7ce4ba540ecc1011317024f8005b264fa85273385e15e89c93c489f7da3c03
+ sha512sums = c84d412df15a8aeaad41000f591e504bfef054614daff3246f292be59ce3b25e724149a94bdead5bcae5f1704c7e7c987b8130fa38f8dac0df466bdc8b9bb0e2
+ sha512sums = 7158ddd53b0e25e534f3df762d607c83f4e3e19385758534adcd1e3fc514d689373048fac878b8e27701bfc863ba6a52860d5dfb64902ec8ce59af427e7fb6c6
+ sha512sums = 4c9df14609e16ece6cbfd321b1242e6fc4377341ea269ec68aa2747c34cc2c40e38f342bdee1f1f5a4d4c6da62233706ec3ed677bcfafdcebe94200ff71e24fd
+ sha512sums = aa3f0d0e2603d32722ba59700efdc4e618fe3ba15f4a2ecb3c63b28dc892138dbc1427b04e9f9749ff5009ca935c70d7c6cefe5b0ad6b121b82f5cf07ea45086
+ sha512sums = 31738b0d7c2ae0fbdc567e84d24774e057bc0257af66e3c08a6386828051d3df4fc7aaacf71aee5a7badfa0734a8999ce1a002e639b1cf35e576b1d889edcfea
+ sha512sums = 6b9e3589a7359499cf197556c00ee32193ee32b8bfb0d8811511d05105e89e107c8c0b3543a96b0234b0893c260ba6e07de23da67493505a846baf42d59cfd6e
+ sha512sums = 3216e96e7cd1624945595f016fbe76a699d8627c60250768857c74c2453e66e3cc9207bfbf486ea1be5685b595bf1ae4626401502f723e94320c42c7b12d0785
+ sha512sums = 773be00a1aea29527e8556b152f463e477f025785e2ca98ca12804b3a5783444bdf4f6d6765b167f64dce3110b91af5efed58c1744d35b2da187d1b4eac8ed59
+ sha512sums = 7c149f99541fb9d6f67a17987ce1ef4456799ac8ad7dc9d963b7a3435f024892014e8c577e7ee79735cbcaff9b67328d4c0e22c73adebf1052102cbcc95c85a8
+ sha512sums = 29eb82ff71385b299b2f1baefbb32c5add484117315245ca21d5d521ec9281d08023753d3daff731ecf93df83f9f1e945cd04a3320f0e05c0d675afbcab6ecc3
+ sha512sums = 4c4c6cdc86da0a7e335526df763379e24af2caa282b25d6ea32dbbc6af6c499177b1f4ae87b2f010e38be812c2529e79ac47abc692774e19af117ccbe9a5bbb1
+
+pkgname = firefox-developer-edition-kde
diff --git a/0001-Use-remoting-name-for-GDK-application-names.patch b/0001-Use-remoting-name-for-GDK-application-names.patch
new file mode 100644
index 000000000000..c1feb3fc8081
--- /dev/null
+++ b/0001-Use-remoting-name-for-GDK-application-names.patch
@@ -0,0 +1,57 @@
+From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
+From: "Jan Alexander Steffens (heftig)" <jan.steffens@gmail.com>
+Date: Mon, 25 Mar 2019 20:30:11 +0100
+Subject: [PATCH] Use remoting name for GDK application names
+
+---
+ toolkit/xre/nsAppRunner.cpp | 6 +-----
+ widget/gtk/nsAppShell.cpp | 12 +++++-------
+ 2 files changed, 6 insertions(+), 12 deletions(-)
+
+diff --git a/toolkit/xre/nsAppRunner.cpp b/toolkit/xre/nsAppRunner.cpp
+index bb14d84338334..f5c0222987fb0 100644
+--- a/toolkit/xre/nsAppRunner.cpp
++++ b/toolkit/xre/nsAppRunner.cpp
+@@ -4299,11 +4299,7 @@ int XREMain::XRE_mainStartup(bool* aExitFlag) {
+ // consistently.
+
+ // Set program name to the one defined in application.ini.
+- {
+- nsAutoCString program(gAppData->name);
+- ToLowerCase(program);
+- g_set_prgname(program.get());
+- }
++ g_set_prgname(gAppData->remotingName);
+
+ // Initialize GTK here for splash.
+
+diff --git a/widget/gtk/nsAppShell.cpp b/widget/gtk/nsAppShell.cpp
+index 60de473de07ab..004c066575c17 100644
+--- a/widget/gtk/nsAppShell.cpp
++++ b/widget/gtk/nsAppShell.cpp
+@@ -24,6 +24,8 @@
+ # include "WakeLockListener.h"
+ #endif
+ #include "gfxPlatform.h"
++#include "nsAppRunner.h"
++#include "mozilla/XREAppData.h"
+ #include "ScreenHelperGTK.h"
+ #include "HeadlessScreenHelper.h"
+ #include "mozilla/widget/ScreenManager.h"
+@@ -152,13 +154,9 @@ nsresult nsAppShell::Init() {
+ // See https://bugzilla.gnome.org/show_bug.cgi?id=747634
+ //
+ // Only bother doing this for the parent process, since it's the one
+- // creating top-level windows. (At this point, a child process hasn't
+- // received the list of registered chrome packages, so the
+- // GetBrandShortName call would fail anyway.)
+- nsAutoString brandName;
+- mozilla::widget::WidgetUtils::GetBrandShortName(brandName);
+- if (!brandName.IsEmpty()) {
+- gdk_set_program_class(NS_ConvertUTF16toUTF8(brandName).get());
++ // creating top-level windows.
++ if (gAppData) {
++ gdk_set_program_class(gAppData->remotingName);
+ }
+ }
+ }
diff --git a/0002-Add-missing-default-scheme.patch b/0002-Add-missing-default-scheme.patch
new file mode 100644
index 000000000000..ce3c400ffa6a
--- /dev/null
+++ b/0002-Add-missing-default-scheme.patch
@@ -0,0 +1,14 @@
+--- a/browser/components/shell/nsKDEShellService.cpp
++++ b/browser/components/shell/nsKDEShellService.cpp
+@@ -101,3 +101,11 @@
+ return NS_ERROR_NOT_IMPLEMENTED;
+ }
+
++
++NS_IMETHODIMP
++nsKDEShellService::IsDefaultForScheme(nsTSubstring<char> const& aScheme,
++ bool* aIsDefaultBrowser)
++{
++ return NS_ERROR_NOT_IMPLEMENTED;
++}
++
diff --git a/PKGBUILD b/PKGBUILD
new file mode 100644
index 000000000000..d2108c005b61
--- /dev/null
+++ b/PKGBUILD
@@ -0,0 +1,297 @@
+# Maintainer: Francois Menning <f.menning@pm.me>
+# Contributor: Andrew Crerar <crerar@archlinux.org>
+# Contributor: Jan Alexander Steffens (heftig) <heftig@archlinux.org>
+# Contributor: Thaodan <theodorstormgrade@gmail.com>
+# Contributor: Weng Xuetian <wengxt@gmail.com>
+
+_pkgname=firefox-developer-edition
+_patchurl=https://raw.githubusercontent.com/openSUSE/firefox-maintenance/master
+
+pkgname=firefox-developer-edition-kde
+pkgver=94.0b9
+pkgrel=1
+pkgdesc="Developer Edition of the popular Firefox web browser."
+arch=('x86_64')
+license=('MPL' 'GPL' 'LGPL')
+url="https://www.mozilla.org/firefox/channel/#developer"
+depends=('gtk3' 'libxt' 'mime-types' 'dbus-glib' 'ffmpeg' 'ttf-font' 'libpulse' 'nss'
+ 'hicolor-icon-theme' 'kmozillahelper' 'nspr' 'hunspell')
+makedepends=('unzip' 'zip' 'diffutils' 'python-setuptools' 'yasm' 'mesa' 'imake' 'inetutils'
+ 'xorg-server-xvfb' 'libpulse' 'inetutils' 'autoconf2.13' 'rust' 'clang' 'llvm' 'jack' 'nodejs'
+ 'cargo' 'mercurial' 'llvm' 'python-psutil' 'cbindgen' 'nasm' 'lld' 'python-zstandard' 'dump_syms')
+optdepends=('networkmanager: Location detection via available WiFi networks'
+ 'libnotify: Notification integration'
+ 'pulseaudio: Audio support'
+ 'speech-dispatcher: Text-to-Speech'
+ 'hunspell-en_US: Spell checking, American English')
+conflicts=('firefox-developer-edition')
+provides=('firefox-developer-edition')
+options=(!emptydirs !makeflags !strip)
+source=(https://archive.mozilla.org/pub/firefox/releases/$pkgver/source/firefox-$pkgver.source.tar.xz{,.asc}
+ firefox-install-dir.patch
+ 0001-Use-remoting-name-for-GDK-application-names.patch
+ 0002-Add-missing-default-scheme.patch
+ "$_pkgname".desktop
+ identity-icons-brand.svg
+ # https://github.com/openSUSE/firefox-maintenance
+ mozilla-nongnome-proxies.patch::$_patchurl/mozilla-nongnome-proxies.patch
+ mozilla-kde.patch::$_patchurl/mozilla-kde.patch
+ mozilla-ntlm-full-path.patch::$_patchurl/mozilla-ntlm-full-path.patch
+ mozilla-sandbox-fips.patch::$_patchurl/mozilla-sandbox-fips.patch
+ mozilla-bmo1005535.patch::$_patchurl/mozilla-bmo1005535.patch
+ mozilla-bmo1504834-part1.patch::$_patchurl/mozilla-bmo1504834-part1.patch
+ mozilla-bmo1504834-part2.patch::$_patchurl/mozilla-bmo1504834-part2.patch
+ mozilla-bmo1504834-part3.patch::$_patchurl/mozilla-bmo1504834-part3.patch
+ mozilla-bmo1504834-part4.patch::$_patchurl/mozilla-bmo1504834-part4.patch
+ mozilla-fix-top-level-asm.patch::$_patchurl/mozilla-fix-top-level-asm.patch
+ mozilla-bmo849632.patch::$_patchurl/mozilla-bmo849632.patch
+ mozilla-bmo998749.patch::$_patchurl/mozilla-bmo998749.patch
+ mozilla-bmo1626236.patch::$_patchurl/mozilla-bmo1626236.patch
+ mozilla-bmo531915.patch::$_patchurl/mozilla-bmo531915.patch
+ firefox-branded-icons.patch::$_patchurl/firefox/firefox-branded-icons.patch
+ firefox-kde.patch::$_patchurl/firefox/firefox-kde.patch
+)
+sha512sums=('3a752f0ef8816427dddbe64f26c16da12fa430dfbc94bf44945d54fd0d581a5191d8a8f0e6aaf0e078697b71b6badc386276af27c8282dcea408bc011851404c'
+ 'SKIP'
+ 'b66dbe7f262d036e5a5b895ab5b0dbb03313bca18b0823c001ef2dbaeb1a33169b57db0cf4dfd268499f28913845119902b5d62e8a6a9cc4820eb0ee2f322a1e'
+ '624a2531b4b85b1ad2286f0a6529313d9ae8a543b9f799a1f06d564db003f126e7bb3b5a35c6ab2f28d0e495a399d97476df8436914ba637cf627b52c3ab6f8d'
+ '2a46f450fa230b964bc105087d578574bebccc18c337d89860740caeb00ea798c69edc70b256d87437dc4e791d1d223dbb1b70531c32333d6b23fa3550d1d941'
+ '96d56ed8d14dd16cd44df5dc156d81a4426280cdd8bd61e71831b7555c4d4a256fca523ce53852f6f98a546bf20d92b9c63aeeaff7a06174b8da7a8028394397'
+ 'b579b73176c72a5ecf36e3f63bba08fdb8041ae99d54e5cab906660fed6a9cf2311f7ca1ec1649e451cc6d5a4b1e6060b974b1d7befe9c8df3c5a89c50383c17'
+ 'dcdaba2b51f8e7dc4fbfeb7c707581a136d8727a64352fb09f40e62c1bba03f66d4770d21bd9ea0b9a249314fd4ce273bb42efb7108db39bbbadf1d0ddb8e3aa'
+ '70e0098da963540eb685184bf24e32c4b7ecb28a373d6c1792961bf3142f964af247c94774be0ae1e014c9e43bf4aee439cb45dcf882ad234bdb00709b3e71d9'
+ 'a8d1da2d85cd59c9254cd10800957eebb2e60818968739c9711d53d651a72b7a895b3cf973e24c019ec996a1ad7e2f3e28448e4e3a43761ee00b53284274e400'
+ '4716b5e450231ba375c26177a8983c8689054df0e8889488455bb1e045ec584f7bf7b7d0779c49fca43e2a05bcf25391dc7f825fadaa1079b283d9679083854f'
+ 'c46a5e05a7cfa6acceae7b3474b5fa26727b32369b1bbd93fcdb0bd3aa2b42192b7ce4ba540ecc1011317024f8005b264fa85273385e15e89c93c489f7da3c03'
+ 'c84d412df15a8aeaad41000f591e504bfef054614daff3246f292be59ce3b25e724149a94bdead5bcae5f1704c7e7c987b8130fa38f8dac0df466bdc8b9bb0e2'
+ '7158ddd53b0e25e534f3df762d607c83f4e3e19385758534adcd1e3fc514d689373048fac878b8e27701bfc863ba6a52860d5dfb64902ec8ce59af427e7fb6c6'
+ '4c9df14609e16ece6cbfd321b1242e6fc4377341ea269ec68aa2747c34cc2c40e38f342bdee1f1f5a4d4c6da62233706ec3ed677bcfafdcebe94200ff71e24fd'
+ 'aa3f0d0e2603d32722ba59700efdc4e618fe3ba15f4a2ecb3c63b28dc892138dbc1427b04e9f9749ff5009ca935c70d7c6cefe5b0ad6b121b82f5cf07ea45086'
+ '31738b0d7c2ae0fbdc567e84d24774e057bc0257af66e3c08a6386828051d3df4fc7aaacf71aee5a7badfa0734a8999ce1a002e639b1cf35e576b1d889edcfea'
+ '6b9e3589a7359499cf197556c00ee32193ee32b8bfb0d8811511d05105e89e107c8c0b3543a96b0234b0893c260ba6e07de23da67493505a846baf42d59cfd6e'
+ '3216e96e7cd1624945595f016fbe76a699d8627c60250768857c74c2453e66e3cc9207bfbf486ea1be5685b595bf1ae4626401502f723e94320c42c7b12d0785'
+ '773be00a1aea29527e8556b152f463e477f025785e2ca98ca12804b3a5783444bdf4f6d6765b167f64dce3110b91af5efed58c1744d35b2da187d1b4eac8ed59'
+ '7c149f99541fb9d6f67a17987ce1ef4456799ac8ad7dc9d963b7a3435f024892014e8c577e7ee79735cbcaff9b67328d4c0e22c73adebf1052102cbcc95c85a8'
+ '29eb82ff71385b299b2f1baefbb32c5add484117315245ca21d5d521ec9281d08023753d3daff731ecf93df83f9f1e945cd04a3320f0e05c0d675afbcab6ecc3'
+ '4c4c6cdc86da0a7e335526df763379e24af2caa282b25d6ea32dbbc6af6c499177b1f4ae87b2f010e38be812c2529e79ac47abc692774e19af117ccbe9a5bbb1')
+validpgpkeys=('14F26682D0916CDD81E37B6D61B7B526D98F0353') # Mozilla Software Releases <release@mozilla.com>
+
+# Google API keys (see http://www.chromium.org/developers/how-tos/api-keys)
+# Note: These are for Arch Linux use ONLY. For your own distribution, please
+# get your own set of keys. Feel free to contact foutrelis@archlinux.org for
+# more information.
+_google_api_key=AIzaSyDwr302FpOSkGRpLlUpPThNTDPbXcIn_FM
+
+# Mozilla API keys (see https://location.services.mozilla.com/api)
+# Note: These are for Arch Linux use ONLY. For your own distribution, please
+# get your own set of keys. Feel free to contact heftig@archlinux.org for
+# more information.
+_mozilla_api_key=e05d56db0a694edc8b5aaebda3f2db6a
+
+prepare() {
+ mkdir mozbuild
+ cd firefox-${pkgver%b*}
+
+ # Install location
+ patch -Np1 -i ../firefox-install-dir.patch
+
+ # https://bugzilla.mozilla.org/show_bug.cgi?id=1530052
+ patch -Np1 -i ../0001-Use-remoting-name-for-GDK-application-names.patch
+
+ # https://github.com/openSUSE/firefox-maintenance/blob/master/firefox/MozillaFirefox.spec
+ # Gecko/Toolkit
+ patch -Np1 -i ../mozilla-nongnome-proxies.patch
+ patch -Np1 -i ../mozilla-kde.patch
+ patch -Np1 -i ../mozilla-ntlm-full-path.patch
+ patch -Np1 -i ../mozilla-sandbox-fips.patch
+ patch -Np1 -i ../mozilla-bmo1005535.patch
+ patch -Np1 -i ../mozilla-bmo1504834-part1.patch
+ patch -Np1 -i ../mozilla-bmo1504834-part2.patch
+ patch -Np1 -i ../mozilla-bmo1504834-part3.patch
+ patch -Np1 -i ../mozilla-bmo1504834-part4.patch
+ patch -Np1 -i ../mozilla-fix-top-level-asm.patch
+ patch -Np1 -i ../mozilla-bmo849632.patch
+ patch -Np1 -i ../mozilla-bmo998749.patch
+ patch -Np1 -i ../mozilla-bmo1626236.patch
+ patch -Np1 -i ../mozilla-bmo531915.patch
+
+ # Firefox/browser
+ patch -Np1 -i ../firefox-kde.patch
+ patch -Np1 -i ../firefox-branded-icons.patch
+
+ # https://github.com/openSUSE/firefox-maintenance/issues/37
+ patch -Np1 -i ../0002-Add-missing-default-scheme.patch
+
+ echo -n "$_google_api_key" > google-api-key
+ echo -n "$_mozilla_api_key" > mozilla-api-key
+
+ cat > ../mozconfig << END
+ac_add_options --enable-application=browser
+mk_add_options MOZ_OBJDIR=${PWD@Q}/obj
+
+ac_add_options --prefix=/usr
+ac_add_options --enable-release
+ac_add_options --enable-hardening
+ac_add_options --enable-optimize
+ac_add_options --enable-rust-simd
+ac_add_options --enable-linker=lld
+ac_add_options --disable-elf-hack
+ac_add_options --disable-bootstrap
+# ac_add_options --with-ccache=sccache
+export CC='clang --target=x86_64-unknown-linux-gnu'
+export CXX='clang++ --target=x86_64-unknown-linux-gnu'
+export AR=llvm-ar
+export NM=llvm-nm
+export RANLIB=llvm-ranlib
+
+# Branding
+ac_add_options --enable-official-branding
+ac_add_options --with-branding=browser/branding/aurora
+ac_add_options --enable-update-channel=aurora
+ac_add_options --with-distribution-id=org.archlinux
+ac_add_options --with-unsigned-addon-scopes=app,system
+ac_add_options --allow-addon-sideload
+export MOZILLA_OFFICIAL=1
+export MOZ_APP_REMOTINGNAME=firefox-developer-edition
+export MOZ_TELEMETRY_REPORTING=1
+export MOZ_REQUIRE_SIGNING=
+
+# Keys
+ac_add_options --with-google-location-service-api-keyfile=${PWD@Q}/google-api-key
+ac_add_options --with-google-safebrowsing-api-keyfile=${PWD@Q}/google-api-key
+ac_add_options --with-mozilla-api-keyfile=${PWD@Q}/mozilla-api-key
+
+# System libraries
+ac_add_options --with-system-nspr
+ac_add_options --with-system-nss
+
+# Features
+# ac_add_options --enable-default-toolkit=cairo-gtk3
+ac_add_options --enable-default-toolkit=cairo-gtk3-wayland
+ac_add_options --enable-alsa
+ac_add_options --enable-jack
+ac_add_options --enable-crashreporter
+ac_add_options --disable-updater
+ac_add_options --disable-tests
+END
+}
+
+build() {
+ cd firefox-${pkgver%b*}
+
+ export MOZ_NOSPAM=1
+ export MOZBUILD_STATE_PATH="$srcdir/mozbuild"
+ export MACH_USE_SYSTEM_PYTHON=1
+ export MOZ_ENABLE_FULL_SYMBOLS=1
+
+ # LTO needs more open files
+ ulimit -n 4096
+
+ # Do 3-tier PGO
+ echo "Building instrumented browser..."
+ cat >.mozconfig ../mozconfig - <<END
+ac_add_options --enable-profile-generate=cross
+END
+ ./mach build
+
+ echo "Profiling instrumented browser..."
+ ./mach package
+ LLVM_PROFDATA=llvm-profdata \
+ JARLOG_FILE="$PWD/jarlog" \
+ xvfb-run -s "-screen 0 1920x1080x24 -nolisten local" \
+ ./mach python build/pgo/profileserver.py
+
+ stat -c "Profile data found (%s bytes)" merged.profdata
+ test -s merged.profdata
+
+ stat -c "Jar log found (%s bytes)" jarlog
+ test -s jarlog
+
+ echo "Removing instrumented browser..."
+ ./mach clobber
+
+ echo "Building optimized browser..."
+ cat >.mozconfig ../mozconfig - <<END
+ac_add_options --enable-lto=cross
+ac_add_options --enable-profile-use=cross
+ac_add_options --with-pgo-profile-path=${PWD@Q}/merged.profdata
+ac_add_options --with-pgo-jarlog=${PWD@Q}/jarlog
+END
+ ./mach build
+
+ echo "Building symbol archive..."
+ ./mach buildsymbols
+}
+
+package() {
+ cd firefox-${pkgver%b*}
+ DESTDIR="$pkgdir" ./mach install
+
+ local vendorjs="$pkgdir/usr/lib/$_pkgname/browser/defaults/preferences/vendor.js"
+ install -Dm644 /dev/stdin "$vendorjs" << END
+// Use LANG environment variable to choose locale.
+pref("intl.locale.requested", "");
+
+// Use system-provided dictionaries.
+pref("spellchecker.dictionary_path", "/usr/share/hunspell");
+
+// Disable default browser checking.
+pref("browser.shell.checkDefaultBrowser", false);
+
+// Don't disable our bundled extensions in the application directory.
+pref("extensions.autoDisableScopes", 11);
+END
+
+ local distini="$pkgdir/usr/lib/$_pkgname/distribution/distribution.ini"
+ install -Dm644 /dev/stdin "$distini" << END
+[Global]
+id=archlinux
+version=1.0
+about=Mozilla Firefox Developer Edition for Arch Linux
+
+[Preferences]
+app.distributor=archlinux
+app.distributor.channel=$_pkgname
+app.partner.archlinux=archlinux
+END
+
+ local i theme=aurora
+ for i in 16 22 24 32 48 64 128 256; do
+ install -Dm644 browser/branding/$theme/default$i.png \
+ "$pkgdir/usr/share/icons/hicolor/${i}x${i}/apps/$_pkgname.png"
+ done
+ install -Dvm644 browser/branding/$theme/content/about-logo.png \
+ "$pkgdir/usr/share/icons/hicolor/192x192/apps/$_pkgname.png"
+ install -Dvm644 browser/branding/$theme/content/about-logo@2x.png \
+ "$pkgdir/usr/share/icons/hicolor/384x384/apps/$_pkgname.png"
+ install -Dvm644 browser/branding/$theme/content/about-logo.svg \
+ "$pkgdir/usr/share/icons/hicolor/scalable/apps/$_pkgname.svg"
+ install -Dvm644 ../identity-icons-brand.svg \
+ "$pkgdir/usr/share/icons/hicolor/symbolic/apps/$_pkgname-symbolic.svg"
+
+ install -Dm644 ../$_pkgname.desktop \
+ "$pkgdir/usr/share/applications/$_pkgname.desktop"
+
+ # Install a wrapper to avoid confusion about binary path
+ install -Dm755 /dev/stdin "$pkgdir/usr/bin/$_pkgname" << END
+#!/bin/sh
+exec /usr/lib/$_pkgname/firefox "\$@"
+END
+
+ # Replace duplicate binary with wrapper
+ # https://bugzilla.mozilla.org/show_bug.cgi?id=658850
+ ln -srf "$pkgdir/usr/bin/$_pkgname" "$pkgdir/usr/lib/$_pkgname/firefox-bin"
+
+ # Use system certificates
+ local nssckbi="$pkgdir/usr/lib/$_pkgname/libnssckbi.so"
+ if [[ -e $nssckbi ]]; then
+ ln -srf "$pkgdir/usr/lib/libnssckbi.so" "$nssckbi"
+ fi
+
+ export SOCORRO_SYMBOL_UPLOAD_TOKEN_FILE="$startdir/.crash-stats-api.token"
+ if [[ -f $SOCORRO_SYMBOL_UPLOAD_TOKEN_FILE ]]; then
+ make -C obj uploadsymbols
+ else
+ cp -fvt "$startdir" obj/dist/*crashreporter-symbols-full.tar.zst
+ fi
+}
diff --git a/firefox-branded-icons.patch b/firefox-branded-icons.patch
new file mode 100644
index 000000000000..f5bd6e5da16f
--- /dev/null
+++ b/firefox-branded-icons.patch
@@ -0,0 +1,50 @@
+# HG changeset patch
+# Parent e0751ad74e835e80041a61ea00c2a63bf6fbe2de
+# Parent 30e1a232528000620a3874de06ea515e5ef8e77f
+
+diff --git a/browser/branding/branding-common.mozbuild b/browser/branding/branding-common.mozbuild
+--- a/browser/branding/branding-common.mozbuild
++++ b/browser/branding/branding-common.mozbuild
+@@ -22,12 +22,15 @@ def FirefoxBranding():
+ FINAL_TARGET_FILES.VisualElements += [
+ 'VisualElements_150.png',
+ 'VisualElements_70.png',
+ ]
+ elif CONFIG['MOZ_WIDGET_TOOLKIT'] == 'gtk':
+ FINAL_TARGET_FILES.chrome.icons.default += [
+ 'default128.png',
+ 'default16.png',
++ 'default22.png',
++ 'default24.png',
++ 'default256.png',
+ 'default32.png',
+ 'default48.png',
+ 'default64.png',
+ ]
+diff --git a/browser/installer/package-manifest.in b/browser/installer/package-manifest.in
+--- a/browser/installer/package-manifest.in
++++ b/browser/installer/package-manifest.in
+@@ -236,20 +236,23 @@
+ @RESPATH@/browser/chrome/browser@JAREXT@
+ @RESPATH@/browser/chrome/browser.manifest
+ @RESPATH@/chrome/pdfjs.manifest
+ @RESPATH@/chrome/pdfjs/*
+ @RESPATH@/chrome/toolkit@JAREXT@
+ @RESPATH@/chrome/toolkit.manifest
+ #ifdef MOZ_GTK
+ @RESPATH@/browser/chrome/icons/default/default16.png
++@RESPATH@/browser/chrome/icons/default/default22.png
++@RESPATH@/browser/chrome/icons/default/default24.png
+ @RESPATH@/browser/chrome/icons/default/default32.png
+ @RESPATH@/browser/chrome/icons/default/default48.png
+ @RESPATH@/browser/chrome/icons/default/default64.png
+ @RESPATH@/browser/chrome/icons/default/default128.png
++@RESPATH@/browser/chrome/icons/default/default256.png
+ #endif
+ @RESPATH@/browser/features/*
+
+ ; [DevTools Startup Files]
+ @RESPATH@/browser/chrome/devtools-startup@JAREXT@
+ @RESPATH@/browser/chrome/devtools-startup.manifest
+
+ ; DevTools
diff --git a/firefox-developer-edition.desktop b/firefox-developer-edition.desktop
new file mode 100644
index 000000000000..7378d3c84eee
--- /dev/null
+++ b/firefox-developer-edition.desktop
@@ -0,0 +1,340 @@
+[Desktop Entry]
+Version=1.0
+Name=Firefox Developer Edition
+GenericName=Web Browser
+GenericName[ar]=متصفح ويب
+GenericName[ast]=Restolador Web
+GenericName[bn]=ওয়েব ব্রাউজার
+GenericName[ca]=Navegador web
+GenericName[cs]=Webový prohlížeč
+GenericName[da]=Webbrowser
+GenericName[de]=Webbrowser
+GenericName[el]=Περιηγητής διαδικτύου
+GenericName[es]=Navegador web
+GenericName[et]=Veebibrauser
+GenericName[fa]=مرورگر اینترنتی
+GenericName[fi]=WWW-selain
+GenericName[fr]=Navigateur Web
+GenericName[gl]=Navegador Web
+GenericName[he]=דפדפן אינטרנט
+GenericName[hr]=Web preglednik
+GenericName[hu]=Webböngésző
+GenericName[it]=Browser web
+GenericName[ja]=ウェブ・ブラウザ
+GenericName[ko]=웹 브라우저
+GenericName[ku]=Geroka torê
+GenericName[lt]=Interneto naršyklė
+GenericName[nb]=Nettleser
+GenericName[nl]=Webbrowser
+GenericName[nn]=Nettlesar
+GenericName[no]=Nettleser
+GenericName[pl]=Przeglądarka WWW
+GenericName[pt]=Navegador Web
+GenericName[pt_BR]=Navegador Web
+GenericName[ro]=Navigator Internet
+GenericName[ru]=Веб-браузер
+GenericName[sk]=Internetový prehliadač
+GenericName[sl]=Spletni brskalnik
+GenericName[sv]=Webbläsare
+GenericName[tr]=Web Tarayıcı
+GenericName[ug]=توركۆرگۈ
+GenericName[uk]=Веб-браузер
+GenericName[vi]=Trình duyệt Web
+GenericName[zh_CN]=网络浏览器
+GenericName[zh_TW]=網路瀏覽器
+Comment=Browse the World Wide Web
+Comment[ar]=تصفح الشبكة العنكبوتية العالمية
+Comment[ast]=Restola pela Rede
+Comment[bn]=ইন্টারনেট ব্রাউজ করুন
+Comment[ca]=Navegueu per el web
+Comment[cs]=Prohlížení stránek World Wide Webu
+Comment[da]=Surf på internettet
+Comment[de]=Im Internet surfen
+Comment[el]=Μπορείτε να περιηγηθείτε στο διαδίκτυο (Web)
+Comment[es]=Navegue por la web
+Comment[et]=Lehitse veebi
+Comment[fa]=صفحات شبکه جهانی اینترنت را مرور نمایید
+Comment[fi]=Selaa Internetin WWW-sivuja
+Comment[fr]=Naviguer sur le Web
+Comment[gl]=Navegar pola rede
+Comment[he]=גלישה ברחבי האינטרנט
+Comment[hr]=Pretražite web
+Comment[hu]=A világháló böngészése
+Comment[it]=Esplora il web
+Comment[ja]=ウェブを閲覧します
+Comment[ko]=웹을 돌아 다닙니다
+Comment[ku]=Li torê bigere
+Comment[lt]=Naršykite internete
+Comment[nb]=Surf på nettet
+Comment[nl]=Verken het internet
+Comment[nn]=Surf på nettet
+Comment[no]=Surf på nettet
+Comment[pl]=Przeglądanie stron WWW
+Comment[pt]=Navegue na Internet
+Comment[pt_BR]=Navegue na Internet
+Comment[ro]=Navigați pe Internet
+Comment[ru]=Доступ в Интернет
+Comment[sk]=Prehliadanie internetu
+Comment[sl]=Brskajte po spletu
+Comment[sv]=Surfa på webben
+Comment[tr]=İnternet'te Gezinin
+Comment[ug]=دۇنيادىكى توربەتلەرنى كۆرگىلى بولىدۇ
+Comment[uk]=Перегляд сторінок Інтернету
+Comment[vi]=Để duyệt các trang web
+Comment[zh_CN]=浏览互联网
+Comment[zh_TW]=瀏覽網際網路
+Keywords=Internet;WWW;Browser;Web;Explorer
+Keywords[ar]=انترنت;إنترنت;متصفح;ويب;وب
+Keywords[ast]=Internet;WWW;Restolador;Web;Esplorador
+Keywords[ca]=Internet;WWW;Navegador;Web;Explorador;Explorer
+Keywords[cs]=Internet;WWW;Prohlížeč;Web;Explorer
+Keywords[da]=Internet;Internettet;WWW;Browser;Browse;Web;Surf;Nettet
+Keywords[de]=Internet;WWW;Browser;Web;Explorer;Webseite;Site;surfen;online;browsen
+Keywords[el]=Internet;WWW;Browser;Web;Explorer;Διαδίκτυο;Περιηγητής;Firefox;Φιρεφοχ;Ιντερνετ
+Keywords[es]=Explorador;Internet;WWW
+Keywords[fi]=Internet;WWW;Browser;Web;Explorer;selain;Internet-selain;internetselain;verkkoselain;netti;surffaa
+Keywords[fr]=Internet;WWW;Browser;Web;Explorer;Fureteur;Surfer;Navigateur
+Keywords[he]=דפדפן;אינטרנט;רשת;אתרים;אתר;פיירפוקס;מוזילה;
+Keywords[hr]=Internet;WWW;preglednik;Web
+Keywords[hu]=Internet;WWW;Böngésző;Web;Háló;Net;Explorer
+Keywords[it]=Internet;WWW;Browser;Web;Navigatore
+Keywords[is]=Internet;WWW;Vafri;Vefur;Netvafri;Flakk
+Keywords[ja]=Internet;WWW;Web;インターネット;ブラウザ;ウェブ;エクスプローラ
+Keywords[nb]=Internett;WWW;Nettleser;Explorer;Web;Browser;Nettside
+Keywords[nl]=Internet;WWW;Browser;Web;Explorer;Verkenner;Website;Surfen;Online
+Keywords[pt]=Internet;WWW;Browser;Web;Explorador;Navegador
+Keywords[pt_BR]=Internet;WWW;Browser;Web;Explorador;Navegador
+Keywords[ru]=Internet;WWW;Browser;Web;Explorer;интернет;браузер;веб;файрфокс;огнелис
+Keywords[sk]=Internet;WWW;Prehliadač;Web;Explorer
+Keywords[sl]=Internet;WWW;Browser;Web;Explorer;Brskalnik;Splet
+Keywords[tr]=İnternet;WWW;Tarayıcı;Web;Gezgin;Web sitesi;Site;sörf;çevrimiçi;tara
+Keywords[uk]=Internet;WWW;Browser;Web;Explorer;Інтернет;мережа;переглядач;оглядач;браузер;веб;файрфокс;вогнелис;перегляд
+Keywords[vi]=Internet;WWW;Browser;Web;Explorer;Trình duyệt;Trang web
+Keywords[zh_CN]=Internet;WWW;Browser;Web;Explorer;网页;浏览;上网;火狐;Firefox;ff;互联网;网站;
+Keywords[zh_TW]=Internet;WWW;Browser;Web;Explorer;網際網路;網路;瀏覽器;上網;網頁;火狐
+Exec=/usr/lib/firefox-developer-edition/firefox --class="firefox-developer-edition" %u
+Icon=firefox-developer-edition
+Terminal=false
+X-MultipleArgs=false
+Type=Application
+MimeType=text/html;text/xml;application/xhtml+xml;x-scheme-handler/http;x-scheme-handler/https;application/x-xpinstall;application/pdf;application/json;
+StartupNotify=true
+StartupWMClass=firefox-developer-edition
+Categories=Network;WebBrowser;
+Actions=new-window;new-private-window;
+
+[Desktop Action new-window]
+Name=New Window
+Name[ach]=Dirica manyen
+Name[af]=Nuwe venster
+Name[an]=Nueva finestra
+Name[ar]=نافذة جديدة
+Name[as]=নতুন উইন্ডো
+Name[ast]=Ventana nueva
+Name[az]=Yeni Pəncərə
+Name[be]=Новае акно
+Name[bg]=Нов прозорец
+Name[bn_BD]=নতুন উইন্ডো (N)
+Name[bn_IN]=নতুন উইন্ডো
+Name[br]=Prenestr nevez
+Name[brx]=गोदान उइन्ड'(N)
+Name[bs]=Novi prozor
+Name[ca]=Finestra nova
+Name[cak]=K'ak'a' tzuwäch
+Name[cs]=Nové okno
+Name[cy]=Ffenestr Newydd
+Name[da]=Nyt vindue
+Name[de]=Neues Fenster
+Name[dsb]=Nowe wokno
+Name[el]=Νέο παράθυρο
+Name[en_GB]=New Window
+Name[en_US]=New Window
+Name[en_ZA]=New Window
+Name[eo]=Nova fenestro
+Name[es_AR]=Nueva ventana
+Name[es_CL]=Nueva ventana
+Name[es_ES]=Nueva ventana
+Name[es_MX]=Nueva ventana
+Name[et]=Uus aken
+Name[eu]=Leiho berria
+Name[fa]=پنجره جدید
+Name[ff]=Henorde Hesere
+Name[fi]=Uusi ikkuna
+Name[fr]=Nouvelle fenêtre
+Name[fy_NL]=Nij finster
+Name[ga_IE]=Fuinneog Nua
+Name[gd]=Uinneag ùr
+Name[gl]=Nova xanela
+Name[gn]=Ovetã pyahu
+Name[gu_IN]=નવી વિન્ડો
+Name[he]=חלון חדש
+Name[hi_IN]=नया विंडो
+Name[hr]=Novi prozor
+Name[hsb]=Nowe wokno
+Name[hu]=Új ablak
+Name[hy_AM]=Նոր Պատուհան
+Name[id]=Jendela Baru
+Name[is]=Nýr gluggi
+Name[it]=Nuova finestra
+Name[ja]=新しいウィンドウ
+Name[ja_JP-mac]=新規ウインドウ
+Name[ka]=ახალი ფანჯარა
+Name[kk]=Жаңа терезе
+Name[km]=បង្អួចថ្មី
+Name[kn]=ಹೊಸ ಕಿಟಕಿ
+Name[ko]=새 창
+Name[kok]=नवें जनेल
+Name[ks]=نئئ وِنڈو
+Name[lij]=Neuvo barcon
+Name[lo]=ຫນ້າຕ່າງໃຫມ່
+Name[lt]=Naujas langas
+Name[ltg]=Jauns lūgs
+Name[lv]=Jauns logs
+Name[mai]=नव विंडो
+Name[mk]=Нов прозорец
+Name[ml]=പുതിയ ജാലകം
+Name[mr]=नवीन पटल
+Name[ms]=Tetingkap Baru
+Name[my]=ဝင်းဒိုးအသစ်
+Name[nb_NO]=Nytt vindu
+Name[ne_NP]=नयाँ सञ्झ्याल
+Name[nl]=Nieuw venster
+Name[nn_NO]=Nytt vindauge
+Name[or]=ନୂତନ ୱିଣ୍ଡୋ
+Name[pa_IN]=ਨਵੀਂ ਵਿੰਡੋ
+Name[pl]=Nowe okno
+Name[pt_BR]=Nova janela
+Name[pt_PT]=Nova janela
+Name[rm]=Nova fanestra
+Name[ro]=Fereastră nouă
+Name[ru]=Новое окно
+Name[sat]=नावा विंडो (N)
+Name[si]=නව කවුළුවක්
+Name[sk]=Nové okno
+Name[sl]=Novo okno
+Name[son]=Zanfun taaga
+Name[sq]=Dritare e Re
+Name[sr]=Нови прозор
+Name[sv_SE]=Nytt fönster
+Name[ta]=புதிய சாளரம்
+Name[te]=కొత్త విండో
+Name[th]=หน้าต่างใหม่
+Name[tr]=Yeni pencere
+Name[tsz]=Eraatarakua jimpani
+Name[uk]=Нове вікно
+Name[ur]=نیا دریچہ
+Name[uz]=Yangi oyna
+Name[vi]=Cửa sổ mới
+Name[wo]=Palanteer bu bees
+Name[xh]=Ifestile entsha
+Name[zh_CN]=新建窗口
+Name[zh_TW]=開新視窗
+Exec=/usr/lib/firefox-developer-edition/firefox --class="firefox-developer-edition" --new-window %u
+
+[Desktop Action new-private-window]
+Name=New Private Window
+Name[ach]=Dirica manyen me mung
+Name[af]=Nuwe privaatvenster
+Name[an]=Nueva finestra privada
+Name[ar]=نافذة خاصة جديدة
+Name[as]=নতুন ব্যক্তিগত উইন্ডো
+Name[ast]=Ventana privada nueva
+Name[az]=Yeni Məxfi Pəncərə
+Name[be]=Новае акно адасаблення
+Name[bg]=Нов прозорец за поверително сърфиране
+Name[bn_BD]=নতুন ব্যক্তিগত উইন্ডো
+Name[bn_IN]=নতুন ব্যক্তিগত উইন্ডো
+Name[br]=Prenestr merdeiñ prevez nevez
+Name[brx]=गोदान प्राइभेट उइन्ड'
+Name[bs]=Novi privatni prozor
+Name[ca]=Finestra privada nova
+Name[cak]=K'ak'a' ichinan tzuwäch
+Name[cs]=Nové anonymní okno
+Name[cy]=Ffenestr Breifat Newydd
+Name[da]=Nyt privat vindue
+Name[de]=Neues privates Fenster
+Name[dsb]=Nowe priwatne wokno
+Name[el]=Νέο παράθυρο ιδιωτικής περιήγησης
+Name[en_GB]=New Private Window
+Name[en_US]=New Private Window
+Name[en_ZA]=New Private Window
+Name[eo]=Nova privata fenestro
+Name[es_AR]=Nueva ventana privada
+Name[es_CL]=Nueva ventana privada
+Name[es_ES]=Nueva ventana privada
+Name[es_MX]=Nueva ventana privada
+Name[et]=Uus privaatne aken
+Name[eu]=Leiho pribatu berria
+Name[fa]=پنجره ناشناس جدید
+Name[ff]=Henorde Suturo Hesere
+Name[fi]=Uusi yksityinen ikkuna
+Name[fr]=Nouvelle fenêtre de navigation privée
+Name[fy_NL]=Nij priveefinster
+Name[ga_IE]=Fuinneog Nua Phríobháideach
+Name[gd]=Uinneag phrìobhaideach ùr
+Name[gl]=Nova xanela privada
+Name[gn]=Ovetã ñemi pyahu
+Name[gu_IN]=નવી ખાનગી વિન્ડો
+Name[he]=חלון פרטי חדש
+Name[hi_IN]=नयी निजी विंडो
+Name[hr]=Novi privatni prozor
+Name[hsb]=Nowe priwatne wokno
+Name[hu]=Új privát ablak
+Name[hy_AM]=Սկսել Գաղտնի դիտարկում
+Name[id]=Jendela Mode Pribadi Baru
+Name[is]=Nýr huliðsgluggi
+Name[it]=Nuova finestra anonima
+Name[ja]=新しいプライベートウィンドウ
+Name[ja_JP-mac]=新規プライベートウインドウ
+Name[ka]=ახალი პირადი ფანჯარა
+Name[kk]=Жаңа жекелік терезе
+Name[km]=បង្អួចឯកជនថ្មី
+Name[kn]=ಹೊಸ ಖಾಸಗಿ ಕಿಟಕಿ
+Name[ko]=새 사생활 보호 모드
+Name[kok]=नवो खाजगी विंडो
+Name[ks]=نْو پرایوٹ وینڈو
+Name[lij]=Nêuvo barcón privòu
+Name[lo]=ເປີດຫນ້າຕ່າງສວນຕົວຂື້ນມາໃຫມ່
+Name[lt]=Naujas privataus naršymo langas
+Name[ltg]=Jauns privatais lūgs
+Name[lv]=Jauns privātais logs
+Name[mai]=नया निज विंडो (W)
+Name[mk]=Нов приватен прозорец
+Name[ml]=പുതിയ സ്വകാര്യ ജാലകം
+Name[mr]=नवीन वैयक्तिक पटल
+Name[ms]=Tetingkap Persendirian Baharu
+Name[my]=New Private Window
+Name[nb_NO]=Nytt privat vindu
+Name[ne_NP]=नयाँ निजी सञ्झ्याल
+Name[nl]=Nieuw privévenster
+Name[nn_NO]=Nytt privat vindauge
+Name[or]=ନୂତନ ବ୍ୟକ୍ତିଗତ ୱିଣ୍ଡୋ
+Name[pa_IN]=ਨਵੀਂ ਪ੍ਰਾਈਵੇਟ ਵਿੰਡੋ
+Name[pl]=Nowe okno prywatne
+Name[pt_BR]=Nova janela privativa
+Name[pt_PT]=Nova janela privada
+Name[rm]=Nova fanestra privata
+Name[ro]=Fereastră privată nouă
+Name[ru]=Новое приватное окно
+Name[sat]=नावा निजेराक् विंडो (W )
+Name[si]=නව පුද්ගලික කවුළුව (W)
+Name[sk]=Nové okno v režime Súkromné prehliadanie
+Name[sl]=Novo zasebno okno
+Name[son]=Sutura zanfun taaga
+Name[sq]=Dritare e Re Private
+Name[sr]=Нови приватан прозор
+Name[sv_SE]=Nytt privat fönster
+Name[ta]=புதிய தனிப்பட்ட சாளரம்
+Name[te]=కొత్త ఆంతరంగిక విండో
+Name[th]=หน้าต่างส่วนตัวใหม่
+Name[tr]=Yeni gizli pencere
+Name[tsz]=Juchiiti eraatarakua jimpani
+Name[uk]=Приватне вікно
+Name[ur]=نیا نجی دریچہ
+Name[uz]=Yangi maxfiy oyna
+Name[vi]=Cửa sổ riêng tư mới
+Name[wo]=Panlanteeru biir bu bees
+Name[xh]=Ifestile yangasese entsha
+Name[zh_CN]=新建隐私浏览窗口
+Name[zh_TW]=新增隱私視窗
+Exec=/usr/lib/firefox-developer-edition/firefox --class="firefox-developer-edition" --private-window %u
diff --git a/firefox-install-dir.patch b/firefox-install-dir.patch
new file mode 100644
index 000000000000..70ce329f2946
--- /dev/null
+++ b/firefox-install-dir.patch
@@ -0,0 +1,43 @@
+ browser/branding/aurora/configure.sh | 1 -
+ config/baseconfig.mk | 2 +-
+ toolkit/mozapps/installer/packager.mk | 4 ++--
+ 3 files changed, 3 insertions(+), 4 deletions(-)
+
+diff --git c/browser/branding/aurora/configure.sh i/browser/branding/aurora/configure.sh
+index 19d4ff057f73..2c79e136cc67 100644
+--- c/browser/branding/aurora/configure.sh
++++ i/browser/branding/aurora/configure.sh
+@@ -3,5 +3,4 @@
+ # file, You can obtain one at http://mozilla.org/MPL/2.0/.
+
+ MOZ_APP_DISPLAYNAME="Firefox Developer Edition"
+-MOZ_APP_REMOTINGNAME=firefox-dev
+ MOZ_DEV_EDITION=1
+diff --git c/config/baseconfig.mk i/config/baseconfig.mk
+index 3ef3af95d611..81530dface0a 100644
+--- c/config/baseconfig.mk
++++ i/config/baseconfig.mk
+@@ -2,7 +2,7 @@
+ # directly in python/mozbuild/mozbuild/base.py for gmake validation.
+ # We thus use INCLUDED_AUTOCONF_MK to enable/disable some parts depending
+ # whether a normal build is happening or whether the check is running.
+-installdir = $(libdir)/$(MOZ_APP_NAME)
++installdir = $(libdir)/$(MOZ_APP_NAME)-developer-edition
+ ifeq (.,$(DEPTH))
+ DIST = dist
+ else
+diff --git c/toolkit/mozapps/installer/packager.mk i/toolkit/mozapps/installer/packager.mk
+index 64f902a26942..d3313dacbcb7 100644
+--- c/toolkit/mozapps/installer/packager.mk
++++ i/toolkit/mozapps/installer/packager.mk
+@@ -138,8 +138,8 @@ endif
+ (cd $(DIST)/$(MOZ_PKG_DIR) && $(TAR) --exclude=precomplete $(TAR_CREATE_FLAGS) - .) | \
+ (cd $(DESTDIR)$(installdir) && tar -xf -)
+ $(NSINSTALL) -D $(DESTDIR)$(bindir)
+- $(RM) -f $(DESTDIR)$(bindir)/$(MOZ_APP_NAME)
+- ln -s $(installdir)/$(MOZ_APP_NAME) $(DESTDIR)$(bindir)
++ $(RM) -f $(DESTDIR)$(bindir)/$(MOZ_APP_NAME)-developer-edition
++ ln -s $(installdir)/$(MOZ_APP_NAME) $(DESTDIR)$(bindir)/$(MOZ_APP_NAME)-developer-edition
+
+ upload:
+ $(PYTHON) -u $(MOZILLA_DIR)/build/upload.py --base-path $(DIST) $(UPLOAD_FILES)
diff --git a/firefox-kde.patch b/firefox-kde.patch
new file mode 100644
index 000000000000..29d7e78c552e
--- /dev/null
+++ b/firefox-kde.patch
@@ -0,0 +1,282 @@
+# HG changeset patch
+# User msirringhaus@suse.de
+# Date 1559300151 -7200
+# Fri May 31 12:55:51 2019 +0200
+# Node ID 54d41b0033b8d649d842a1f862c6fed8b9874dec
+# Parent 856ef9c699423b1cd35e4df8745e78c409c8dbae
+How to apply this patch:
+1. Import and apply it
+2. cp browser/base/content/browser.xul browser/base/content/browser-kde.xul
+3. Find editBookmarkPanelDoneButton
+4. Replace #ifndef with #ifdef in the line above (this hanges the button order from Gnome-style to KDE-style)
+5. hg qrefresh
+
+diff --git a/browser/components/preferences/main.js b/browser/components/preferences/main.js
+--- a/browser/components/preferences/main.js
++++ b/browser/components/preferences/main.js
+@@ -338,16 +338,23 @@ var gMainPane = {
+ }, backoffTimes[this._backoffIndex + 1 < backoffTimes.length ? this._backoffIndex++ : backoffTimes.length - 1]);
+ };
+
+ window.setTimeout(() => {
+ window.requestIdleCallback(pollForDefaultBrowser);
+ }, backoffTimes[this._backoffIndex]);
+ }
+
++ var env = Components.classes["@mozilla.org/process/environment;1"]
++ .getService(Components.interfaces.nsIEnvironment);
++ var kde_session = 0;
++ if (env.get('KDE_FULL_SESSION') == "true") {
++ kde_session = 1;
++ }
++
+ this.initBrowserContainers();
+ this.buildContentProcessCountMenuList();
+
+ let performanceSettingsLink = document.getElementById(
+ "performanceSettingsLearnMore"
+ );
+ let performanceSettingsUrl =
+ Services.urlFormatter.formatURLPref("app.support.baseURL") +
+@@ -1313,16 +1320,27 @@ var gMainPane = {
+ this._backoffIndex = 0;
+
+ let shellSvc = getShellService();
+ if (!shellSvc) {
+ return;
+ }
+ try {
+ shellSvc.setDefaultBrowser(true, false);
++ if (kde_session == 1) {
++ var shellObj = Components.classes["@mozilla.org/file/local;1"]
++ .createInstance(Components.interfaces.nsILocalFile);
++ shellObj.initWithPath("/usr/bin/kwriteconfig");
++ var process = Components.classes["@mozilla.org/process/util;1"]
++ .createInstance(Components.interfaces.nsIProcess);
++ process.init(shellObj);
++ var args = ["--file", "kdeglobals", "--group", "General", "--key",
++ "BrowserApplication", "firefox"];
++ process.run(false, args, args.length);
++ }
+ } catch (ex) {
+ Cu.reportError(ex);
+ return;
+ }
+
+ let isDefault = shellSvc.isDefaultBrowser(false, true);
+ let setDefaultPane = document.getElementById("setDefaultPane");
+ setDefaultPane.classList.toggle("is-default", isDefault);
+diff --git a/browser/components/shell/moz.build b/browser/components/shell/moz.build
+--- a/browser/components/shell/moz.build
++++ b/browser/components/shell/moz.build
+@@ -32,16 +32,18 @@ if CONFIG["MOZ_WIDGET_TOOLKIT"] == "coco
+ ]
+ elif CONFIG["MOZ_WIDGET_TOOLKIT"] == "gtk":
+ XPIDL_SOURCES += [
+ "nsIGNOMEShellService.idl",
+ ]
+
+ SOURCES += [
+ "nsGNOMEShellService.cpp",
++ "nsKDEShellService.cpp",
++ "nsUnixShellService.cpp",
+ ]
+ if CONFIG["MOZ_ENABLE_DBUS"]:
+ SOURCES += [
+ "nsGNOMEShellDBusHelper.cpp",
+ "nsGNOMEShellSearchProvider.cpp",
+ ]
+ include("/ipc/chromium/chromium-config.mozbuild")
+
+diff --git a/browser/components/shell/nsKDEShellService.cpp b/browser/components/shell/nsKDEShellService.cpp
+new file mode 100644
+--- /dev/null
++++ b/browser/components/shell/nsKDEShellService.cpp
+@@ -0,0 +1,103 @@
++/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
++/* This Source Code Form is subject to the terms of the Mozilla Public
++ * License, v. 2.0. If a copy of the MPL was not distributed with this
++ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
++
++#include "mozilla/ArrayUtils.h"
++
++#include "nsCOMPtr.h"
++#include "nsKDEShellService.h"
++#include "nsShellService.h"
++#include "nsKDEUtils.h"
++#include "nsIPrefService.h"
++#include "nsIProcess.h"
++#include "nsIFile.h"
++#include "nsServiceManagerUtils.h"
++#include "nsComponentManagerUtils.h"
++#include "nsIMutableArray.h"
++#include "nsISupportsPrimitives.h"
++#include "nsArrayUtils.h"
++
++using namespace mozilla;
++
++nsresult
++nsKDEShellService::Init()
++{
++ if( !nsKDEUtils::kdeSupport())
++ return NS_ERROR_NOT_AVAILABLE;
++ return NS_OK;
++}
++
++NS_IMPL_ISUPPORTS(nsKDEShellService, nsIGNOMEShellService, nsIShellService)
++
++NS_IMETHODIMP
++nsKDEShellService::IsDefaultBrowser(bool aForAllTypes,
++ bool* aIsDefaultBrowser)
++{
++ *aIsDefaultBrowser = false;
++
++ nsCOMPtr<nsIMutableArray> command = do_CreateInstance( NS_ARRAY_CONTRACTID );
++ if (!command)
++ return NS_ERROR_FAILURE;
++
++ nsCOMPtr<nsISupportsCString> str = do_CreateInstance( NS_SUPPORTS_CSTRING_CONTRACTID );
++ if (!str)
++ return NS_ERROR_FAILURE;
++
++ str->SetData("ISDEFAULTBROWSER"_ns);
++ command->AppendElement( str );
++
++ if( nsKDEUtils::command( command ))
++ *aIsDefaultBrowser = true;
++ return NS_OK;
++}
++
++NS_IMETHODIMP
++nsKDEShellService::SetDefaultBrowser(bool aClaimAllTypes,
++ bool aForAllUsers)
++{
++ nsCOMPtr<nsIMutableArray> command = do_CreateInstance( NS_ARRAY_CONTRACTID );
++ if (!command)
++ return NS_ERROR_FAILURE;
++
++ nsCOMPtr<nsISupportsCString> cmdstr = do_CreateInstance( NS_SUPPORTS_CSTRING_CONTRACTID );
++ nsCOMPtr<nsISupportsCString> paramstr = do_CreateInstance( NS_SUPPORTS_CSTRING_CONTRACTID );
++ if (!cmdstr || !paramstr)
++ return NS_ERROR_FAILURE;
++
++ cmdstr->SetData("SETDEFAULTBROWSER"_ns);
++ command->AppendElement( cmdstr );
++
++ paramstr->SetData( aClaimAllTypes ? "ALLTYPES"_ns : "NORMAL"_ns );
++ command->AppendElement( paramstr );
++
++ return nsKDEUtils::command( command ) ? NS_OK : NS_ERROR_FAILURE;
++}
++
++NS_IMETHODIMP
++nsKDEShellService::GetCanSetDesktopBackground(bool* aResult)
++{
++ *aResult = true;
++ return NS_OK;
++}
++
++NS_IMETHODIMP
++nsKDEShellService::SetDesktopBackground(dom::Element* aElement,
++ int32_t aPosition,
++ const nsACString& aImageName)
++{
++ return NS_ERROR_NOT_IMPLEMENTED;
++}
++
++NS_IMETHODIMP
++nsKDEShellService::GetDesktopBackgroundColor(PRUint32 *aColor)
++{
++ return NS_ERROR_NOT_IMPLEMENTED;
++}
++
++NS_IMETHODIMP
++nsKDEShellService::SetDesktopBackgroundColor(PRUint32 aColor)
++{
++ return NS_ERROR_NOT_IMPLEMENTED;
++}
++
+diff --git a/browser/components/shell/nsKDEShellService.h b/browser/components/shell/nsKDEShellService.h
+new file mode 100644
+--- /dev/null
++++ b/browser/components/shell/nsKDEShellService.h
+@@ -0,0 +1,32 @@
++/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
++/* This Source Code Form is subject to the terms of the Mozilla Public
++ * License, v. 2.0. If a copy of the MPL was not distributed with this
++ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
++
++#ifndef nskdeshellservice_h____
++#define nskdeshellservice_h____
++
++#include "nsIGNOMEShellService.h"
++#include "nsToolkitShellService.h"
++#include "nsString.h"
++#include "mozilla/Attributes.h"
++
++class nsKDEShellService final : public nsIGNOMEShellService,
++ public nsToolkitShellService
++{
++public:
++ nsKDEShellService() : mCheckedThisSession(false) { }
++
++ NS_DECL_ISUPPORTS
++ NS_DECL_NSISHELLSERVICE
++ NS_DECL_NSIGNOMESHELLSERVICE
++
++ nsresult Init();
++
++private:
++ ~nsKDEShellService() {}
++
++ bool mCheckedThisSession;
++};
++
++#endif // nskdeshellservice_h____
+diff --git a/browser/components/shell/nsUnixShellService.cpp b/browser/components/shell/nsUnixShellService.cpp
+new file mode 100644
+--- /dev/null
++++ b/browser/components/shell/nsUnixShellService.cpp
+@@ -0,0 +1,22 @@
++/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
++/* This Source Code Form is subject to the terms of the Mozilla Public
++ * License, v. 2.0. If a copy of the MPL was not distributed with this
++ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
++
++
++#include "nsUnixShellService.h"
++#include "nsGNOMEShellService.h"
++#include "nsKDEShellService.h"
++#include "nsKDEUtils.h"
++#include "mozilla/ModuleUtils.h"
++
++NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsGNOMEShellService, Init)
++NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsKDEShellService, Init)
++
++NS_IMETHODIMP
++nsUnixShellServiceConstructor(nsISupports *aOuter, REFNSIID aIID, void **aResult)
++{
++ if( nsKDEUtils::kdeSupport())
++ return nsKDEShellServiceConstructor( aOuter, aIID, aResult );
++ return nsGNOMEShellServiceConstructor( aOuter, aIID, aResult );
++}
+diff --git a/browser/components/shell/nsUnixShellService.h b/browser/components/shell/nsUnixShellService.h
+new file mode 100644
+--- /dev/null
++++ b/browser/components/shell/nsUnixShellService.h
+@@ -0,0 +1,15 @@
++/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
++/* This Source Code Form is subject to the terms of the Mozilla Public
++ * License, v. 2.0. If a copy of the MPL was not distributed with this
++ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
++
++
++#ifndef nsunixshellservice_h____
++#define nsunixshellservice_h____
++
++#include "nsIGNOMEShellService.h"
++
++NS_IMETHODIMP
++nsUnixShellServiceConstructor(nsISupports *aOuter, REFNSIID aIID, void **aResult);
++
++#endif // nsunixshellservice_h____
diff --git a/identity-icons-brand.svg b/identity-icons-brand.svg
new file mode 100644
index 000000000000..fc8b1a356768
--- /dev/null
+++ b/identity-icons-brand.svg
@@ -0,0 +1,3 @@
+<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16">
+ <path fill="context-fill" fill-opacity="context-fill-opacity" d="M15.424 5.366A4.384 4.384 0 0 0 13.817 3.4a7.893 7.893 0 0 1 .811 2.353v.017c-.9-2.185-2.441-3.066-3.7-4.984l-.189-.3c-.035-.059-.063-.112-.088-.161a1.341 1.341 0 0 1-.119-.306.022.022 0 0 0-.013-.019.026.026 0 0 0-.019 0h-.006a5.629 5.629 0 0 0-2.755 4.308c.094-.006.187-.014.282-.014a4.069 4.069 0 0 1 3.51 1.983A2.838 2.838 0 0 0 9.6 5.824a3.2 3.2 0 0 1-1.885 6.013 3.651 3.651 0 0 1-1.042-.2c-.078-.028-.157-.059-.235-.093-.046-.02-.091-.04-.135-.062A3.282 3.282 0 0 1 4.415 8.95s.369-1.334 2.647-1.334a1.91 1.91 0 0 0 .964-.857 12.756 12.756 0 0 1-1.941-1.118c-.29-.277-.428-.411-.551-.511-.066-.054-.128-.1-.207-.152a3.481 3.481 0 0 1-.022-1.894 5.915 5.915 0 0 0-1.929 1.442A4.108 4.108 0 0 1 3.1 2.584a1.561 1.561 0 0 0-.267.138 5.767 5.767 0 0 0-.783.649 6.9 6.9 0 0 0-.748.868 6.446 6.446 0 0 0-1.08 2.348c0 .009-.076.325-.131.715l-.025.182c-.019.117-.033.245-.048.444v.023c-.005.076-.011.16-.016.258v.04A7.884 7.884 0 0 0 8.011 16a7.941 7.941 0 0 0 7.9-6.44l.036-.3a7.724 7.724 0 0 0-.523-3.894z" />
+</svg>
diff --git a/mozilla-bmo1005535.patch b/mozilla-bmo1005535.patch
new file mode 100644
index 000000000000..d20d81209160
--- /dev/null
+++ b/mozilla-bmo1005535.patch
@@ -0,0 +1,30 @@
+# HG changeset patch
+# User Steve Singer <steve@ssinger.info>
+# Date 1558451540 -7200
+# Tue May 21 17:12:20 2019 +0200
+# Node ID 433beec63e6b5f409683af20a0c1ab137cc7bfad
+# Parent c0fdccc716e80a6d289c94f5d507ae141c62a3bf
+Bug 1005535 - Get skia GPU building on big endian.
+
+diff --git a/gfx/skia/skia/src/gpu/GrColor.h b/gfx/skia/skia/src/gpu/GrColor.h
+--- a/gfx/skia/skia/src/gpu/GrColor.h
++++ b/gfx/skia/skia/src/gpu/GrColor.h
+@@ -59,17 +59,17 @@ static inline GrColor GrColorPackRGBA(un
+ #define GrColorUnpackG(color) (((color) >> GrColor_SHIFT_G) & 0xFF)
+ #define GrColorUnpackB(color) (((color) >> GrColor_SHIFT_B) & 0xFF)
+ #define GrColorUnpackA(color) (((color) >> GrColor_SHIFT_A) & 0xFF)
+
+ /**
+ * Since premultiplied means that alpha >= color, we construct a color with
+ * each component==255 and alpha == 0 to be "illegal"
+ */
+-#define GrColor_ILLEGAL (~(0xFF << GrColor_SHIFT_A))
++#define GrColor_ILLEGAL ((uint32_t)(~(0xFF << GrColor_SHIFT_A)))
+
+ /** Normalizes and coverts an uint8_t to a float. [0, 255] -> [0.0, 1.0] */
+ static inline float GrNormalizeByteToFloat(uint8_t value) {
+ static const float ONE_OVER_255 = 1.f / 255.f;
+ return value * ONE_OVER_255;
+ }
+
+ /** Used to pick vertex attribute types. */
diff --git a/mozilla-bmo1504834-part1.patch b/mozilla-bmo1504834-part1.patch
new file mode 100644
index 000000000000..1afe3aa4a2ea
--- /dev/null
+++ b/mozilla-bmo1504834-part1.patch
@@ -0,0 +1,121 @@
+# HG changeset patch
+# Parent b5471d23321d16a0bacc25b7afd27d2e16adba1a
+Taken from https://bugzilla.mozilla.org/show_bug.cgi?id=1504834
+
+diff --git a/gfx/2d/DrawTargetSkia.cpp b/gfx/2d/DrawTargetSkia.cpp
+--- a/gfx/2d/DrawTargetSkia.cpp
++++ b/gfx/2d/DrawTargetSkia.cpp
+@@ -130,18 +130,17 @@ static IntRect CalculateSurfaceBounds(co
+ Rect sampledBounds = inverse.TransformBounds(*aBounds);
+ if (!sampledBounds.ToIntRect(&bounds)) {
+ return surfaceBounds;
+ }
+
+ return surfaceBounds.Intersect(bounds);
+ }
+
+-static const int kARGBAlphaOffset =
+- SurfaceFormat::A8R8G8B8_UINT32 == SurfaceFormat::B8G8R8A8 ? 3 : 0;
++static const int kARGBAlphaOffset = 0; // Skia is always BGRA SurfaceFormat::A8R8G8B8_UINT32 == SurfaceFormat::B8G8R8A8 ? 3 : 0;
+
+ static bool VerifyRGBXFormat(uint8_t* aData, const IntSize& aSize,
+ const int32_t aStride, SurfaceFormat aFormat) {
+ if (aFormat != SurfaceFormat::B8G8R8X8 || aSize.IsEmpty()) {
+ return true;
+ }
+ // We should've initialized the data to be opaque already
+ // On debug builds, verify that this is actually true.
+diff --git a/gfx/2d/Types.h b/gfx/2d/Types.h
+--- a/gfx/2d/Types.h
++++ b/gfx/2d/Types.h
+@@ -84,25 +84,18 @@ enum class SurfaceFormat : int8_t {
+ Depth,
+
+ // This represents the unknown format.
+ UNKNOWN,
+
+ // The following values are endian-independent synonyms. The _UINT32 suffix
+ // indicates that the name reflects the layout when viewed as a uint32_t
+ // value.
+-#if MOZ_LITTLE_ENDIAN()
+ A8R8G8B8_UINT32 = B8G8R8A8, // 0xAARRGGBB
+ X8R8G8B8_UINT32 = B8G8R8X8, // 0x00RRGGBB
+-#elif MOZ_BIG_ENDIAN()
+- A8R8G8B8_UINT32 = A8R8G8B8, // 0xAARRGGBB
+- X8R8G8B8_UINT32 = X8R8G8B8, // 0x00RRGGBB
+-#else
+-# error "bad endianness"
+-#endif
+
+ // The following values are OS and endian-independent synonyms.
+ //
+ // TODO(aosmond): When everything blocking bug 1581828 has been resolved, we
+ // can make this use R8B8G8A8 and R8B8G8X8 for non-Windows platforms.
+ OS_RGBA = A8R8G8B8_UINT32,
+ OS_RGBX = X8R8G8B8_UINT32
+ };
+diff --git a/gfx/skia/skia/third_party/skcms/skcms.cc b/gfx/skia/skia/third_party/skcms/skcms.cc
+--- a/gfx/skia/skia/third_party/skcms/skcms.cc
++++ b/gfx/skia/skia/third_party/skcms/skcms.cc
+@@ -25,16 +25,18 @@
+ // it'd be a lot slower. But we want all those headers included so we
+ // can use their features after runtime checks later.
+ #include <smmintrin.h>
+ #include <avxintrin.h>
+ #include <avx2intrin.h>
+ #include <avx512fintrin.h>
+ #include <avx512dqintrin.h>
+ #endif
++#else
++ #define SKCMS_PORTABLE
+ #endif
+
+ // sizeof(x) will return size_t, which is 32-bit on some machines and 64-bit on others.
+ // We have better testing on 64-bit machines, so force 32-bit machines to behave like 64-bit.
+ //
+ // Please do not use sizeof() directly, and size_t only when required.
+ // (We have no way of enforcing these requests...)
+ #define SAFE_SIZEOF(x) ((uint64_t)sizeof(x))
+@@ -275,30 +277,38 @@ enum {
+ skcms_Signature_sf32 = 0x73663332,
+ // XYZ is also a PCS signature, so it's defined in skcms.h
+ // skcms_Signature_XYZ = 0x58595A20,
+ };
+
+ static uint16_t read_big_u16(const uint8_t* ptr) {
+ uint16_t be;
+ memcpy(&be, ptr, sizeof(be));
+-#if defined(_MSC_VER)
++#if __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__
++ return be;
++#else
++ #if defined(_MSC_VER)
+ return _byteswap_ushort(be);
+-#else
++ #else
+ return __builtin_bswap16(be);
++ #endif
+ #endif
+ }
+
+ static uint32_t read_big_u32(const uint8_t* ptr) {
+ uint32_t be;
+ memcpy(&be, ptr, sizeof(be));
+-#if defined(_MSC_VER)
++#if __BYTE_ORDER == __ORDER_BIG_ENDIAN__
++ return be;
++#else
++ #if defined(_MSC_VER)
+ return _byteswap_ulong(be);
+-#else
++ #else
+ return __builtin_bswap32(be);
++ #endif
+ #endif
+ }
+
+ static int32_t read_big_i32(const uint8_t* ptr) {
+ return (int32_t)read_big_u32(ptr);
+ }
+
+ static float read_big_fixed(const uint8_t* ptr) {
diff --git a/mozilla-bmo1504834-part2.patch b/mozilla-bmo1504834-part2.patch
new file mode 100644
index 000000000000..25f7fbc2c14e
--- /dev/null
+++ b/mozilla-bmo1504834-part2.patch
@@ -0,0 +1,112 @@
+# HG changeset patch
+# Parent 9319844dca3133fa8bd7107079f1d1ddc5c0bf70
+Skia does not support big endian. The places to fix are too numerous and upstream (skia, not Mozilla)
+has no interest in maintaining big endian.
+So here we try to swizzle the input for skia, so that skia always works on LE, and when it comes
+out again, we transform back to BE.
+
+diff --git a/gfx/2d/ConvolutionFilter.cpp b/gfx/2d/ConvolutionFilter.cpp
+--- a/gfx/2d/ConvolutionFilter.cpp
++++ b/gfx/2d/ConvolutionFilter.cpp
+@@ -29,32 +29,79 @@ bool ConvolutionFilter::GetFilterOffsetA
+ int32_t* aResultLength) {
+ if (aRowIndex >= mFilter->numValues()) {
+ return false;
+ }
+ mFilter->FilterForValue(aRowIndex, aResultOffset, aResultLength);
+ return true;
+ }
+
++static void ByteSwapArray(uint8_t *u8Array, int32_t size) {
++ uint32_t *array = reinterpret_cast<uint32_t*>(u8Array);
++ for (int pxl = 0; pxl < size; ++pxl) {
++ // Use an endian swap to move the bytes, i.e. BGRA -> ARGB.
++ uint32_t rgba = array[pxl];
++ array[pxl] = NativeEndian::swapToLittleEndian(rgba);
++ }
++}
++
+ void ConvolutionFilter::ConvolveHorizontally(const uint8_t* aSrc, uint8_t* aDst,
+ bool aHasAlpha) {
++#if MOZ_BIG_ENDIAN()
++ int outputSize = mFilter->numValues();
++
++ // Input size isn't handed in, so we have to calculate it quickly
++ int inputSize = 0;
++ for (int xx = 0; xx < outputSize; ++xx) {
++ // Get the filter that determines the current output pixel.
++ int filterOffset, filterLength;
++ mFilter->FilterForValue(xx, &filterOffset, &filterLength);
++ inputSize = std::max(inputSize, filterOffset + filterLength);
++ }
++
++ ByteSwapArray((uint8_t*)aSrc, inputSize);
++#endif
++
+ SkOpts::convolve_horizontally(aSrc, *mFilter, aDst, aHasAlpha);
++
++#if MOZ_BIG_ENDIAN()
++ ByteSwapArray((uint8_t*)aSrc, inputSize);
++ ByteSwapArray(aDst, outputSize);
++#endif
+ }
+
+ void ConvolutionFilter::ConvolveVertically(uint8_t* const* aSrc, uint8_t* aDst,
+ int32_t aRowIndex, int32_t aRowSize,
+ bool aHasAlpha) {
+ MOZ_ASSERT(aRowIndex < mFilter->numValues());
+
+ int32_t filterOffset;
+ int32_t filterLength;
+ auto filterValues =
+ mFilter->FilterForValue(aRowIndex, &filterOffset, &filterLength);
++
++#if MOZ_BIG_ENDIAN()
++ for (int filterY = 0; filterY < filterLength; filterY++) {
++ // Skia only knows LE, so we have to swizzle the input
++ ByteSwapArray(aSrc[filterY], aRowSize);
++ }
++#endif
++
+ SkOpts::convolve_vertically(filterValues, filterLength, aSrc, aRowSize, aDst,
+ aHasAlpha);
++
++#if MOZ_BIG_ENDIAN()
++ // After skia is finished, we swizzle back to BE, in case
++ // the input is used again somewhere else
++ for (int filterY = 0; filterY < filterLength; filterY++) {
++ ByteSwapArray(aSrc[filterY], aRowSize);
++ }
++ // The destination array as well
++ ByteSwapArray(aDst, aRowSize);
++#endif
+ }
+
+ /* ConvolutionFilter::ComputeResizeFactor is derived from Skia's
+ * SkBitmapScaler/SkResizeFilter::computeFactors. It is governed by Skia's
+ * BSD-style license (see gfx/skia/LICENSE) and the following copyright:
+ * Copyright (c) 2015 Google Inc.
+ */
+ bool ConvolutionFilter::ComputeResizeFilter(ResizeMethod aResizeMethod,
+diff --git a/gfx/skia/skia/include/core/SkPreConfig.h b/gfx/skia/skia/include/core/SkPreConfig.h
+--- a/gfx/skia/skia/include/core/SkPreConfig.h
++++ b/gfx/skia/skia/include/core/SkPreConfig.h
+@@ -68,17 +68,17 @@
+ #define SK_CPU_BENDIAN
+ #elif defined(__BYTE_ORDER__) && (__BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__)
+ #define SK_CPU_LENDIAN
+ #elif defined(__sparc) || defined(__sparc__) || \
+ defined(_POWER) || defined(__powerpc__) || \
+ defined(__ppc__) || defined(__hppa) || \
+ defined(__PPC__) || defined(__PPC64__) || \
+ defined(_MIPSEB) || defined(__ARMEB__) || \
+- defined(__s390__) || \
++ defined(__s390__) || defined(__s390x__) || \
+ (defined(__sh__) && defined(__BIG_ENDIAN__)) || \
+ (defined(__ia64) && defined(__BIG_ENDIAN__))
+ #define SK_CPU_BENDIAN
+ #else
+ #define SK_CPU_LENDIAN
+ #endif
+ #endif
+
diff --git a/mozilla-bmo1504834-part3.patch b/mozilla-bmo1504834-part3.patch
new file mode 100644
index 000000000000..d07702e13554
--- /dev/null
+++ b/mozilla-bmo1504834-part3.patch
@@ -0,0 +1,64 @@
+# HG changeset patch
+# Parent d1d66f7e4d0e7fd45e91e4fcee07555e72046d48
+For FF68, AntiAliasing of XULTexts seem to be broken on big endian (s390x). Text and icons of the sandwich-menu to the
+right of the address bar, as well as plugin-windows appears transparant, which usually means unreadable (white on white).
+
+diff --git a/gfx/skia/skia/include/private/SkNx.h b/gfx/skia/skia/include/private/SkNx.h
+--- a/gfx/skia/skia/include/private/SkNx.h
++++ b/gfx/skia/skia/include/private/SkNx.h
+@@ -233,17 +233,28 @@ struct SkNx<1,T> {
+ AI SkNx operator<<(int bits) const { return fVal << bits; }
+ AI SkNx operator>>(int bits) const { return fVal >> bits; }
+
+ AI SkNx operator+(const SkNx& y) const { return fVal + y.fVal; }
+ AI SkNx operator-(const SkNx& y) const { return fVal - y.fVal; }
+ AI SkNx operator*(const SkNx& y) const { return fVal * y.fVal; }
+ AI SkNx operator/(const SkNx& y) const { return fVal / y.fVal; }
+
++ // On Big endian the commented out variant doesn't work,
++ // and honestly, I have no idea why it exists in the first place.
++ // The reason its broken is, I think, that it defaults to the double-variant of ToBits()
++ // which gets a 64-bit integer, and FromBits returns 32-bit,
++ // cutting off the wrong half again.
++ // Overall, I see no reason to have ToBits and FromBits at all (even for floats/doubles).
++ // Still we are only "fixing" this for big endian and leave little endian alone (never touch a running system)
++#ifdef SK_CPU_BENDIAN
++ AI SkNx operator&(const SkNx& y) const { return fVal & y.fVal; }
++#else
+ AI SkNx operator&(const SkNx& y) const { return FromBits(ToBits(fVal) & ToBits(y.fVal)); }
++#endif
+ AI SkNx operator|(const SkNx& y) const { return FromBits(ToBits(fVal) | ToBits(y.fVal)); }
+ AI SkNx operator^(const SkNx& y) const { return FromBits(ToBits(fVal) ^ ToBits(y.fVal)); }
+
+ AI SkNx operator==(const SkNx& y) const { return FromBits(fVal == y.fVal ? ~0 : 0); }
+ AI SkNx operator!=(const SkNx& y) const { return FromBits(fVal != y.fVal ? ~0 : 0); }
+ AI SkNx operator<=(const SkNx& y) const { return FromBits(fVal <= y.fVal ? ~0 : 0); }
+ AI SkNx operator>=(const SkNx& y) const { return FromBits(fVal >= y.fVal ? ~0 : 0); }
+ AI SkNx operator< (const SkNx& y) const { return FromBits(fVal < y.fVal ? ~0 : 0); }
+diff --git a/gfx/skia/skia/src/opts/SkBlitMask_opts.h b/gfx/skia/skia/src/opts/SkBlitMask_opts.h
+--- a/gfx/skia/skia/src/opts/SkBlitMask_opts.h
++++ b/gfx/skia/skia/src/opts/SkBlitMask_opts.h
+@@ -198,17 +198,23 @@ namespace SK_OPTS_NS {
+ const SkAlpha* mask, size_t maskRB,
+ int w, int h) {
+ auto fn = [](const Sk4px& d, const Sk4px& aa) {
+ // = (s + d(1-sa))aa + d(1-aa)
+ // = s*aa + d(1-sa*aa)
+ // ~~~>
+ // a = 1*aa + d(1-1*aa) = aa + d(1-aa)
+ // c = 0*aa + d(1-1*aa) = d(1-aa)
++
++ // For big endian we have to swap the alpha-mask from 0,0,0,255 to 255,0,0,0
++#ifdef SK_CPU_BENDIAN
++ return Sk4px(Sk16b(aa) & Sk16b(255,0,0,0, 255,0,0,0, 255,0,0,0, 255,0,0,0))
++#else
+ return Sk4px(Sk16b(aa) & Sk16b(0,0,0,255, 0,0,0,255, 0,0,0,255, 0,0,0,255))
++#endif
+ + d.approxMulDiv255(aa.inv());
+ };
+ while (h --> 0) {
+ Sk4px::MapDstAlpha(w, dst, mask, fn);
+ dst += dstRB / sizeof(*dst);
+ mask += maskRB / sizeof(*mask);
+ }
+ }
diff --git a/mozilla-bmo1504834-part4.patch b/mozilla-bmo1504834-part4.patch
new file mode 100644
index 000000000000..a7052643d23e
--- /dev/null
+++ b/mozilla-bmo1504834-part4.patch
@@ -0,0 +1,40 @@
+# HG changeset patch
+# Parent 883d2c7fec80b9714ccfefa461a02f5b09e3ee09
+Problem description: Tab-titles that are too long to fit into a tab get faded out.
+ On big endian this is broken and instead of fading out, the
+ tab gets white and the font transparent, leading to an unreadable
+ tab-title
+Solution: This is not a real solution, but a hack. The real solution would have been
+ to byte-swap the correct buffer, but I could not find it.
+ So the next best thing is to deactivate the fading-effect. Now all tab-titles
+ are readable, albeit not as pretty to look at as they could be.
+Side-effects: I have not yet found an unwanted side-effect.
+
+diff --git a/gfx/2d/DrawTargetSkia.cpp b/gfx/2d/DrawTargetSkia.cpp
+--- a/gfx/2d/DrawTargetSkia.cpp
++++ b/gfx/2d/DrawTargetSkia.cpp
+@@ -1856,16 +1856,24 @@ void DrawTargetSkia::PushLayerWithBlend(
+ }
+
+ SkCanvas::SaveLayerRec saveRec(
+ aBounds.IsEmpty() ? nullptr : &bounds, &paint, nullptr, clipImage.get(),
+ &clipMatrix,
+ SkCanvas::kPreserveLCDText_SaveLayerFlag |
+ (aCopyBackground ? SkCanvas::kInitWithPrevious_SaveLayerFlag : 0));
+
++#if MOZ_BIG_ENDIAN()
++ // Pushing a layer where an aMask is defined produces wrong output.
++ // We _should_ endian swap the data, but I couldn't find a workable way to do so
++ // Therefore I deactivate those layers in the meantime.
++ // The result is: Tab-titles that are longer than the available space should be faded out.
++ // The fading doesn't work, so we deactivate the fading-effect here.
++ if (!aMask)
++#endif
+ mCanvas->saveLayer(saveRec);
+
+ SetPermitSubpixelAA(aOpaque);
+
+ #ifdef MOZ_WIDGET_COCOA
+ CGContextRelease(mCG);
+ mCG = nullptr;
+ #endif
diff --git a/mozilla-bmo1626236.patch b/mozilla-bmo1626236.patch
new file mode 100644
index 000000000000..b4634ec4bf79
--- /dev/null
+++ b/mozilla-bmo1626236.patch
@@ -0,0 +1,85 @@
+# HG changeset patch
+# User msirringhaus@suse.de
+# Date 1582805876 -3600
+# Thu Feb 27 13:17:56 2020 +0100
+# Node ID cc3d09abea31068e57f1ab918782f9f86fc6a158
+# Parent 9cd90914846f667f18babc491a74c164ae5d6e9f
+imported patch decoder_workaround.patch
+
+diff -r 9cd90914846f image/decoders/nsGIFDecoder2.cpp
+--- a/image/decoders/nsGIFDecoder2.cpp Thu Feb 27 12:57:14 2020 +0100
++++ b/image/decoders/nsGIFDecoder2.cpp Fri Mar 27 13:06:18 2020 +0100
+@@ -422,6 +422,9 @@
+ MOZ_ASSERT(mSwizzleFn);
+ uint8_t* data = reinterpret_cast<uint8_t*>(aColormap);
+ mSwizzleFn(data, data, aColors);
++#if MOZ_BIG_ENDIAN()
++ SwizzleRow(SurfaceFormat::A8R8G8B8, SurfaceFormat::B8G8R8A8)(data, data, aColors);
++#endif
+ }
+
+ LexerResult nsGIFDecoder2::DoDecode(SourceBufferIterator& aIterator,
+diff -r 9cd90914846f image/decoders/nsJPEGDecoder.cpp
+--- a/image/decoders/nsJPEGDecoder.cpp Thu Feb 27 12:57:14 2020 +0100
++++ b/image/decoders/nsJPEGDecoder.cpp Fri Mar 27 13:06:18 2020 +0100
+@@ -263,6 +263,9 @@
+ case JCS_YCbCr:
+ // By default, we will output directly to BGRA. If we need to apply
+ // special color transforms, this may change.
++#if MOZ_BIG_ENDIAN()
++ mInfo.out_color_space = MOZ_JCS_EXT_NATIVE_ENDIAN_XRGB;
++#else
+ switch (SurfaceFormat::OS_RGBX) {
+ case SurfaceFormat::B8G8R8X8:
+ mInfo.out_color_space = JCS_EXT_BGRX;
+@@ -277,6 +280,7 @@
+ mState = JPEG_ERROR;
+ return Transition::TerminateFailure();
+ }
++#endif
+ break;
+ case JCS_CMYK:
+ case JCS_YCCK:
+diff -r 9cd90914846f image/decoders/nsPNGDecoder.cpp
+--- a/image/decoders/nsPNGDecoder.cpp Thu Feb 27 12:57:14 2020 +0100
++++ b/image/decoders/nsPNGDecoder.cpp Fri Mar 27 13:06:18 2020 +0100
+@@ -361,7 +361,7 @@
+ IResumable* aOnResume) {
+ MOZ_ASSERT(!HasError(), "Shouldn't call DoDecode after error!");
+
+- return mLexer.Lex(aIterator, aOnResume,
++ LexerResult res = mLexer.Lex(aIterator, aOnResume,
+ [=](State aState, const char* aData, size_t aLength) {
+ switch (aState) {
+ case State::PNG_DATA:
+@@ -371,6 +371,14 @@
+ }
+ MOZ_CRASH("Unknown State");
+ });
++
++#if MOZ_BIG_ENDIAN()
++ if(res.is<TerminalState>() && res.as<TerminalState>() == TerminalState::SUCCESS) {
++ NativeEndian::swapToLittleEndianInPlace<uint32_t>((uint32_t*)(mImageData), mImageDataLength / 4);
++ }
++#endif
++
++ return res;
+ }
+
+ LexerTransition<nsPNGDecoder::State> nsPNGDecoder::ReadPNGData(
+diff -r 9cd90914846f image/decoders/nsWebPDecoder.cpp
+--- a/image/decoders/nsWebPDecoder.cpp Thu Feb 27 12:57:14 2020 +0100
++++ b/image/decoders/nsWebPDecoder.cpp Fri Mar 27 13:06:18 2020 +0100
+@@ -237,7 +237,12 @@
+ // WebP doesn't guarantee that the alpha generated matches the hint in the
+ // header, so we always need to claim the input is BGRA. If the output is
+ // BGRX, swizzling will mask off the alpha channel.
++#if MOZ_BIG_ENDIAN()
++ mBuffer.colorspace = MODE_ARGB;
++ SurfaceFormat inFormat = mFormat;
++#else
+ SurfaceFormat inFormat = SurfaceFormat::OS_RGBA;
++#endif
+
+ SurfacePipeFlags pipeFlags = SurfacePipeFlags();
+ if (mFormat == SurfaceFormat::OS_RGBA &&
diff --git a/mozilla-bmo531915.patch b/mozilla-bmo531915.patch
new file mode 100644
index 000000000000..a573a9e6fbe2
--- /dev/null
+++ b/mozilla-bmo531915.patch
@@ -0,0 +1,29 @@
+# HG changeset patch
+# User Wolfgang Rosenauer <wr@rosenauer.org>
+# Parent 7332dfc4c47d73f1b88850b7727d33096d68e329
+
+diff --git a/modules/fdlibm/src/math_private.h b/modules/fdlibm/src/math_private.h
+--- a/modules/fdlibm/src/math_private.h
++++ b/modules/fdlibm/src/math_private.h
+@@ -25,17 +25,21 @@
+
+ #include "mozilla/EndianUtils.h"
+
+ /*
+ * Emulate FreeBSD internal double types.
+ * Adapted from https://github.com/freebsd/freebsd-src/search?q=__double_t
+ */
+
++#ifdef __i386__
++typedef long double __double_t;
++#else
+ typedef double __double_t;
++#endif
+ typedef __double_t double_t;
+
+ /*
+ * The original fdlibm code used statements like:
+ * n0 = ((*(int*)&one)>>29)^1; * index of high word *
+ * ix0 = *(n0+(int*)&x); * high word of x *
+ * ix1 = *((1-n0)+(int*)&x); * low word of x *
+ * to dig two 32 bit words out of the 64 bit IEEE floating point
diff --git a/mozilla-bmo849632.patch b/mozilla-bmo849632.patch
new file mode 100644
index 000000000000..9de64b91ea06
--- /dev/null
+++ b/mozilla-bmo849632.patch
@@ -0,0 +1,35 @@
+# HG changeset patch
+# Parent 3de59fe1b8708c01e134ce698c4232b8a854f617
+Problem: webGL sites are displayed in the wrong color (usually blue-ish)
+Solution: Problem is with skia once again. Output of webgl seems endian-correct, but skia only
+ knows how to deal with little endian.
+ So we swizzle the output of webgl after reading it from readpixels()
+Note: This does not fix all webGL sites, but is a step in the right direction
+
+diff --git a/gfx/gl/GLContext.h b/gfx/gl/GLContext.h
+--- a/gfx/gl/GLContext.h
++++ b/gfx/gl/GLContext.h
+@@ -1548,16 +1548,23 @@ class GLContext : public GenericAtomicRe
+ AFTER_GL_CALL;
+ }
+
+ void raw_fReadPixels(GLint x, GLint y, GLsizei width, GLsizei height,
+ GLenum format, GLenum type, GLvoid* pixels) {
+ BEFORE_GL_CALL;
+ mSymbols.fReadPixels(x, y, width, height, format, type, pixels);
+ OnSyncCall();
++#if MOZ_BIG_ENDIAN()
++ uint8_t* itr = (uint8_t*)pixels;
++ for (GLsizei i = 0; i < width * height; i++) {
++ NativeEndian::swapToLittleEndianInPlace((uint32_t*)itr, 1);
++ itr += 4;
++ }
++#endif
+ AFTER_GL_CALL;
+ mHeavyGLCallsSinceLastFlush = true;
+ }
+
+ void fReadPixels(GLint x, GLint y, GLsizei width, GLsizei height,
+ GLenum format, GLenum type, GLvoid* pixels);
+
+ public:
diff --git a/mozilla-bmo998749.patch b/mozilla-bmo998749.patch
new file mode 100644
index 000000000000..50e22b56946e
--- /dev/null
+++ b/mozilla-bmo998749.patch
@@ -0,0 +1,29 @@
+# HG changeset patch
+# User msirringhaus@suse.de
+# Date 1583738770 -3600
+# Mon Mar 09 08:26:10 2020 +0100
+# Node ID 34676feac1a542e409e22acf5b98735f8313b1ce
+# Parent 506857dace0a08d1c9685e3ac264646590b3e27f
+[mq]: mozilla-bmo998749.patch
+
+diff -r 506857dace0a -r 34676feac1a5 gfx/2d/FilterProcessing.h
+--- a/gfx/2d/FilterProcessing.h Fri Feb 28 12:31:51 2020 +0100
++++ b/gfx/2d/FilterProcessing.h Mon Mar 09 08:26:10 2020 +0100
+@@ -13,10 +13,17 @@
+ namespace mozilla {
+ namespace gfx {
+
++#if MOZ_BIG_ENDIAN()
++const ptrdiff_t B8G8R8A8_COMPONENT_BYTEOFFSET_B = 3;
++const ptrdiff_t B8G8R8A8_COMPONENT_BYTEOFFSET_G = 2;
++const ptrdiff_t B8G8R8A8_COMPONENT_BYTEOFFSET_R = 1;
++const ptrdiff_t B8G8R8A8_COMPONENT_BYTEOFFSET_A = 0;
++#else
+ const ptrdiff_t B8G8R8A8_COMPONENT_BYTEOFFSET_B = 0;
+ const ptrdiff_t B8G8R8A8_COMPONENT_BYTEOFFSET_G = 1;
+ const ptrdiff_t B8G8R8A8_COMPONENT_BYTEOFFSET_R = 2;
+ const ptrdiff_t B8G8R8A8_COMPONENT_BYTEOFFSET_A = 3;
++#endif
+
+ class FilterProcessing {
+ public:
diff --git a/mozilla-fix-top-level-asm.patch b/mozilla-fix-top-level-asm.patch
new file mode 100644
index 000000000000..cb72a15b8447
--- /dev/null
+++ b/mozilla-fix-top-level-asm.patch
@@ -0,0 +1,66 @@
+From 91bb79836ee274855393bdf6ab10e24899b1b349 Mon Sep 17 00:00:00 2001
+From: Martin Liska <mliska@suse.cz>
+Date: Fri, 17 May 2019 14:41:35 +0200
+Subject: [PATCH] Fix top-level asm issue.
+
+---
+ security/sandbox/linux/moz.build | 5 ++++-
+ 1 file changed, 4 insertions(+), 1 deletion(-)
+
+diff --git a/security/sandbox/linux/moz.build b/security/sandbox/linux/moz.build
+--- a/security/sandbox/linux/moz.build
++++ b/security/sandbox/linux/moz.build
+@@ -66,32 +66,32 @@ UNIFIED_SOURCES += [
+ "../chromium/base/time/time_now_posix.cc",
+ "../chromium/sandbox/linux/bpf_dsl/bpf_dsl.cc",
+ "../chromium/sandbox/linux/bpf_dsl/codegen.cc",
+ "../chromium/sandbox/linux/bpf_dsl/dump_bpf.cc",
+ "../chromium/sandbox/linux/bpf_dsl/policy.cc",
+ "../chromium/sandbox/linux/bpf_dsl/policy_compiler.cc",
+ "../chromium/sandbox/linux/bpf_dsl/syscall_set.cc",
+ "../chromium/sandbox/linux/seccomp-bpf/die.cc",
+- "../chromium/sandbox/linux/seccomp-bpf/syscall.cc",
+ "broker/SandboxBrokerCommon.cpp",
+ "Sandbox.cpp",
+ "SandboxBrokerClient.cpp",
+ "SandboxFilter.cpp",
+ "SandboxFilterUtil.cpp",
+ "SandboxHooks.cpp",
+ "SandboxInfo.cpp",
+ "SandboxLogging.cpp",
+ "SandboxOpenedFiles.cpp",
+ "SandboxReporterClient.cpp",
+ ]
+
+ SOURCES += [
+ "../chromium/base/strings/safe_sprintf.cc",
+ "../chromium/base/third_party/icu/icu_utf.cc",
++ "../chromium/sandbox/linux/seccomp-bpf/syscall.cc",
+ "../chromium/sandbox/linux/seccomp-bpf/trap.cc",
+ "../chromium/sandbox/linux/services/syscall_wrappers.cc",
+ ]
+
+ # This copy of SafeSPrintf doesn't need to avoid the Chromium logging
+ # dependency like the one in libxul does, but this way the behavior is
+ # consistent. See also the comment in SandboxLogging.h.
+ SOURCES["../chromium/base/strings/safe_sprintf.cc"].flags += ["-DNDEBUG"]
+@@ -105,16 +105,19 @@ if CONFIG["CC_TYPE"] in ("clang", "gcc")
+ "-Wno-unreachable-code-return"
+ ]
+
+ if CONFIG["CC_TYPE"] in ("clang", "gcc"):
+ CXXFLAGS += ["-Wno-shadow", "-Wno-error=stack-protector"]
+ SOURCES["../chromium/sandbox/linux/services/syscall_wrappers.cc"].flags += [
+ "-Wno-empty-body",
+ ]
++ SOURCES['../chromium/sandbox/linux/seccomp-bpf/syscall.cc'].flags += [
++ '-fno-lto'
++ ]
+
+ # gcc lto likes to put the top level asm in syscall.cc in a different partition
+ # from the function using it which breaks the build. Work around that by
+ # forcing there to be only one partition.
+ for f in CONFIG["OS_CXXFLAGS"]:
+ if f.startswith("-flto") and CONFIG["CC_TYPE"] != "clang":
+ LDFLAGS += ["--param lto-partitions=1"]
+
diff --git a/mozilla-kde.patch b/mozilla-kde.patch
new file mode 100644
index 000000000000..32e7fe439258
--- /dev/null
+++ b/mozilla-kde.patch
@@ -0,0 +1,1931 @@
+# HG changeset patch
+# User msirringhaus@suse.de
+# Date 1559294891 -7200
+# Fri May 31 11:28:11 2019 +0200
+# Node ID c2aa7198fb925e7fde96abf65b6f68b9b755f112
+# Parent 0dd1b6436342922d434e7c818875b2a02a73b5ed
+Description: Add KDE integration to Firefox (toolkit parts)
+Author: Wolfgang Rosenauer <wolfgang@rosenauer.org>
+Author: Lubos Lunak <lunak@suse.com>
+Bug: https://bugzilla.mozilla.org/show_bug.cgi?id=140751
+ https://bugzilla.novell.com/show_bug.cgi?id=170055
+
+diff --git a/modules/libpref/Preferences.cpp b/modules/libpref/Preferences.cpp
+--- a/modules/libpref/Preferences.cpp
++++ b/modules/libpref/Preferences.cpp
+@@ -84,16 +84,17 @@
+ #include "plbase64.h"
+ #include "PLDHashTable.h"
+ #include "plstr.h"
+ #include "prlink.h"
+ #include "xpcpublic.h"
+ #ifdef MOZ_BACKGROUNDTASKS
+ # include "mozilla/BackgroundTasks.h"
+ #endif
++#include "nsKDEUtils.h"
+
+ #ifdef DEBUG
+ # include <map>
+ #endif
+
+ #ifdef MOZ_MEMORY
+ # include "mozmemory.h"
+ #endif
+@@ -4634,16 +4635,27 @@ nsresult Preferences::InitInitialObjects
+ "unix.js"
+ # if defined(_AIX)
+ ,
+ "aix.js"
+ # endif
+ #endif
+ };
+
++ if(nsKDEUtils::kdeSession()) { // TODO what if some setup actually requires the helper?
++ for(int i = 0;
++ i < MOZ_ARRAY_LENGTH(specialFiles);
++ ++i ) {
++ if( *specialFiles[ i ] == '\0' ) {
++ specialFiles[ i ] = "kde.js";
++ break;
++ }
++ }
++ }
++
+ rv = pref_LoadPrefsInDir(defaultPrefDir, specialFiles,
+ ArrayLength(specialFiles));
+ if (NS_FAILED(rv)) {
+ NS_WARNING("Error parsing application default preferences.");
+ }
+
+ // Load jar:$app/omni.jar!/defaults/preferences/*.js
+ // or jar:$gre/omni.jar!/defaults/preferences/*.js.
+@@ -4708,17 +4720,17 @@ nsresult Preferences::InitInitialObjects
+ }
+
+ nsCOMPtr<nsIFile> path = do_QueryInterface(elem);
+ if (!path) {
+ continue;
+ }
+
+ // Do we care if a file provided by this process fails to load?
+- pref_LoadPrefsInDir(path, nullptr, 0);
++ pref_LoadPrefsInDir(path, specialFiles, ArrayLength(specialFiles));
+ }
+ }
+
+ if (XRE_IsParentProcess()) {
+ SetupTelemetryPref();
+ }
+
+ if (aIsStartup) {
+diff --git a/modules/libpref/moz.build b/modules/libpref/moz.build
+--- a/modules/libpref/moz.build
++++ b/modules/libpref/moz.build
+@@ -118,16 +118,20 @@ EXPORTS.mozilla += [
+ ]
+ EXPORTS.mozilla += sorted(["!" + g for g in gen_h])
+
+ UNIFIED_SOURCES += [
+ "Preferences.cpp",
+ "SharedPrefMap.cpp",
+ ]
+
++LOCAL_INCLUDES += [
++ '/toolkit/xre'
++]
++
+ gen_all_tuple = tuple(gen_h + gen_cpp + gen_rs)
+
+ GeneratedFile(
+ *gen_all_tuple,
+ script="init/generate_static_pref_list.py",
+ entry_point="emit_code",
+ inputs=["init/StaticPrefList.yaml"]
+ )
+diff --git a/python/mozbuild/mozpack/chrome/flags.py b/python/mozbuild/mozpack/chrome/flags.py
+--- a/python/mozbuild/mozpack/chrome/flags.py
++++ b/python/mozbuild/mozpack/chrome/flags.py
+@@ -229,16 +229,17 @@ class Flags(OrderedDict):
+ "os": StringFlag,
+ "osversion": VersionFlag,
+ "abi": StringFlag,
+ "platform": Flag,
+ "xpcnativewrappers": Flag,
+ "tablet": Flag,
+ "process": StringFlag,
+ "backgroundtask": StringFlag,
++ "desktop": StringFlag,
+ }
+ RE = re.compile(r"([!<>=]+)")
+
+ def __init__(self, *flags):
+ """
+ Initialize a set of flags given in string form.
+ flags = Flags('contentaccessible=yes', 'appversion>=3.5')
+ """
+diff --git a/python/mozbuild/mozpack/chrome/manifest.py b/python/mozbuild/mozpack/chrome/manifest.py
+--- a/python/mozbuild/mozpack/chrome/manifest.py
++++ b/python/mozbuild/mozpack/chrome/manifest.py
+@@ -39,16 +39,17 @@ class ManifestEntry(object):
+ "os",
+ "osversion",
+ "abi",
+ "xpcnativewrappers",
+ "tablet",
+ "process",
+ "contentaccessible",
+ "backgroundtask",
++ "desktop",
+ ]
+
+ def __init__(self, base, *flags):
+ """
+ Initialize a manifest entry with the given base path and flags.
+ """
+ self.base = base
+ self.flags = Flags(*flags)
+diff --git a/toolkit/components/downloads/moz.build b/toolkit/components/downloads/moz.build
+--- a/toolkit/components/downloads/moz.build
++++ b/toolkit/components/downloads/moz.build
+@@ -45,10 +45,14 @@ XPCOM_MANIFESTS += [
+
+ if CONFIG["MOZ_PLACES"]:
+ EXTRA_JS_MODULES += [
+ "DownloadHistory.jsm",
+ ]
+
+ FINAL_LIBRARY = "xul"
+
++LOCAL_INCLUDES += [
++ '/toolkit/xre'
++]
++
+ with Files("**"):
+ BUG_COMPONENT = ("Toolkit", "Downloads API")
+diff --git a/toolkit/mozapps/downloads/HelperAppDlg.jsm b/toolkit/mozapps/downloads/HelperAppDlg.jsm
+--- a/toolkit/mozapps/downloads/HelperAppDlg.jsm
++++ b/toolkit/mozapps/downloads/HelperAppDlg.jsm
+@@ -1231,36 +1231,66 @@ nsUnknownContentTypeDialog.prototype = {
+ params.handlerApp &&
+ params.handlerApp.executable &&
+ params.handlerApp.executable.isFile()
+ ) {
+ // Remember the file they chose to run.
+ this.chosenApp = params.handlerApp;
+ }
+ } else if ("@mozilla.org/applicationchooser;1" in Cc) {
+- var nsIApplicationChooser = Ci.nsIApplicationChooser;
+- var appChooser = Cc["@mozilla.org/applicationchooser;1"].createInstance(
+- nsIApplicationChooser
+- );
+- appChooser.init(
+- this.mDialog,
+- this.dialogElement("strings").getString("chooseAppFilePickerTitle")
+- );
+- var contentTypeDialogObj = this;
+- let appChooserCallback = function appChooserCallback_done(aResult) {
+- if (aResult) {
+- contentTypeDialogObj.chosenApp = aResult.QueryInterface(
+- Ci.nsILocalHandlerApp
+- );
+- }
+- contentTypeDialogObj.finishChooseApp();
+- };
+- appChooser.open(this.mLauncher.MIMEInfo.MIMEType, appChooserCallback);
+- // The finishChooseApp is called from appChooserCallback
+- return;
++ // handle the KDE case which is implemented in the filepicker
++ // therefore falling back to Gtk2 like behaviour if KDE is running
++ // FIXME this should be better handled in the nsIApplicationChooser
++ // interface
++ var env = Components.classes["@mozilla.org/process/environment;1"]
++ .getService(Components.interfaces.nsIEnvironment);
++ if (env.get('KDE_FULL_SESSION') == "true")
++ {
++ var nsIFilePicker = Ci.nsIFilePicker;
++ var fp = Cc["@mozilla.org/filepicker;1"]
++ .createInstance(nsIFilePicker);
++ fp.init(this.mDialog,
++ this.dialogElement("strings").getString("chooseAppFilePickerTitle"),
++ nsIFilePicker.modeOpen);
++
++ fp.appendFilters(nsIFilePicker.filterApps);
++
++ fp.open(aResult => {
++ if (aResult == nsIFilePicker.returnOK && fp.file) {
++ // Remember the file they chose to run.
++ var localHandlerApp =
++ Cc["@mozilla.org/uriloader/local-handler-app;1"].
++ createInstance(Ci.nsILocalHandlerApp);
++ localHandlerApp.executable = fp.file;
++ this.chosenApp = localHandlerApp;
++ }
++ this.finishChooseApp();
++ });
++ } else {
++ var nsIApplicationChooser = Ci.nsIApplicationChooser;
++ var appChooser = Cc["@mozilla.org/applicationchooser;1"].createInstance(
++ nsIApplicationChooser
++ );
++ appChooser.init(
++ this.mDialog,
++ this.dialogElement("strings").getString("chooseAppFilePickerTitle")
++ );
++ var contentTypeDialogObj = this;
++ let appChooserCallback = function appChooserCallback_done(aResult) {
++ if (aResult) {
++ contentTypeDialogObj.chosenApp = aResult.QueryInterface(
++ Ci.nsILocalHandlerApp
++ );
++ }
++ contentTypeDialogObj.finishChooseApp();
++ };
++ appChooser.open(this.mLauncher.MIMEInfo.MIMEType, appChooserCallback);
++ // The finishChooseApp is called from appChooserCallback
++ return;
++ }
+ } else {
+ var nsIFilePicker = Ci.nsIFilePicker;
+ var fp = Cc["@mozilla.org/filepicker;1"].createInstance(nsIFilePicker);
+ fp.init(
+ this.mDialog,
+ this.dialogElement("strings").getString("chooseAppFilePickerTitle"),
+ nsIFilePicker.modeOpen
+ );
+diff --git a/toolkit/system/unixproxy/nsUnixSystemProxySettings.cpp b/toolkit/system/unixproxy/nsUnixSystemProxySettings.cpp
+--- a/toolkit/system/unixproxy/nsUnixSystemProxySettings.cpp
++++ b/toolkit/system/unixproxy/nsUnixSystemProxySettings.cpp
+@@ -13,16 +13,17 @@
+ #include "nsPrintfCString.h"
+ #include "nsNetCID.h"
+ #include "nsNetUtil.h"
+ #include "nsISupportsPrimitives.h"
+ #include "nsIGSettingsService.h"
+ #include "nsInterfaceHashtable.h"
+ #include "mozilla/Attributes.h"
+ #include "nsIURI.h"
++#include "nsKDEUtils.h"
+
+ using namespace mozilla;
+
+ class nsUnixSystemProxySettings final : public nsISystemProxySettings {
+ public:
+ NS_DECL_ISUPPORTS
+ NS_DECL_NSISYSTEMPROXYSETTINGS
+
+@@ -36,16 +37,18 @@ class nsUnixSystemProxySettings final :
+ nsCOMPtr<nsIGSettingsCollection> mProxySettings;
+ nsInterfaceHashtable<nsCStringHashKey, nsIGSettingsCollection>
+ mSchemeProxySettings;
+ nsresult GetProxyFromGSettings(const nsACString& aScheme,
+ const nsACString& aHost, int32_t aPort,
+ nsACString& aResult);
+ nsresult SetProxyResultFromGSettings(const char* aKeyBase, const char* aType,
+ nsACString& aResult);
++ nsresult GetProxyFromKDE(const nsACString& aScheme, const nsACString& aHost,
++ PRInt32 aPort, nsACString& aResult);
+ };
+
+ NS_IMPL_ISUPPORTS(nsUnixSystemProxySettings, nsISystemProxySettings)
+
+ NS_IMETHODIMP
+ nsUnixSystemProxySettings::GetMainThreadOnly(bool* aMainThreadOnly) {
+ // dbus prevents us from being threadsafe, but this routine should not block
+ // anyhow
+@@ -381,21 +384,50 @@ nsresult nsUnixSystemProxySettings::GetP
+ return NS_OK;
+ }
+
+ nsresult nsUnixSystemProxySettings::GetProxyForURI(const nsACString& aSpec,
+ const nsACString& aScheme,
+ const nsACString& aHost,
+ const int32_t aPort,
+ nsACString& aResult) {
++ if (nsKDEUtils::kdeSupport())
++ return GetProxyFromKDE(aScheme, aHost, aPort, aResult);
++
+ if (mProxySettings) {
+ nsresult rv = GetProxyFromGSettings(aScheme, aHost, aPort, aResult);
+ if (NS_SUCCEEDED(rv)) return rv;
+ }
+
+ return GetProxyFromEnvironment(aScheme, aHost, aPort, aResult);
+ }
+
++nsresult
++nsUnixSystemProxySettings::GetProxyFromKDE(const nsACString& aScheme,
++ const nsACString& aHost,
++ PRInt32 aPort,
++ nsACString& aResult)
++{
++ nsAutoCString url;
++ url = aScheme;
++ url += "://";
++ url += aHost;
++ if( aPort >= 0 )
++ {
++ url += ":";
++ url += nsPrintfCString("%d", aPort);
++ }
++ nsTArray<nsCString> command;
++ command.AppendElement( "GETPROXY"_ns );
++ command.AppendElement( url );
++ nsTArray<nsCString> result;
++ if( !nsKDEUtils::command( command, &result ) || result.Length() != 1 )
++ return NS_ERROR_FAILURE;
++ aResult = result[0];
++ return NS_OK;
++}
++
++
+ NS_IMPL_COMPONENT_FACTORY(nsUnixSystemProxySettings) {
+ auto result = MakeRefPtr<nsUnixSystemProxySettings>();
+ result->Init();
+ return result.forget().downcast<nsISupports>();
+ }
+diff --git a/toolkit/xre/moz.build b/toolkit/xre/moz.build
+--- a/toolkit/xre/moz.build
++++ b/toolkit/xre/moz.build
+@@ -91,17 +91,19 @@ elif CONFIG["MOZ_WIDGET_TOOLKIT"] == "co
+ "../components/printingui",
+ ]
+ elif CONFIG["MOZ_WIDGET_TOOLKIT"] == "uikit":
+ UNIFIED_SOURCES += [
+ "nsNativeAppSupportDefault.cpp",
+ "UIKitDirProvider.mm",
+ ]
+ elif CONFIG["MOZ_WIDGET_TOOLKIT"] == "gtk":
++ EXPORTS += ['nsKDEUtils.h']
+ UNIFIED_SOURCES += [
++ "nsKDEUtils.cpp",
+ "nsNativeAppSupportUnix.cpp",
+ ]
+ else:
+ UNIFIED_SOURCES += [
+ "nsNativeAppSupportDefault.cpp",
+ ]
+
+ if CONFIG["MOZ_HAS_REMOTE"]:
+diff --git a/toolkit/xre/nsKDEUtils.cpp b/toolkit/xre/nsKDEUtils.cpp
+new file mode 100644
+--- /dev/null
++++ b/toolkit/xre/nsKDEUtils.cpp
+@@ -0,0 +1,344 @@
++/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
++/* This Source Code Form is subject to the terms of the Mozilla Public
++ * License, v. 2.0. If a copy of the MPL was not distributed with this
++ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
++
++#include "nsKDEUtils.h"
++#include "nsIWidget.h"
++#include "nsISupportsPrimitives.h"
++#include "nsIMutableArray.h"
++#include "nsComponentManagerUtils.h"
++#include "nsArrayUtils.h"
++
++#include <gtk/gtk.h>
++
++#include <limits.h>
++#include <stdio.h>
++#include <sys/wait.h>
++#include <sys/resource.h>
++#include <unistd.h>
++#include <X11/Xlib.h>
++// copied from X11/X.h as a hack since for an unknown
++// reason it's not picked up from X11/X.h
++#ifndef None
++#define None 0L /* universal null resource or null atom */
++#endif
++
++//#define DEBUG_KDE
++#ifdef DEBUG_KDE
++#define KMOZILLAHELPER "kmozillahelper"
++#else
++// not need for lib64, it's a binary
++#define KMOZILLAHELPER "/usr/lib/mozilla/kmozillahelper"
++#endif
++
++#define KMOZILLAHELPER_VERSION 6
++#define MAKE_STR2( n ) #n
++#define MAKE_STR( n ) MAKE_STR2( n )
++
++static bool getKdeSession()
++ {
++ Display* dpy = XOpenDisplay( NULL );
++ if( dpy == NULL )
++ return false;
++ Atom kde_full_session = XInternAtom( dpy, "KDE_FULL_SESSION", true );
++ bool kde = false;
++ if( kde_full_session != None )
++ {
++ int cnt;
++ if( Atom* props = XListProperties( dpy, DefaultRootWindow( dpy ), &cnt ))
++ {
++ for( int i = 0;
++ i < cnt;
++ ++i )
++ {
++ if( props[ i ] == kde_full_session )
++ {
++ kde = true;
++#ifdef DEBUG_KDE
++ fprintf( stderr, "KDE SESSION %d\n", kde );
++#endif
++ break;
++ }
++ }
++ XFree( props );
++ }
++ }
++ XCloseDisplay( dpy );
++ return kde;
++ }
++
++static bool getKdeSupport()
++ {
++ nsTArray<nsCString> command;
++ command.AppendElement( "CHECK"_ns );
++ command.AppendElement( "KMOZILLAHELPER_VERSION"_ns );
++ bool kde = nsKDEUtils::command( command );
++#ifdef DEBUG_KDE
++ fprintf( stderr, "KDE RUNNING %d\n", kde );
++#endif
++ return kde;
++ }
++
++nsKDEUtils::nsKDEUtils()
++ : commandFile( NULL )
++ , replyFile( NULL )
++ {
++ }
++
++nsKDEUtils::~nsKDEUtils()
++ {
++// closeHelper(); not actually useful, exiting will close the fd too
++ }
++
++nsKDEUtils* nsKDEUtils::self()
++ {
++ static nsKDEUtils s;
++ return &s;
++ }
++
++static bool helperRunning = false;
++static bool helperFailed = false;
++
++bool nsKDEUtils::kdeSession()
++ {
++ static bool session = getKdeSession();
++ return session;
++ }
++
++bool nsKDEUtils::kdeSupport()
++ {
++ static bool support = kdeSession() && getKdeSupport();
++ return support && helperRunning;
++ }
++
++struct nsKDECommandData
++ {
++ FILE* file;
++ nsTArray<nsCString>* output;
++ GMainLoop* loop;
++ bool success;
++ };
++
++static gboolean kdeReadFunc( GIOChannel*, GIOCondition, gpointer data )
++ {
++ nsKDECommandData* p = static_cast< nsKDECommandData* >( data );
++ char buf[ 8192 ]; // TODO big enough
++ bool command_done = false;
++ bool command_failed = false;
++ while( !command_done && !command_failed && fgets( buf, 8192, p->file ) != NULL )
++ { // TODO what if the kernel splits a line into two chunks?
++//#ifdef DEBUG_KDE
++// fprintf( stderr, "READ: %s %d\n", buf, feof( p->file ));
++//#endif
++ if( char* eol = strchr( buf, '\n' ))
++ *eol = '\0';
++ command_done = ( strcmp( buf, "\\1" ) == 0 );
++ command_failed = ( strcmp( buf, "\\0" ) == 0 );
++ nsAutoCString line( buf );
++ line.ReplaceSubstring( "\\n", "\n" );
++ line.ReplaceSubstring( "\\" "\\", "\\" ); // \\ -> \ , i.e. unescape
++ if( p->output && !( command_done || command_failed ))
++ p->output->AppendElement( nsCString( buf )); // TODO utf8?
++ }
++ bool quit = false;
++ if( feof( p->file ) || command_failed )
++ {
++ quit = true;
++ p->success = false;
++ }
++ if( command_done )
++ { // reading one reply finished
++ quit = true;
++ p->success = true;
++ }
++ if( quit )
++ {
++ if( p->loop )
++ g_main_loop_quit( p->loop );
++ return FALSE;
++ }
++ return TRUE;
++ }
++
++bool nsKDEUtils::command( const nsTArray<nsCString>& command, nsTArray<nsCString>* output )
++ {
++ return self()->internalCommand( command, NULL, false, output );
++ }
++
++bool nsKDEUtils::command( nsIArray* command, nsIArray** output)
++ {
++ nsTArray<nsCString> in;
++ PRUint32 length;
++ command->GetLength( &length );
++ for ( PRUint32 i = 0; i < length; i++ )
++ {
++ nsCOMPtr<nsISupportsCString> str = do_QueryElementAt( command, i );
++ if( str )
++ {
++ nsAutoCString s;
++ str->GetData( s );
++ in.AppendElement( s );
++ }
++ }
++
++ nsTArray<nsCString> out;
++ bool ret = self()->internalCommand( in, NULL, false, &out );
++
++ if ( !output ) return ret;
++
++ nsCOMPtr<nsIMutableArray> result = do_CreateInstance( NS_ARRAY_CONTRACTID );
++ if ( !result ) return false;
++
++ for ( PRUint32 i = 0; i < out.Length(); i++ )
++ {
++ nsCOMPtr<nsISupportsCString> rstr = do_CreateInstance( NS_SUPPORTS_CSTRING_CONTRACTID );
++ if ( !rstr ) return false;
++
++ rstr->SetData( out[i] );
++ result->AppendElement( rstr );
++ }
++
++ NS_ADDREF( *output = result);
++ return ret;
++ }
++
++
++bool nsKDEUtils::commandBlockUi( const nsTArray<nsCString>& command, GtkWindow* parent, nsTArray<nsCString>* output )
++ {
++ return self()->internalCommand( command, parent, true, output );
++ }
++
++bool nsKDEUtils::internalCommand( const nsTArray<nsCString>& command, GtkWindow* parent, bool blockUi,
++ nsTArray<nsCString>* output )
++ {
++ if( !startHelper())
++ return false;
++ feedCommand( command );
++ // do not store the data in 'this' but in extra structure, just in case there
++ // is reentrancy (can there be? the event loop is re-entered)
++ nsKDECommandData data;
++ data.file = replyFile;
++ data.output = output;
++ data.success = false;
++ if( blockUi )
++ {
++ data.loop = g_main_loop_new( NULL, FALSE );
++ GtkWidget* window = gtk_window_new( GTK_WINDOW_TOPLEVEL );
++ if( parent && gtk_window_get_group(parent) )
++ gtk_window_group_add_window( gtk_window_get_group(parent), GTK_WINDOW( window ));
++ gtk_widget_realize( window );
++ gtk_widget_set_sensitive( window, TRUE );
++ gtk_grab_add( window );
++ GIOChannel* channel = g_io_channel_unix_new( fileno( data.file ));
++ g_io_add_watch( channel, static_cast< GIOCondition >( G_IO_IN | G_IO_ERR | G_IO_HUP ), kdeReadFunc, &data );
++ g_io_channel_unref( channel );
++ g_main_loop_run( data.loop );
++ g_main_loop_unref( data.loop );
++ gtk_grab_remove( window );
++ gtk_widget_destroy( window );
++ }
++ else
++ {
++ data.loop = NULL;
++ while( kdeReadFunc( NULL, static_cast< GIOCondition >( 0 ), &data ))
++ ;
++ }
++ return data.success;
++ }
++
++bool nsKDEUtils::startHelper()
++ {
++ if( helperRunning )
++ return true;
++ if( helperFailed )
++ return false;
++ helperFailed = true;
++ int fdcommand[ 2 ];
++ int fdreply[ 2 ];
++ if( pipe( fdcommand ) < 0 )
++ return false;
++ if( pipe( fdreply ) < 0 )
++ {
++ close( fdcommand[ 0 ] );
++ close( fdcommand[ 1 ] );
++ return false;
++ }
++ char* args[ 2 ] = { const_cast< char* >( KMOZILLAHELPER ), NULL };
++ switch( fork())
++ {
++ case -1:
++ {
++ close( fdcommand[ 0 ] );
++ close( fdcommand[ 1 ] );
++ close( fdreply[ 0 ] );
++ close( fdreply[ 1 ] );
++ return false;
++ }
++ case 0: // child
++ {
++ if( dup2( fdcommand[ 0 ], STDIN_FILENO ) < 0 )
++ _exit( 1 );
++ if( dup2( fdreply[ 1 ], STDOUT_FILENO ) < 0 )
++ _exit( 1 );
++ int maxfd = 1024; // close all other fds
++ struct rlimit rl;
++ if( getrlimit( RLIMIT_NOFILE, &rl ) == 0 )
++ maxfd = rl.rlim_max;
++ for( int i = 3;
++ i < maxfd;
++ ++i )
++ close( i );
++#ifdef DEBUG_KDE
++ execvp( KMOZILLAHELPER, args );
++#else
++ execv( KMOZILLAHELPER, args );
++#endif
++ _exit( 1 ); // failed
++ }
++ default: // parent
++ {
++ commandFile = fdopen( fdcommand[ 1 ], "w" );
++ replyFile = fdopen( fdreply[ 0 ], "r" );
++ close( fdcommand[ 0 ] );
++ close( fdreply[ 1 ] );
++ if( commandFile == NULL || replyFile == NULL )
++ {
++ closeHelper();
++ return false;
++ }
++ // ok, helper ready, getKdeRunning() will check if it works
++ }
++ }
++ helperFailed = false;
++ helperRunning = true;
++ return true;
++ }
++
++void nsKDEUtils::closeHelper()
++ {
++ if( commandFile != NULL )
++ fclose( commandFile ); // this will also make the helper quit
++ if( replyFile != NULL )
++ fclose( replyFile );
++ helperRunning = false;
++ }
++
++void nsKDEUtils::feedCommand( const nsTArray<nsCString>& command )
++ {
++ for( int i = 0;
++ i < command.Length();
++ ++i )
++ {
++ nsCString line = command[ i ];
++ line.ReplaceSubstring( "\\", "\\" "\\" ); // \ -> \\ , i.e. escape
++ line.ReplaceSubstring( "\n", "\\n" );
++#ifdef DEBUG_KDE
++ fprintf( stderr, "COMM: %s\n", line.get());
++#endif
++ fputs( line.get(), commandFile );
++ fputs( "\n", commandFile );
++ }
++ fputs( "\\E\n", commandFile ); // done as \E, so it cannot happen in normal data
++ fflush( commandFile );
++ }
+diff --git a/toolkit/xre/nsKDEUtils.h b/toolkit/xre/nsKDEUtils.h
+new file mode 100644
+--- /dev/null
++++ b/toolkit/xre/nsKDEUtils.h
+@@ -0,0 +1,48 @@
++/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
++/* This Source Code Form is subject to the terms of the Mozilla Public
++ * License, v. 2.0. If a copy of the MPL was not distributed with this
++ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
++
++#ifndef nsKDEUtils_h__
++#define nsKDEUtils_h__
++
++#include "nsString.h"
++#include "nsTArray.h"
++#include <stdio.h>
++
++typedef struct _GtkWindow GtkWindow;
++
++class nsIArray;
++
++class NS_EXPORT nsKDEUtils
++ {
++ public:
++ /* Returns true if running inside a KDE session (regardless of whether there is KDE
++ support available for Firefox). This should be used e.g. when determining
++ dialog button order but not for code that requires the KDE support. */
++ static bool kdeSession();
++ /* Returns true if running inside a KDE session and KDE support is available
++ for Firefox. This should be used everywhere where the external helper is needed. */
++ static bool kdeSupport();
++ /* Executes the given helper command, returns true if helper returned success. */
++ static bool command( const nsTArray<nsCString>& command, nsTArray<nsCString>* output = NULL );
++ static bool command( nsIArray* command, nsIArray** output = NULL );
++ /* Like command(), but additionally blocks the parent widget like if there was
++ a modal dialog shown and enters the event loop (i.e. there are still paint updates,
++ this is for commands that take long). */
++ static bool commandBlockUi( const nsTArray<nsCString>& command, GtkWindow* parent, nsTArray<nsCString>* output = NULL );
++
++ private:
++ nsKDEUtils();
++ ~nsKDEUtils();
++ static nsKDEUtils* self();
++ bool startHelper();
++ void closeHelper();
++ void feedCommand( const nsTArray<nsCString>& command );
++ bool internalCommand( const nsTArray<nsCString>& command, GtkWindow* parent, bool isParent,
++ nsTArray<nsCString>* output );
++ FILE* commandFile;
++ FILE* replyFile;
++ };
++
++#endif // nsKDEUtils
+diff --git a/uriloader/exthandler/HandlerServiceParent.cpp b/uriloader/exthandler/HandlerServiceParent.cpp
+--- a/uriloader/exthandler/HandlerServiceParent.cpp
++++ b/uriloader/exthandler/HandlerServiceParent.cpp
+@@ -7,17 +7,17 @@
+ #include "mozilla/ipc/ProtocolUtils.h"
+ #include "mozilla/Logging.h"
+ #include "HandlerServiceParent.h"
+ #include "nsIHandlerService.h"
+ #include "nsIMIMEInfo.h"
+ #include "ContentHandlerService.h"
+ #include "nsStringEnumerator.h"
+ #ifdef MOZ_WIDGET_GTK
+-# include "unix/nsGNOMERegistry.h"
++# include "unix/nsCommonRegistry.h"
+ #endif
+
+ using mozilla::dom::ContentHandlerService;
+ using mozilla::dom::HandlerApp;
+ using mozilla::dom::HandlerInfo;
+ using mozilla::dom::RemoteHandlerApp;
+
+ namespace {
+@@ -299,17 +299,17 @@ mozilla::ipc::IPCResult HandlerServicePa
+ mozilla::ipc::IPCResult HandlerServiceParent::RecvExistsForProtocolOS(
+ const nsCString& aProtocolScheme, bool* aHandlerExists) {
+ if (aProtocolScheme.Length() > MAX_SCHEME_LENGTH) {
+ *aHandlerExists = false;
+ return IPC_OK();
+ }
+ #ifdef MOZ_WIDGET_GTK
+ // Check the GNOME registry for a protocol handler
+- *aHandlerExists = nsGNOMERegistry::HandlerExists(aProtocolScheme.get());
++ *aHandlerExists = nsCommonRegistry::HandlerExists(aProtocolScheme.get());
+ #else
+ *aHandlerExists = false;
+ #endif
+ return IPC_OK();
+ }
+
+ /*
+ * Check if a handler exists for the provided protocol. Check the datastore
+@@ -328,17 +328,17 @@ mozilla::ipc::IPCResult HandlerServicePa
+ nsCOMPtr<nsIExternalProtocolService> protoSvc =
+ do_GetService(NS_EXTERNALPROTOCOLSERVICE_CONTRACTID, &rv);
+ if (NS_WARN_IF(NS_FAILED(rv))) {
+ *aHandlerExists = false;
+ return IPC_OK();
+ }
+ rv = protoSvc->ExternalProtocolHandlerExists(aProtocolScheme.get(),
+ aHandlerExists);
+-
++##
+ if (NS_WARN_IF(NS_FAILED(rv))) {
+ *aHandlerExists = false;
+ }
+ #else
+ MOZ_RELEASE_ASSERT(false, "No implementation on this platform.");
+ *aHandlerExists = false;
+ #endif
+ return IPC_OK();
+diff --git a/uriloader/exthandler/moz.build b/uriloader/exthandler/moz.build
+--- a/uriloader/exthandler/moz.build
++++ b/uriloader/exthandler/moz.build
+@@ -80,17 +80,19 @@ else:
+ SOURCES += [
+ osdir + "/nsOSHelperAppService.cpp",
+ ]
+ if CONFIG["CC_TYPE"] in ("clang", "gcc"):
+ CXXFLAGS += ["-Wno-error=shadow"]
+
+ if CONFIG["MOZ_WIDGET_TOOLKIT"] == "gtk":
+ UNIFIED_SOURCES += [
++ "unix/nsCommonRegistry.cpp",
+ "unix/nsGNOMERegistry.cpp",
++ "unix/nsKDERegistry.cpp",
+ "unix/nsMIMEInfoUnix.cpp",
+ ]
+ elif CONFIG["MOZ_WIDGET_TOOLKIT"] == "android":
+ UNIFIED_SOURCES += [
+ "android/nsMIMEInfoAndroid.cpp",
+ ]
+ elif CONFIG["MOZ_WIDGET_TOOLKIT"] == "windows":
+ UNIFIED_SOURCES += [
+@@ -128,16 +130,17 @@ include("/ipc/chromium/chromium-config.m
+ FINAL_LIBRARY = "xul"
+
+ LOCAL_INCLUDES += [
+ "/docshell/base",
+ "/dom/base",
+ "/dom/ipc",
+ "/netwerk/base",
+ "/netwerk/protocol/http",
++ "/toolkit/xre",
+ ]
+
+ if CONFIG["MOZ_ENABLE_DBUS"]:
+ CXXFLAGS += CONFIG["TK_CFLAGS"]
+ CXXFLAGS += CONFIG["MOZ_DBUS_CFLAGS"]
+
+ if CONFIG["MOZ_WIDGET_TOOLKIT"] == "gtk":
+ CXXFLAGS += CONFIG["TK_CFLAGS"]
+diff --git a/uriloader/exthandler/unix/nsCommonRegistry.cpp b/uriloader/exthandler/unix/nsCommonRegistry.cpp
+new file mode 100644
+--- /dev/null
++++ b/uriloader/exthandler/unix/nsCommonRegistry.cpp
+@@ -0,0 +1,53 @@
++/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
++/* This Source Code Form is subject to the terms of the Mozilla Public
++ * License, v. 2.0. If a copy of the MPL was not distributed with this
++ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
++
++#include "nsCommonRegistry.h"
++
++#include "nsGNOMERegistry.h"
++#include "nsKDERegistry.h"
++#include "nsString.h"
++#include "nsKDEUtils.h"
++
++/* static */ bool
++nsCommonRegistry::HandlerExists(const char *aProtocolScheme)
++{
++ if( nsKDEUtils::kdeSupport())
++ return nsKDERegistry::HandlerExists( aProtocolScheme );
++ return nsGNOMERegistry::HandlerExists( aProtocolScheme );
++}
++
++/* static */ nsresult
++nsCommonRegistry::LoadURL(nsIURI *aURL)
++{
++ if( nsKDEUtils::kdeSupport())
++ return nsKDERegistry::LoadURL( aURL );
++ return nsGNOMERegistry::LoadURL( aURL );
++}
++
++/* static */ void
++nsCommonRegistry::GetAppDescForScheme(const nsACString& aScheme,
++ nsAString& aDesc)
++{
++ if( nsKDEUtils::kdeSupport())
++ return nsKDERegistry::GetAppDescForScheme( aScheme, aDesc );
++ return nsGNOMERegistry::GetAppDescForScheme( aScheme, aDesc );
++}
++
++
++/* static */ already_AddRefed<nsMIMEInfoBase>
++nsCommonRegistry::GetFromExtension(const nsACString& aFileExt)
++{
++ if( nsKDEUtils::kdeSupport())
++ return nsKDERegistry::GetFromExtension( aFileExt );
++ return nsGNOMERegistry::GetFromExtension( aFileExt );
++}
++
++/* static */ already_AddRefed<nsMIMEInfoBase>
++nsCommonRegistry::GetFromType(const nsACString& aMIMEType)
++{
++ if( nsKDEUtils::kdeSupport())
++ return nsKDERegistry::GetFromType( aMIMEType );
++ return nsGNOMERegistry::GetFromType( aMIMEType );
++}
+diff --git a/uriloader/exthandler/unix/nsCommonRegistry.h b/uriloader/exthandler/unix/nsCommonRegistry.h
+new file mode 100644
+--- /dev/null
++++ b/uriloader/exthandler/unix/nsCommonRegistry.h
+@@ -0,0 +1,28 @@
++/* This Source Code Form is subject to the terms of the Mozilla Public
++ * License, v. 2.0. If a copy of the MPL was not distributed with this
++ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
++
++#ifndef nsCommonRegistry_h__
++#define nsCommonRegistry_h__
++
++#include "nsIURI.h"
++#include "nsCOMPtr.h"
++
++class nsMIMEInfoBase;
++
++class nsCommonRegistry
++{
++ public:
++ static bool HandlerExists(const char *aProtocolScheme);
++
++ static nsresult LoadURL(nsIURI *aURL);
++
++ static void GetAppDescForScheme(const nsACString& aScheme,
++ nsAString& aDesc);
++
++ static already_AddRefed<nsMIMEInfoBase> GetFromExtension(const nsACString& aFileExt);
++
++ static already_AddRefed<nsMIMEInfoBase> GetFromType(const nsACString& aMIMEType);
++};
++
++#endif
+diff --git a/uriloader/exthandler/unix/nsKDERegistry.cpp b/uriloader/exthandler/unix/nsKDERegistry.cpp
+new file mode 100644
+--- /dev/null
++++ b/uriloader/exthandler/unix/nsKDERegistry.cpp
+@@ -0,0 +1,86 @@
++/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
++/* This Source Code Form is subject to the terms of the Mozilla Public
++ * License, v. 2.0. If a copy of the MPL was not distributed with this
++ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
++
++#include "nsKDERegistry.h"
++#include "prlink.h"
++#include "prmem.h"
++#include "nsString.h"
++#include "nsMIMEInfoUnix.h"
++#include "nsKDEUtils.h"
++
++/* static */ bool
++nsKDERegistry::HandlerExists(const char *aProtocolScheme)
++{
++ nsTArray<nsCString> command;
++ command.AppendElement( "HANDLEREXISTS"_ns );
++ command.AppendElement( nsAutoCString( aProtocolScheme ));
++ return nsKDEUtils::command( command );
++}
++
++/* static */ nsresult
++nsKDERegistry::LoadURL(nsIURI *aURL)
++{
++ nsTArray<nsCString> command;
++ command.AppendElement( "OPEN"_ns );
++ nsCString url;
++ aURL->GetSpec( url );
++ command.AppendElement( url );
++ bool rv = nsKDEUtils::command( command );
++ if (!rv)
++ return NS_ERROR_FAILURE;
++
++ return NS_OK;
++}
++
++/* static */ void
++nsKDERegistry::GetAppDescForScheme(const nsACString& aScheme,
++ nsAString& aDesc)
++{
++ nsTArray<nsCString> command;
++ command.AppendElement( "GETAPPDESCFORSCHEME"_ns );
++ command.AppendElement( aScheme );
++ nsTArray<nsCString> output;
++ if( nsKDEUtils::command( command, &output ) && output.Length() == 1 )
++ CopyUTF8toUTF16( output[ 0 ], aDesc );
++}
++
++
++/* static */ already_AddRefed<nsMIMEInfoBase>
++nsKDERegistry::GetFromExtension(const nsACString& aFileExt)
++{
++ NS_ASSERTION(aFileExt[0] != '.', "aFileExt shouldn't start with a dot");
++ nsTArray<nsCString> command;
++ command.AppendElement( "GETFROMEXTENSION"_ns );
++ command.AppendElement( aFileExt );
++ return GetFromHelper( command );
++}
++
++/* static */ already_AddRefed<nsMIMEInfoBase>
++nsKDERegistry::GetFromType(const nsACString& aMIMEType)
++{
++ nsTArray<nsCString> command;
++ command.AppendElement( "GETFROMTYPE"_ns );
++ command.AppendElement( aMIMEType );
++ return GetFromHelper( command );
++}
++
++/* static */ already_AddRefed<nsMIMEInfoBase>
++nsKDERegistry::GetFromHelper(const nsTArray<nsCString>& command)
++{
++ nsTArray<nsCString> output;
++ if( nsKDEUtils::command( command, &output ) && output.Length() == 3 )
++ {
++ nsCString mimetype = output[ 0 ];
++ RefPtr<nsMIMEInfoUnix> mimeInfo = new nsMIMEInfoUnix( mimetype );
++ NS_ENSURE_TRUE(mimeInfo, nullptr);
++ nsCString description = output[ 1 ];
++ mimeInfo->SetDescription(NS_ConvertUTF8toUTF16(description));
++ nsCString handlerAppName = output[ 2 ];
++ mimeInfo->SetDefaultDescription(NS_ConvertUTF8toUTF16(handlerAppName));
++ mimeInfo->SetPreferredAction(nsIMIMEInfo::useSystemDefault);
++ return mimeInfo.forget();
++ }
++ return nullptr;
++}
+diff --git a/uriloader/exthandler/unix/nsKDERegistry.h b/uriloader/exthandler/unix/nsKDERegistry.h
+new file mode 100644
+--- /dev/null
++++ b/uriloader/exthandler/unix/nsKDERegistry.h
+@@ -0,0 +1,34 @@
++/* This Source Code Form is subject to the terms of the Mozilla Public
++ * License, v. 2.0. If a copy of the MPL was not distributed with this
++ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
++
++#ifndef nsKDERegistry_h__
++#define nsKDERegistry_h__
++
++#include "nsIURI.h"
++#include "nsCOMPtr.h"
++#include "nsTArray.h"
++
++class nsMIMEInfoBase;
++//class nsAutoCString;
++//class nsCString;
++
++class nsKDERegistry
++{
++ public:
++ static bool HandlerExists(const char *aProtocolScheme);
++
++ static nsresult LoadURL(nsIURI *aURL);
++
++ static void GetAppDescForScheme(const nsACString& aScheme,
++ nsAString& aDesc);
++
++ static already_AddRefed<nsMIMEInfoBase> GetFromExtension(const nsACString& aFileExt);
++
++ static already_AddRefed<nsMIMEInfoBase> GetFromType(const nsACString& aMIMEType);
++ private:
++ static already_AddRefed<nsMIMEInfoBase> GetFromHelper(const nsTArray<nsCString>& command);
++
++};
++
++#endif //nsKDERegistry_h__
+diff --git a/uriloader/exthandler/unix/nsMIMEInfoUnix.cpp b/uriloader/exthandler/unix/nsMIMEInfoUnix.cpp
+--- a/uriloader/exthandler/unix/nsMIMEInfoUnix.cpp
++++ b/uriloader/exthandler/unix/nsMIMEInfoUnix.cpp
+@@ -1,46 +1,49 @@
+ /* -*- Mode: C++; tab-width: 3; indent-tabs-mode: nil; c-basic-offset: 2 -*-
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+ #include "nsMIMEInfoUnix.h"
+-#include "nsGNOMERegistry.h"
++#include "nsCommonRegistry.h"
+ #include "nsIGIOService.h"
+ #include "nsNetCID.h"
+ #include "nsIIOService.h"
+ #ifdef MOZ_ENABLE_DBUS
+ # include "nsDBusHandlerApp.h"
+ #endif
++#if defined(XP_UNIX) && !defined(XP_MACOSX)
++#include "nsKDEUtils.h"
++#endif
+
+ nsresult nsMIMEInfoUnix::LoadUriInternal(nsIURI* aURI) {
+- return nsGNOMERegistry::LoadURL(aURI);
++ return nsCommonRegistry::LoadURL(aURI);
+ }
+
+ NS_IMETHODIMP
+ nsMIMEInfoUnix::GetHasDefaultHandler(bool* _retval) {
+ // if mDefaultApplication is set, it means the application has been set from
+ // either /etc/mailcap or ${HOME}/.mailcap, in which case we don't want to
+ // give the GNOME answer.
+ if (mDefaultApplication) return nsMIMEInfoImpl::GetHasDefaultHandler(_retval);
+
+ *_retval = false;
+
+ if (mClass == eProtocolInfo) {
+- *_retval = nsGNOMERegistry::HandlerExists(mSchemeOrType.get());
++ *_retval = nsCommonRegistry::HandlerExists(mSchemeOrType.get());
+ } else {
+ RefPtr<nsMIMEInfoBase> mimeInfo =
+- nsGNOMERegistry::GetFromType(mSchemeOrType);
++ nsCommonRegistry::GetFromType(mSchemeOrType);
+ if (!mimeInfo) {
+ nsAutoCString ext;
+ nsresult rv = GetPrimaryExtension(ext);
+ if (NS_SUCCEEDED(rv)) {
+- mimeInfo = nsGNOMERegistry::GetFromExtension(ext);
++ mimeInfo = nsCommonRegistry::GetFromExtension(ext);
+ }
+ }
+ if (mimeInfo) *_retval = true;
+ }
+
+ if (*_retval) return NS_OK;
+
+ return NS_OK;
+@@ -50,16 +53,33 @@ nsresult nsMIMEInfoUnix::LaunchDefaultWi
+ // if mDefaultApplication is set, it means the application has been set from
+ // either /etc/mailcap or ${HOME}/.mailcap, in which case we don't want to
+ // give the GNOME answer.
+ if (mDefaultApplication) return nsMIMEInfoImpl::LaunchDefaultWithFile(aFile);
+
+ nsAutoCString nativePath;
+ aFile->GetNativePath(nativePath);
+
++ if( nsKDEUtils::kdeSupport()) {
++ bool supports;
++ if( NS_SUCCEEDED( GetHasDefaultHandler( &supports )) && supports ) {
++ nsTArray<nsCString> command;
++ command.AppendElement( "OPEN"_ns );
++ command.AppendElement( nativePath );
++ command.AppendElement( "MIMETYPE"_ns );
++ command.AppendElement( mSchemeOrType );
++ if( nsKDEUtils::command( command ))
++ return NS_OK;
++ }
++ if (!mDefaultApplication)
++ return NS_ERROR_FILE_NOT_FOUND;
++
++ return LaunchWithIProcess(mDefaultApplication, nativePath);
++ }
++
+ nsCOMPtr<nsIGIOService> giovfs = do_GetService(NS_GIOSERVICE_CONTRACTID);
+ if (!giovfs) {
+ return NS_ERROR_FAILURE;
+ }
+
+ // nsGIOMimeApp->Launch wants a URI string instead of local file
+ nsresult rv;
+ nsCOMPtr<nsIIOService> ioservice =
+diff --git a/uriloader/exthandler/unix/nsOSHelperAppService.cpp b/uriloader/exthandler/unix/nsOSHelperAppService.cpp
+--- a/uriloader/exthandler/unix/nsOSHelperAppService.cpp
++++ b/uriloader/exthandler/unix/nsOSHelperAppService.cpp
+@@ -5,17 +5,17 @@
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+ #include <sys/types.h>
+ #include <sys/stat.h>
+
+ #include "nsOSHelperAppService.h"
+ #include "nsMIMEInfoUnix.h"
+ #ifdef MOZ_WIDGET_GTK
+-# include "nsGNOMERegistry.h"
++# include "nsCommonRegistry.h"
+ # ifdef MOZ_BUILD_APP_IS_BROWSER
+ # include "nsIToolkitShellService.h"
+ # include "nsIGNOMEShellService.h"
+ # endif
+ #endif
+ #include "nsISupports.h"
+ #include "nsString.h"
+ #include "nsReadableUtils.h"
+@@ -1025,17 +1025,17 @@ nsresult nsOSHelperAppService::GetHandle
+
+ nsresult nsOSHelperAppService::OSProtocolHandlerExists(
+ const char* aProtocolScheme, bool* aHandlerExists) {
+ nsresult rv = NS_OK;
+
+ if (!XRE_IsContentProcess()) {
+ #ifdef MOZ_WIDGET_GTK
+ // Check the GNOME registry for a protocol handler
+- *aHandlerExists = nsGNOMERegistry::HandlerExists(aProtocolScheme);
++ *aHandlerExists = nsCommonRegistry::HandlerExists(aProtocolScheme);
+ #else
+ *aHandlerExists = false;
+ #endif
+ } else {
+ *aHandlerExists = false;
+ nsCOMPtr<nsIHandlerService> handlerSvc =
+ do_GetService(NS_HANDLERSERVICE_CONTRACTID, &rv);
+ if (NS_SUCCEEDED(rv) && handlerSvc) {
+@@ -1045,17 +1045,17 @@ nsresult nsOSHelperAppService::OSProtoco
+ }
+
+ return rv;
+ }
+
+ NS_IMETHODIMP nsOSHelperAppService::GetApplicationDescription(
+ const nsACString& aScheme, nsAString& _retval) {
+ #ifdef MOZ_WIDGET_GTK
+- nsGNOMERegistry::GetAppDescForScheme(aScheme, _retval);
++ nsCommonRegistry::GetAppDescForScheme(aScheme, _retval);
+ return _retval.IsEmpty() ? NS_ERROR_NOT_AVAILABLE : NS_OK;
+ #else
+ return NS_ERROR_NOT_AVAILABLE;
+ #endif
+ }
+
+ NS_IMETHODIMP nsOSHelperAppService::IsCurrentAppOSDefaultForProtocol(
+ const nsACString& aScheme, bool* _retval) {
+@@ -1148,17 +1148,17 @@ already_AddRefed<nsMIMEInfoBase> nsOSHel
+ nsresult rv =
+ LookUpTypeAndDescription(NS_ConvertUTF8toUTF16(aFileExt), majorType,
+ minorType, mime_types_description, true);
+
+ if (NS_FAILED(rv) || majorType.IsEmpty()) {
+ #ifdef MOZ_WIDGET_GTK
+ LOG(("Looking in GNOME registry\n"));
+ RefPtr<nsMIMEInfoBase> gnomeInfo =
+- nsGNOMERegistry::GetFromExtension(aFileExt);
++ nsCommonRegistry::GetFromExtension(aFileExt);
+ if (gnomeInfo) {
+ LOG(("Got MIMEInfo from GNOME registry\n"));
+ return gnomeInfo.forget();
+ }
+ #endif
+
+ rv = LookUpTypeAndDescription(NS_ConvertUTF8toUTF16(aFileExt), majorType,
+ minorType, mime_types_description, false);
+@@ -1261,17 +1261,17 @@ already_AddRefed<nsMIMEInfoBase> nsOSHel
+
+ // Now look up our extensions
+ nsAutoString extensions, mime_types_description;
+ LookUpExtensionsAndDescription(majorType, minorType, extensions,
+ mime_types_description);
+
+ #ifdef MOZ_WIDGET_GTK
+ if (handler.IsEmpty()) {
+- RefPtr<nsMIMEInfoBase> gnomeInfo = nsGNOMERegistry::GetFromType(aMIMEType);
++ RefPtr<nsMIMEInfoBase> gnomeInfo = nsCommonRegistry::GetFromType(aMIMEType);
+ if (gnomeInfo) {
+ LOG(
+ ("Got MIMEInfo from GNOME registry without extensions; setting them "
+ "to %s\n",
+ NS_LossyConvertUTF16toASCII(extensions).get()));
+
+ NS_ASSERTION(!gnomeInfo->HasExtensions(), "How'd that happen?");
+ gnomeInfo->SetFileExtensions(NS_ConvertUTF16toUTF8(extensions));
+diff --git a/widget/gtk/moz.build b/widget/gtk/moz.build
+--- a/widget/gtk/moz.build
++++ b/widget/gtk/moz.build
+@@ -137,16 +137,17 @@ FINAL_LIBRARY = "xul"
+
+ LOCAL_INCLUDES += [
+ "/layout/base",
+ "/layout/forms",
+ "/layout/generic",
+ "/layout/xul",
+ "/other-licenses/atk-1.0",
+ "/third_party/cups/include",
++ "/toolkit/xre",
+ "/widget",
+ "/widget/headless",
+ ]
+
+ if CONFIG["MOZ_X11"]:
+ LOCAL_INCLUDES += [
+ "/widget/x11",
+ ]
+diff --git a/widget/gtk/nsFilePicker.cpp b/widget/gtk/nsFilePicker.cpp
+--- a/widget/gtk/nsFilePicker.cpp
++++ b/widget/gtk/nsFilePicker.cpp
+@@ -1,15 +1,16 @@
+ /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+ /* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+ #include <dlfcn.h>
+ #include <gtk/gtk.h>
++#include <gdk/gdkx.h>
+ #include <sys/types.h>
+ #include <sys/stat.h>
+ #include <unistd.h>
+
+ #include "mozilla/Types.h"
+ #include "nsGtkUtils.h"
+ #include "nsIFileURL.h"
+ #include "nsIGIOService.h"
+@@ -22,16 +23,18 @@
+ #include "nsMemory.h"
+ #include "nsEnumeratorUtils.h"
+ #include "nsNetUtil.h"
+ #include "nsReadableUtils.h"
+ #include "MozContainer.h"
+ #include "WidgetUtilsGtk.h"
+
+ #include "nsFilePicker.h"
++#include "nsKDEUtils.h"
++#include "nsURLHelper.h"
+
+ #undef LOG
+ #ifdef MOZ_LOGGING
+ # include "mozilla/Logging.h"
+ # include "nsTArray.h"
+ # include "Units.h"
+ extern mozilla::LazyLogModule gWidgetLog;
+ # define LOG(args) MOZ_LOG(gWidgetLog, mozilla::LogLevel::Debug, args)
+@@ -242,17 +245,19 @@ nsFilePicker::AppendFilters(int32_t aFil
+ mAllowURLs = !!(aFilterMask & filterAllowURLs);
+ return nsBaseFilePicker::AppendFilters(aFilterMask);
+ }
+
+ NS_IMETHODIMP
+ nsFilePicker::AppendFilter(const nsAString& aTitle, const nsAString& aFilter) {
+ if (aFilter.EqualsLiteral("..apps")) {
+ // No platform specific thing we can do here, really....
+- return NS_OK;
++ // Unless it's KDE.
++ if( mMode != modeOpen || !nsKDEUtils::kdeSupport())
++ return NS_OK;
+ }
+
+ nsAutoCString filter, name;
+ CopyUTF16toUTF8(aFilter, filter);
+ CopyUTF16toUTF8(aTitle, name);
+
+ mFilters.AppendElement(filter);
+ mFilterNames.AppendElement(name);
+@@ -352,16 +357,39 @@ nsresult nsFilePicker::Show(int16_t* aRe
+ return NS_OK;
+ }
+
+ NS_IMETHODIMP
+ nsFilePicker::Open(nsIFilePickerShownCallback* aCallback) {
+ // Can't show two dialogs concurrently with the same filepicker
+ if (mRunning) return NS_ERROR_NOT_AVAILABLE;
+
++ // KDE file picker is not handled via callback
++ if( nsKDEUtils::kdeSupport()) {
++ mCallback = aCallback;
++ mRunning = true;
++ NS_ADDREF_THIS();
++ g_idle_add([](gpointer data) -> gboolean {
++ nsFilePicker* queuedPicker = (nsFilePicker*) data;
++ int16_t result;
++ queuedPicker->kdeFileDialog(&result);
++ if (queuedPicker->mCallback) {
++ queuedPicker->mCallback->Done(result);
++ queuedPicker->mCallback = nullptr;
++ } else {
++ queuedPicker->mResult = result;
++ }
++ queuedPicker->mRunning = false;
++ NS_RELEASE(queuedPicker);
++ return G_SOURCE_REMOVE;
++ }, this);
++
++ return NS_OK;
++ }
++
+ NS_ConvertUTF16toUTF8 title(mTitle);
+
+ GtkWindow* parent_widget =
+ GTK_WINDOW(mParentWidget->GetNativeData(NS_NATIVE_SHELLWIDGET));
+
+ GtkFileChooserAction action = GetGtkFileChooserAction(mMode);
+
+ const gchar* accept_button;
+@@ -581,16 +609,244 @@ void nsFilePicker::Done(void* file_choos
+ mCallback->Done(result);
+ mCallback = nullptr;
+ } else {
+ mResult = result;
+ }
+ NS_RELEASE_THIS();
+ }
+
++nsCString nsFilePicker::kdeMakeFilter( int index )
++ {
++ nsCString buf = mFilters[ index ];
++ for( PRUint32 i = 0;
++ i < buf.Length();
++ ++i )
++ if( buf[ i ] == ';' ) // KDE separates just using spaces
++ buf.SetCharAt( ' ', i );
++ if (!mFilterNames[index].IsEmpty())
++ {
++ buf += "|";
++ buf += mFilterNames[index].get();
++ }
++ return buf;
++ }
++
++static PRInt32 windowToXid( nsIWidget* widget )
++ {
++ GtkWindow *parent_widget = GTK_WINDOW(widget->GetNativeData(NS_NATIVE_SHELLWIDGET));
++ GdkWindow* gdk_window = gtk_widget_get_window( gtk_widget_get_toplevel( GTK_WIDGET( parent_widget )));
++ return GDK_WINDOW_XID( gdk_window );
++ }
++
++NS_IMETHODIMP nsFilePicker::kdeFileDialog(PRInt16 *aReturn)
++ {
++ NS_ENSURE_ARG_POINTER(aReturn);
++
++ if( mMode == modeOpen && mFilters.Length() == 1 && mFilters[ 0 ].EqualsLiteral( "..apps" ))
++ return kdeAppsDialog( aReturn );
++
++ nsCString title;
++ title.Adopt(ToNewUTF8String(mTitle));
++
++ const char* arg = NULL;
++ if( mAllowURLs )
++ {
++ switch( mMode )
++ {
++ case nsIFilePicker::modeOpen:
++ case nsIFilePicker::modeOpenMultiple:
++ arg = "GETOPENURL";
++ break;
++ case nsIFilePicker::modeSave:
++ arg = "GETSAVEURL";
++ break;
++ case nsIFilePicker::modeGetFolder:
++ arg = "GETDIRECTORYURL";
++ break;
++ }
++ }
++ else
++ {
++ switch( mMode )
++ {
++ case nsIFilePicker::modeOpen:
++ case nsIFilePicker::modeOpenMultiple:
++ arg = "GETOPENFILENAME";
++ break;
++ case nsIFilePicker::modeSave:
++ arg = "GETSAVEFILENAME";
++ break;
++ case nsIFilePicker::modeGetFolder:
++ arg = "GETDIRECTORYFILENAME";
++ break;
++ }
++ }
++
++ nsAutoCString directory;
++ if (mDisplayDirectory) {
++ mDisplayDirectory->GetNativePath(directory);
++ } else if (mPrevDisplayDirectory) {
++ mPrevDisplayDirectory->GetNativePath(directory);
++ }
++
++ nsAutoCString startdir;
++ if (!directory.IsEmpty()) {
++ startdir = directory;
++ }
++ if (mMode == nsIFilePicker::modeSave) {
++ if( !startdir.IsEmpty())
++ {
++ startdir += "/";
++ startdir += ToNewUTF8String(mDefault);
++ }
++ else
++ startdir = ToNewUTF8String(mDefault);
++ }
++
++ nsAutoCString filters;
++ PRInt32 count = mFilters.Length();
++ if( count == 0 ) //just in case
++ filters = "*";
++ else
++ {
++ filters = kdeMakeFilter( 0 );
++ for (PRInt32 i = 1; i < count; ++i)
++ {
++ filters += "\n";
++ filters += kdeMakeFilter( i );
++ }
++ }
++
++ nsTArray<nsCString> command;
++ command.AppendElement( nsAutoCString( arg ));
++ command.AppendElement( startdir );
++ if( mMode != nsIFilePicker::modeGetFolder )
++ {
++ command.AppendElement( filters );
++ nsAutoCString selected;
++ selected.AppendInt( mSelectedType );
++ command.AppendElement( selected );
++ }
++ command.AppendElement( title );
++ if( mMode == nsIFilePicker::modeOpenMultiple )
++ command.AppendElement( "MULTIPLE"_ns );
++ if( PRInt32 xid = windowToXid( mParentWidget ))
++ {
++ command.AppendElement( "PARENT"_ns );
++ nsAutoCString parent;
++ parent.AppendInt( xid );
++ command.AppendElement( parent );
++ }
++
++ nsTArray<nsCString> output;
++ if( nsKDEUtils::commandBlockUi( command, GTK_WINDOW(mParentWidget->GetNativeData(NS_NATIVE_SHELLWIDGET)), &output ))
++ {
++ *aReturn = nsIFilePicker::returnOK;
++ mFiles.Clear();
++ if( mMode != nsIFilePicker::modeGetFolder )
++ {
++ mSelectedType = atoi( output[ 0 ].get());
++ output.RemoveElementAt( 0 );
++ }
++ if (mMode == nsIFilePicker::modeOpenMultiple)
++ {
++ mFileURL.Truncate();
++ PRUint32 count = output.Length();
++ for( PRUint32 i = 0;
++ i < count;
++ ++i )
++ {
++ nsCOMPtr<nsIFile> localfile;
++ nsresult rv = NS_NewNativeLocalFile( output[ i ],
++ PR_FALSE,
++ getter_AddRefs(localfile));
++ if (NS_SUCCEEDED(rv))
++ mFiles.AppendObject(localfile);
++ }
++ }
++ else
++ {
++ if( output.Length() == 0 )
++ mFileURL = nsCString();
++ else if( mAllowURLs )
++ mFileURL = output[ 0 ];
++ else // GetFile() actually requires it to be url even for local files :-/
++ {
++ nsCOMPtr<nsIFile> localfile;
++ nsresult rv = NS_NewNativeLocalFile( output[ 0 ],
++ PR_FALSE,
++ getter_AddRefs(localfile));
++ if (NS_SUCCEEDED(rv))
++ rv = net_GetURLSpecFromActualFile(localfile, mFileURL);
++ }
++ }
++ // Remember last used directory.
++ nsCOMPtr<nsIFile> file;
++ GetFile(getter_AddRefs(file));
++ if (file) {
++ nsCOMPtr<nsIFile> dir;
++ file->GetParent(getter_AddRefs(dir));
++ nsCOMPtr<nsIFile> localDir(do_QueryInterface(dir));
++ if (localDir) {
++ localDir.swap(mPrevDisplayDirectory);
++ }
++ }
++ if (mMode == nsIFilePicker::modeSave)
++ {
++ nsCOMPtr<nsIFile> file;
++ GetFile(getter_AddRefs(file));
++ if (file)
++ {
++ bool exists = false;
++ file->Exists(&exists);
++ if (exists) // TODO do overwrite check in the helper app
++ *aReturn = nsIFilePicker::returnReplace;
++ }
++ }
++ }
++ else
++ {
++ *aReturn = nsIFilePicker::returnCancel;
++ }
++ return NS_OK;
++ }
++
++
++NS_IMETHODIMP nsFilePicker::kdeAppsDialog(PRInt16 *aReturn)
++ {
++ NS_ENSURE_ARG_POINTER(aReturn);
++
++ nsCString title;
++ title.Adopt(ToNewUTF8String(mTitle));
++
++ nsTArray<nsCString> command;
++ command.AppendElement( "APPSDIALOG"_ns );
++ command.AppendElement( title );
++ if( PRInt32 xid = windowToXid( mParentWidget ))
++ {
++ command.AppendElement( "PARENT"_ns );
++ nsAutoCString parent;
++ parent.AppendInt( xid );
++ command.AppendElement( parent );
++ }
++
++ nsTArray<nsCString> output;
++ if( nsKDEUtils::commandBlockUi( command, GTK_WINDOW(mParentWidget->GetNativeData(NS_NATIVE_SHELLWIDGET)), &output ))
++ {
++ *aReturn = nsIFilePicker::returnOK;
++ mFileURL = output.Length() > 0 ? output[ 0 ] : nsCString();
++ }
++ else
++ {
++ *aReturn = nsIFilePicker::returnCancel;
++ }
++ return NS_OK;
++ }
++
+ // All below functions available as of GTK 3.20+
+ void* nsFilePicker::GtkFileChooserNew(const gchar* title, GtkWindow* parent,
+ GtkFileChooserAction action,
+ const gchar* accept_label) {
+ static auto sGtkFileChooserNativeNewPtr =
+ (void* (*)(const gchar*, GtkWindow*, GtkFileChooserAction, const gchar*,
+ const gchar*))dlsym(RTLD_DEFAULT,
+ "gtk_file_chooser_native_new");
+diff --git a/widget/gtk/nsFilePicker.h b/widget/gtk/nsFilePicker.h
+--- a/widget/gtk/nsFilePicker.h
++++ b/widget/gtk/nsFilePicker.h
+@@ -67,16 +67,22 @@ class nsFilePicker : public nsBaseFilePi
+ nsString mDefaultExtension;
+
+ nsTArray<nsCString> mFilters;
+ nsTArray<nsCString> mFilterNames;
+
+ private:
+ static nsIFile* mPrevDisplayDirectory;
+
++ bool kdeRunning();
++ bool getKdeRunning();
++ NS_IMETHODIMP kdeFileDialog(PRInt16 *aReturn);
++ NS_IMETHODIMP kdeAppsDialog(PRInt16 *aReturn);
++ nsCString kdeMakeFilter( int index );
++
+ void* GtkFileChooserNew(const gchar* title, GtkWindow* parent,
+ GtkFileChooserAction action,
+ const gchar* accept_label);
+ void GtkFileChooserShow(void* file_chooser);
+ void GtkFileChooserDestroy(void* file_chooser);
+ void GtkFileChooserSetModal(void* file_chooser, GtkWindow* parent_widget,
+ gboolean modal);
+
+diff --git a/xpcom/components/ManifestParser.cpp b/xpcom/components/ManifestParser.cpp
+--- a/xpcom/components/ManifestParser.cpp
++++ b/xpcom/components/ManifestParser.cpp
+@@ -38,16 +38,17 @@
+ #include "nsTextFormatter.h"
+ #include "nsVersionComparator.h"
+ #include "nsXPCOMCIDInternal.h"
+
+ #include "nsIConsoleService.h"
+ #include "nsIScriptError.h"
+ #include "nsIXULAppInfo.h"
+ #include "nsIXULRuntime.h"
++#include "nsKDEUtils.h"
+
+ using namespace mozilla;
+
+ struct ManifestDirective {
+ const char* directive;
+ int argc;
+
+ bool ischrome;
+@@ -397,16 +398,17 @@ void ParseManifest(NSLocationType aType,
+ constexpr auto kRemoteEnabled = u"remoteenabled"_ns;
+ constexpr auto kRemoteRequired = u"remoterequired"_ns;
+ constexpr auto kApplication = u"application"_ns;
+ constexpr auto kAppVersion = u"appversion"_ns;
+ constexpr auto kGeckoVersion = u"platformversion"_ns;
+ constexpr auto kOs = u"os"_ns;
+ constexpr auto kOsVersion = u"osversion"_ns;
+ constexpr auto kABI = u"abi"_ns;
++ constexpr auto kDesktop = u"desktop"_ns;
+ constexpr auto kProcess = u"process"_ns;
+ #if defined(MOZ_WIDGET_ANDROID)
+ constexpr auto kTablet = u"tablet"_ns;
+ #endif
+ // You might expect this to be guarded by MOZ_BACKGROUNDTASKS, but it's not
+ // possible to have conditional manifest contents, so we need to recognize and
+ // discard these tokens even when MOZ_BACKGROUNDTASKS is not set.
+ constexpr auto kBackgroundTask = u"backgroundtask"_ns;
+@@ -456,39 +458,44 @@ void ParseManifest(NSLocationType aType,
+ CopyUTF8toUTF16(s, abi);
+ abi.Insert(char16_t('_'), 0);
+ abi.Insert(osTarget, 0);
+ }
+ }
+ }
+
+ nsAutoString osVersion;
++ nsAutoString desktop;
+ #if defined(XP_WIN)
+ # pragma warning(push)
+ # pragma warning(disable : 4996) // VC12+ deprecates GetVersionEx
+ OSVERSIONINFO info = {sizeof(OSVERSIONINFO)};
+ if (GetVersionEx(&info)) {
+ nsTextFormatter::ssprintf(osVersion, u"%ld.%ld", info.dwMajorVersion,
+ info.dwMinorVersion);
+ }
++ desktop = u"win"_ns;
+ # pragma warning(pop)
+ #elif defined(MOZ_WIDGET_COCOA)
+ SInt32 majorVersion = nsCocoaFeatures::macOSVersionMajor();
+ SInt32 minorVersion = nsCocoaFeatures::macOSVersionMinor();
+ nsTextFormatter::ssprintf(osVersion, u"%ld.%ld", majorVersion, minorVersion);
++ desktop = u"macosx"_ns);
+ #elif defined(MOZ_WIDGET_GTK)
+ nsTextFormatter::ssprintf(osVersion, u"%ld.%ld", gtk_major_version,
+ gtk_minor_version);
++ desktop = nsKDEUtils::kdeSession() ? u"kde"_ns : u"gnome"_ns;
+ #elif defined(MOZ_WIDGET_ANDROID)
+ bool isTablet = false;
+ if (mozilla::AndroidBridge::Bridge()) {
+ mozilla::AndroidBridge::Bridge()->GetStaticStringField(
+ "android/os/Build$VERSION", "RELEASE", osVersion);
+ isTablet = java::GeckoAppShell::IsTablet();
+ }
++ desktop = u"android"_ns;
+ #endif
+
+ if (XRE_IsContentProcess()) {
+ process = kContent;
+ } else {
+ process = kMain;
+ }
+
+@@ -583,25 +590,27 @@ void ParseManifest(NSLocationType aType,
+ // When in background task mode, default to not registering
+ // category directivies unless backgroundtask=1 is specified.
+ TriState stBackgroundTask = (BackgroundTasks::IsBackgroundTaskMode() &&
+ strcmp("category", directive->directive) == 0)
+ ? eBad
+ : eUnspecified;
+ #endif
+ int flags = 0;
++ TriState stDesktop = eUnspecified;
+
+ while ((token = nsCRT::strtok(whitespace, kWhitespace, &whitespace)) &&
+ ok) {
+ ToLowerCase(token);
+ NS_ConvertASCIItoUTF16 wtoken(token);
+
+ if (CheckStringFlag(kApplication, wtoken, appID, stApp) ||
+ CheckOsFlag(kOs, wtoken, osTarget, stOs) ||
+ CheckStringFlag(kABI, wtoken, abi, stABI) ||
++ CheckStringFlag(kDesktop, wtoken, desktop, stDesktop) ||
+ CheckStringFlag(kProcess, wtoken, process, stProcess) ||
+ CheckVersionFlag(kOsVersion, wtoken, osVersion, stOsVersion) ||
+ CheckVersionFlag(kAppVersion, wtoken, appVersion, stAppVersion) ||
+ CheckVersionFlag(kGeckoVersion, wtoken, geckoVersion,
+ stGeckoVersion)) {
+ continue;
+ }
+
+@@ -650,17 +659,17 @@ void ParseManifest(NSLocationType aType,
+ }
+
+ LogMessageWithContext(
+ aFile, line, "Unrecognized chrome manifest modifier '%s'.", token);
+ ok = false;
+ }
+
+ if (!ok || stApp == eBad || stAppVersion == eBad ||
+- stGeckoVersion == eBad || stOs == eBad || stOsVersion == eBad ||
++ stGeckoVersion == eBad || stOs == eBad || stOsVersion == eBad || stDesktop == eBad ||
+ #ifdef MOZ_WIDGET_ANDROID
+ stTablet == eBad ||
+ #endif
+ #ifdef MOZ_BACKGROUNDTASKS
+ stBackgroundTask == eBad ||
+ #endif
+ stABI == eBad || stProcess == eBad) {
+ continue;
+diff --git a/xpcom/components/moz.build b/xpcom/components/moz.build
+--- a/xpcom/components/moz.build
++++ b/xpcom/components/moz.build
+@@ -66,16 +66,17 @@ LOCAL_INCLUDES += [
+ "!..",
+ "../base",
+ "../build",
+ "../ds",
+ "/chrome",
+ "/js/xpconnect/loader",
+ "/layout/build",
+ "/modules/libjar",
++ "/toolkit/xre",
+ ]
+
+ if CONFIG["MOZ_WIDGET_TOOLKIT"] == "gtk":
+ CXXFLAGS += CONFIG["TK_CFLAGS"]
+ if CONFIG["MOZ_ENABLE_DBUS"]:
+ CXXFLAGS += CONFIG["MOZ_DBUS_GLIB_CFLAGS"]
+
+ if CONFIG["MOZ_BACKGROUNDTASKS"]:
+diff --git a/xpcom/io/nsLocalFileUnix.cpp b/xpcom/io/nsLocalFileUnix.cpp
+--- a/xpcom/io/nsLocalFileUnix.cpp
++++ b/xpcom/io/nsLocalFileUnix.cpp
+@@ -53,16 +53,17 @@
+ #include "prproces.h"
+ #include "nsIDirectoryEnumerator.h"
+ #include "nsSimpleEnumerator.h"
+ #include "private/pprio.h"
+ #include "prlink.h"
+
+ #ifdef MOZ_WIDGET_GTK
+ # include "nsIGIOService.h"
++# include "nsKDEUtils.h"
+ #endif
+
+ #ifdef MOZ_WIDGET_COCOA
+ # include <Carbon/Carbon.h>
+ # include "CocoaFileUtils.h"
+ # include "prmem.h"
+ # include "plbase64.h"
+
+@@ -2023,62 +2024,77 @@ nsLocalFile::SetPersistentDescriptor(con
+
+ NS_IMETHODIMP
+ nsLocalFile::Reveal() {
+ if (!FilePreferences::IsAllowedPath(mPath)) {
+ return NS_ERROR_FILE_ACCESS_DENIED;
+ }
+
+ #ifdef MOZ_WIDGET_GTK
+- nsCOMPtr<nsIGIOService> giovfs = do_GetService(NS_GIOSERVICE_CONTRACTID);
+- if (!giovfs) {
+- return NS_ERROR_FAILURE;
+- }
++ nsAutoCString url;
+
+ bool isDirectory;
+ if (NS_FAILED(IsDirectory(&isDirectory))) {
+ return NS_ERROR_FAILURE;
+ }
+
++ nsCOMPtr<nsIGIOService> giovfs = do_GetService(NS_GIOSERVICE_CONTRACTID);
+ if (isDirectory) {
+- return giovfs->ShowURIForInput(mPath);
++ url = mPath;
+ }
+ if (NS_SUCCEEDED(giovfs->OrgFreedesktopFileManager1ShowItems(mPath))) {
+ return NS_OK;
+ }
+ nsCOMPtr<nsIFile> parentDir;
+ nsAutoCString dirPath;
+ if (NS_FAILED(GetParent(getter_AddRefs(parentDir)))) {
+ return NS_ERROR_FAILURE;
+ }
+ if (NS_FAILED(parentDir->GetNativePath(dirPath))) {
+ return NS_ERROR_FAILURE;
+ }
+
+- return giovfs->ShowURIForInput(dirPath);
++ url = dirPath;
+ #elif defined(MOZ_WIDGET_COCOA)
+ CFURLRef url;
+ if (NS_SUCCEEDED(GetCFURL(&url))) {
+ nsresult rv = CocoaFileUtils::RevealFileInFinder(url);
+ ::CFRelease(url);
+ return rv;
+ }
+ return NS_ERROR_FAILURE;
+ #else
+ return NS_ERROR_FAILURE;
+ #endif
++ if(nsKDEUtils::kdeSupport()) {
++ nsTArray<nsCString> command;
++ command.AppendElement( "REVEAL"_ns );
++ command.AppendElement( mPath );
++ return nsKDEUtils::command( command ) ? NS_OK : NS_ERROR_FAILURE;
++ }
++
++ if (!giovfs)
++ return NS_ERROR_FAILURE;
++
++ return giovfs->ShowURIForInput(url);
+ }
+
+ NS_IMETHODIMP
+ nsLocalFile::Launch() {
+ if (!FilePreferences::IsAllowedPath(mPath)) {
+ return NS_ERROR_FILE_ACCESS_DENIED;
+ }
+
+ #ifdef MOZ_WIDGET_GTK
++ if( nsKDEUtils::kdeSupport()) {
++ nsTArray<nsCString> command;
++ command.AppendElement( "OPEN"_ns );
++ command.AppendElement( mPath );
++ return nsKDEUtils::command( command ) ? NS_OK : NS_ERROR_FAILURE;
++ }
+ nsCOMPtr<nsIGIOService> giovfs = do_GetService(NS_GIOSERVICE_CONTRACTID);
+ if (!giovfs) {
+ return NS_ERROR_FAILURE;
+ }
+
+ return giovfs->ShowURIForInput(mPath);
+ #elif defined(MOZ_WIDGET_ANDROID)
+ // Not supported on GeckoView
diff --git a/mozilla-nongnome-proxies.patch b/mozilla-nongnome-proxies.patch
new file mode 100644
index 000000000000..301ea588704d
--- /dev/null
+++ b/mozilla-nongnome-proxies.patch
@@ -0,0 +1,44 @@
+# HG changeset patch
+# User Wolfgang Rosenauer
+# Date 1558442915 -7200
+# Tue May 21 14:48:35 2019 +0200
+# Node ID 6bcf2dfebc1ea2aa34e5cc61152709fc8e409dc5
+# Parent bd5d1f49975deb730064a16b3079edb53c4a5f84
+Do not use gconf for proxy settings if not running within Gnome
+Index: toolkit/system/unixproxy/nsUnixSystemProxySettings.cpp
+===================================================================
+RCS file: /cvsroot/mozilla/toolkit/system/unixproxy/nsUnixSystemProxySettings.cpp,v
+retrieving revision 1.1
+
+diff --git a/toolkit/system/unixproxy/nsUnixSystemProxySettings.cpp b/toolkit/system/unixproxy/nsUnixSystemProxySettings.cpp
+--- a/toolkit/system/unixproxy/nsUnixSystemProxySettings.cpp
++++ b/toolkit/system/unixproxy/nsUnixSystemProxySettings.cpp
+@@ -49,20 +49,24 @@ NS_IMETHODIMP
+ nsUnixSystemProxySettings::GetMainThreadOnly(bool* aMainThreadOnly) {
+ // dbus prevents us from being threadsafe, but this routine should not block
+ // anyhow
+ *aMainThreadOnly = true;
+ return NS_OK;
+ }
+
+ void nsUnixSystemProxySettings::Init() {
+- mGSettings = do_GetService(NS_GSETTINGSSERVICE_CONTRACTID);
+- if (mGSettings) {
+- mGSettings->GetCollectionForSchema("org.gnome.system.proxy"_ns,
+- getter_AddRefs(mProxySettings));
++ const char* sessionType = PR_GetEnv("DESKTOP_SESSION");
++ if (sessionType && !strcmp(sessionType, "gnome")) {
++ mGSettings = do_GetService(NS_GSETTINGSSERVICE_CONTRACTID);
++ if (mGSettings) {
++ mGSettings->GetCollectionForSchema(
++ "org.gnome.system.proxy"_ns,
++ getter_AddRefs(mProxySettings));
++ }
+ }
+ }
+
+ nsresult nsUnixSystemProxySettings::GetPACURI(nsACString& aResult) {
+ if (mProxySettings) {
+ nsCString proxyMode;
+ // Check if mode is auto
+ nsresult rv = mProxySettings->GetString("mode"_ns, proxyMode);
diff --git a/mozilla-ntlm-full-path.patch b/mozilla-ntlm-full-path.patch
new file mode 100644
index 000000000000..ce5b6a29e824
--- /dev/null
+++ b/mozilla-ntlm-full-path.patch
@@ -0,0 +1,28 @@
+# HG changeset patch
+# User Petr Cerny <pcerny@novell.com>
+# Parent 7308e4a7c1f769f4bbbc90870b849cadd99495a6
+# Parent 2361c5db1e70e358b2158325e07fa15bb4569c2c
+Bug 634334 - call to the ntlm_auth helper fails
+
+diff --git a/extensions/auth/nsAuthSambaNTLM.cpp b/extensions/auth/nsAuthSambaNTLM.cpp
+--- a/extensions/auth/nsAuthSambaNTLM.cpp
++++ b/extensions/auth/nsAuthSambaNTLM.cpp
+@@ -156,17 +156,17 @@ static uint8_t* ExtractMessage(const nsA
+ *aLen = (length / 4) * 3 - numEquals;
+ return reinterpret_cast<uint8_t*>(PL_Base64Decode(s, length, nullptr));
+ }
+
+ nsresult nsAuthSambaNTLM::SpawnNTLMAuthHelper() {
+ const char* username = PR_GetEnv("USER");
+ if (!username) return NS_ERROR_FAILURE;
+
+- const char* const args[] = {"ntlm_auth",
++ const char* const args[] = {"/usr/bin/ntlm_auth",
+ "--helper-protocol",
+ "ntlmssp-client-1",
+ "--use-cached-creds",
+ "--username",
+ username,
+ nullptr};
+
+ bool isOK = SpawnIOChild(const_cast<char* const*>(args), &mChildPID,
diff --git a/mozilla-sandbox-fips.patch b/mozilla-sandbox-fips.patch
new file mode 100644
index 000000000000..8894666dba9a
--- /dev/null
+++ b/mozilla-sandbox-fips.patch
@@ -0,0 +1,40 @@
+From: meissner@suse.com, cgrobertson@suse.com
+Subject: allow Firefox to access addtional process information
+References:
+http://bugzilla.suse.com/show_bug.cgi?id=1167132
+bsc#1174284 - Firefox tab just crashed in FIPS mode
+
+Index: firefox-93.0/security/sandbox/linux/Sandbox.cpp
+===================================================================
+--- firefox-93.0.orig/security/sandbox/linux/Sandbox.cpp
++++ firefox-93.0/security/sandbox/linux/Sandbox.cpp
+@@ -655,6 +655,7 @@ void SetMediaPluginSandbox(const char* a
+ auto files = new SandboxOpenedFiles();
+ files->Add(std::move(plugin));
+ files->Add("/dev/urandom", SandboxOpenedFile::Dup::YES);
++ files->Add("/dev/random", SandboxOpenedFile::Dup::YES);
+ files->Add("/etc/ld.so.cache"); // Needed for NSS in clearkey.
+ files->Add("/sys/devices/system/cpu/cpu0/tsc_freq_khz");
+ files->Add("/sys/devices/system/cpu/cpu0/cpufreq/cpuinfo_max_freq");
+Index: firefox-93.0/security/sandbox/linux/broker/SandboxBrokerPolicyFactory.cpp
+===================================================================
+--- firefox-93.0.orig/security/sandbox/linux/broker/SandboxBrokerPolicyFactory.cpp
++++ firefox-93.0/security/sandbox/linux/broker/SandboxBrokerPolicyFactory.cpp
+@@ -320,6 +320,8 @@ void SandboxBrokerPolicyFactory::InitCon
+
+ // Read permissions
+ policy->AddPath(rdonly, "/dev/urandom");
++ policy->AddPath(rdonly, "/dev/random");
++ policy->AddPath(rdonly, "/proc/sys/crypto/fips_enabled");
+ policy->AddPath(rdonly, "/proc/cpuinfo");
+ policy->AddPath(rdonly, "/proc/meminfo");
+ policy->AddDir(rdonly, "/sys/devices/cpu");
+@@ -792,6 +794,8 @@ SandboxBrokerPolicyFactory::GetSocketPro
+ auto policy = MakeUnique<SandboxBroker::Policy>();
+
+ policy->AddPath(rdonly, "/dev/urandom");
++ policy->AddPath(rdonly, "/dev/random");
++ policy->AddPath(rdonly, "/proc/sys/crypto/fips_enabled");
+ policy->AddPath(rdonly, "/proc/cpuinfo");
+ policy->AddPath(rdonly, "/proc/meminfo");
+ policy->AddDir(rdonly, "/sys/devices/cpu");