Skip site navigation (1)Skip section navigation (2)
Date:      Mon, 15 Feb 2021 21:28:15 +0000 (UTC)
From:      Jan Beich <jbeich@FreeBSD.org>
To:        ports-committers@freebsd.org, svn-ports-all@freebsd.org, svn-ports-head@freebsd.org
Subject:   svn commit: r565343 - in head/www/firefox: . files
Message-ID:  <202102152128.11FLSFWk045209@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: jbeich
Date: Mon Feb 15 21:28:15 2021
New Revision: 565343
URL: https://svnweb.freebsd.org/changeset/ports/565343

Log:
  www/firefox: update to 86.0
  
  Changes:	https://www.mozilla.org/firefox/86.0/releasenotes/

Added:
  head/www/firefox/files/patch-bug1680982   (contents, props changed)
  head/www/firefox/files/patch-bug1686713   (contents, props changed)
Deleted:
  head/www/firefox/files/patch-bug1684261
  head/www/firefox/files/patch-bug1687487
  head/www/firefox/files/patch-bug1690152
Modified:
  head/www/firefox/Makefile   (contents, props changed)
  head/www/firefox/distinfo   (contents, props changed)
  head/www/firefox/files/patch-addon-search   (contents, props changed)
  head/www/firefox/pkg-message   (contents, props changed)

Modified: head/www/firefox/Makefile
==============================================================================
--- head/www/firefox/Makefile	Mon Feb 15 21:21:04 2021	(r565342)
+++ head/www/firefox/Makefile	Mon Feb 15 21:28:15 2021	(r565343)
@@ -2,8 +2,7 @@
 # $FreeBSD$
 
 PORTNAME=	firefox
-DISTVERSION=	85.0.2
-PORTREVISION=	1
+DISTVERSION=	86.0
 PORTEPOCH=	2
 CATEGORIES=	www
 MASTER_SITES=	MOZILLA/${PORTNAME}/releases/${DISTVERSION}/source \

Modified: head/www/firefox/distinfo
==============================================================================
--- head/www/firefox/distinfo	Mon Feb 15 21:21:04 2021	(r565342)
+++ head/www/firefox/distinfo	Mon Feb 15 21:28:15 2021	(r565343)
@@ -1,3 +1,3 @@
-TIMESTAMP = 1612802741
-SHA256 (firefox-85.0.2.source.tar.xz) = b157cdc265daa6140ec8daef2bc98d335f871e7e9ac235287fb199e11c164287
-SIZE (firefox-85.0.2.source.tar.xz) = 372234168
+TIMESTAMP = 1613411049
+SHA256 (firefox-86.0.source.tar.xz) = 5a12bca96ec5d7e5febc750b5400fbd78ffa143cc3a90942bd045af34ac9fdd7
+SIZE (firefox-86.0.source.tar.xz) = 368780392

Modified: head/www/firefox/files/patch-addon-search
==============================================================================
--- head/www/firefox/files/patch-addon-search	Mon Feb 15 21:21:04 2021	(r565342)
+++ head/www/firefox/files/patch-addon-search	Mon Feb 15 21:28:15 2021	(r565343)
@@ -5,16 +5,16 @@ diff --git browser/app/profile/firefox.js browser/app/
 index 75c2c5e435e35..4d8c09c02759b 100644
 --- browser/app/profile/firefox.js
 +++ browser/app/profile/firefox.js
-@@ -37,7 +37,7 @@ pref("extensions.webextOptionalPermissionPrompts", true);
+@@ -39,7 +39,7 @@ pref("extensions.postDownloadThirdPartyPrompt", true);
  // Preferences for AMO integration
  pref("extensions.getAddons.cache.enabled", true);
- pref("extensions.getAddons.get.url", "https://services.addons.mozilla.org/api/v3/addons/search/?guid=%IDS%&lang=%LOCALE%");
+ pref("extensions.getAddons.get.url", "https://services.addons.mozilla.org/api/v4/addons/search/?guid=%IDS%&lang=%LOCALE%");
 -pref("extensions.getAddons.search.browseURL", "https://addons.mozilla.org/%LOCALE%/firefox/search?q=%TERMS%&platform=%OS%&appver=%VERSION%");
 +pref("extensions.getAddons.search.browseURL", "https://addons.mozilla.org/%LOCALE%/firefox/search?q=%TERMS%&platform=Linux&appver=%VERSION%");
  pref("extensions.getAddons.link.url", "https://addons.mozilla.org/%LOCALE%/firefox/");
- pref("extensions.getAddons.langpacks.url", "https://services.addons.mozilla.org/api/v3/addons/language-tools/?app=firefox&type=language&appversion=%VERSION%");
+ pref("extensions.getAddons.langpacks.url", "https://services.addons.mozilla.org/api/v4/addons/language-tools/?app=firefox&type=language&appversion=%VERSION%");
  pref("extensions.getAddons.discovery.api_url", "https://services.addons.mozilla.org/api/v4/discovery/?lang=%LOCALE%&edition=%DISTRIBUTION%");
-@@ -168,8 +168,8 @@ pref("app.update.staging.enabled", true);
+@@ -176,8 +176,8 @@ pref("app.update.langpack.enabled", true);
  //  .. etc ..
  //
  pref("extensions.update.enabled", true);

Added: head/www/firefox/files/patch-bug1680982
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/www/firefox/files/patch-bug1680982	Mon Feb 15 21:28:15 2021	(r565343)
@@ -0,0 +1,369 @@
+commit d947b92c7503
+Author: Greg V <greg@unrelenting.technology>
+Date:   Sun Dec 6 22:07:00 2020 +0000
+
+    Bug 1680982 - Use evdev for gamepads on Linux/FreeBSD
+    
+    Switch from the legacy Linux joystick API to the generic evdev API.
+    
+    - BTN_GAMEPAD semantic buttons are interpreted directly,
+    since all kernel drivers are supposed to use them correctly:
+    https://www.kernel.org/doc/html/latest/input/gamepad.html
+    - BTN_JOYSTICK legacy style numbered buttons use the model specific remappers
+    - using evdev is a prerequisite for adding rumble (haptic feedback) and other extras
+    - the Linux gamepad module is enabled on FreeBSD, because
+    FreeBSD provides evdev, and libudev-devd provides enough of libudev
+    (evdev headers are provided by the devel/evdev-proto package)
+    
+    Differential Revision: https://phabricator.services.mozilla.com/D98868
+---
+ dom/gamepad/linux/LinuxGamepad.cpp | 243 +++++++++++++++++++++++++++++++------
+ dom/gamepad/moz.build              |   2 +-
+ 2 files changed, 210 insertions(+), 35 deletions(-)
+
+diff --git dom/gamepad/linux/LinuxGamepad.cpp dom/gamepad/linux/LinuxGamepad.cpp
+index 512ac765020d..0e51183c2a2d 100644
+--- dom/gamepad/linux/LinuxGamepad.cpp
++++ dom/gamepad/linux/LinuxGamepad.cpp
+@@ -5,15 +5,16 @@
+  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+ 
+ /*
+- * LinuxGamepadService: A Linux backend for the GamepadService.
+- * Derived from the kernel documentation at
+- * http://www.kernel.org/doc/Documentation/input/joystick-api.txt
++ * LinuxGamepadService: An evdev backend for the GamepadService.
++ *
++ * Ref: https://www.kernel.org/doc/html/latest/input/gamepad.html
+  */
+ #include <algorithm>
++#include <unordered_map>
+ #include <cstddef>
+ 
+ #include <glib.h>
+-#include <linux/joystick.h>
++#include <linux/input.h>
+ #include <stdio.h>
+ #include <stdint.h>
+ #include <sys/ioctl.h>
+@@ -21,10 +22,14 @@
+ #include "nscore.h"
+ #include "mozilla/dom/GamepadHandle.h"
+ #include "mozilla/dom/GamepadPlatformService.h"
++#include "mozilla/dom/GamepadRemapping.h"
+ #include "mozilla/Tainting.h"
+ #include "mozilla/UniquePtr.h"
+ #include "udev.h"
+ 
++#define LONG_BITS (sizeof(long) * 8)
++#define NLONGS(x) (((x) + LONG_BITS - 1) / LONG_BITS)
++
+ namespace {
+ 
+ using namespace mozilla::dom;
+@@ -36,19 +41,29 @@ using mozilla::udev_list_entry;
+ using mozilla::udev_monitor;
+ using mozilla::UniquePtr;
+ 
+-static const float kMaxAxisValue = 32767.0;
+-static const char kJoystickPath[] = "/dev/input/js";
++static const char kEvdevPath[] = "/dev/input/event";
++
++static inline bool TestBit(const unsigned long* arr, int bit) {
++  return !!(arr[bit / LONG_BITS] & (1LL << (bit % LONG_BITS)));
++}
++
++static inline double ScaleAxis(const input_absinfo& info, int value) {
++  return 2.0 * (value - info.minimum) / (double)(info.maximum - info.minimum) -
++         1.0;
++}
+ 
+ // TODO: should find a USB identifier for each device so we can
+ // provide something that persists across connect/disconnect cycles.
+-typedef struct {
++struct Gamepad {
+   GamepadHandle handle;
+-  guint source_id;
+-  int numAxes;
+-  int numButtons;
+-  char idstring[256];
+-  char devpath[PATH_MAX];
+-} Gamepad;
++  RefPtr<GamepadRemapper> remapper = nullptr;
++  guint source_id = UINT_MAX;
++  char idstring[256] = {0};
++  char devpath[PATH_MAX] = {0};
++  uint8_t key_map[KEY_MAX] = {0};
++  uint8_t abs_map[ABS_MAX] = {0};
++  std::unordered_map<uint16_t, input_absinfo> abs_info;
++};
+ 
+ class LinuxGamepadService {
+  public:
+@@ -66,7 +81,7 @@ class LinuxGamepadService {
+   bool is_gamepad(struct udev_device* dev);
+   void ReadUdevChange();
+ 
+-  // handler for data from /dev/input/jsN
++  // handler for data from /dev/input/eventN
+   static gboolean OnGamepadData(GIOChannel* source, GIOCondition condition,
+                                 gpointer data);
+ 
+@@ -114,8 +129,12 @@ void LinuxGamepadService::AddDevice(struct udev_device* dev) {
+   g_io_channel_set_encoding(channel, nullptr, nullptr);
+   g_io_channel_set_buffered(channel, FALSE);
+   int fd = g_io_channel_unix_get_fd(channel);
++
++  struct input_id id = {0};
++  ioctl(fd, EVIOCGID, &id);
++
+   char name[128];
+-  if (ioctl(fd, JSIOCGNAME(sizeof(name)), &name) == -1) {
++  if (ioctl(fd, EVIOCGNAME(sizeof(name)), &name) == -1) {
+     strcpy(name, "unknown");
+   }
+   const char* vendor_id =
+@@ -131,20 +150,69 @@ void LinuxGamepadService::AddDevice(struct udev_device* dev) {
+       model_id = mUdev.udev_device_get_sysattr_value(parent, "id/product");
+     }
+   }
++  if (!vendor_id && id.vendor != 0) {
++    vendor_id = (const char*)alloca(5);
++    snprintf((char*)vendor_id, 5, "%04x", id.vendor);
++  }
++  if (!model_id && id.product != 0) {
++    model_id = (const char*)alloca(5);
++    snprintf((char*)model_id, 5, "%04x", id.product);
++  }
+   snprintf(gamepad->idstring, sizeof(gamepad->idstring), "%s-%s-%s",
+            vendor_id ? vendor_id : "unknown", model_id ? model_id : "unknown",
+            name);
+ 
+   char numAxes = 0, numButtons = 0;
+-  ioctl(fd, JSIOCGAXES, &numAxes);
+-  gamepad->numAxes = numAxes;
+-  ioctl(fd, JSIOCGBUTTONS, &numButtons);
+-  gamepad->numButtons = numButtons;
++  unsigned long key_bits[NLONGS(KEY_CNT)] = {0};
++  unsigned long abs_bits[NLONGS(ABS_CNT)] = {0};
++  ioctl(fd, EVIOCGBIT(EV_KEY, sizeof(key_bits)), key_bits);
++  ioctl(fd, EVIOCGBIT(EV_ABS, sizeof(abs_bits)), abs_bits);
++  for (uint16_t i = BTN_JOYSTICK; i < KEY_MAX; i++) {
++    /* Skip proper gamepad events, they are handled directly */
++    if (i == BTN_GAMEPAD) {
++      i = BTN_THUMBR + 1;
++      continue;
++    }
++    if (i == BTN_DPAD_UP) {
++      i = BTN_DPAD_RIGHT + 1;
++      continue;
++    }
++    if (TestBit(key_bits, i)) {
++      gamepad->key_map[i] = numButtons++;
++    }
++  }
++  for (uint16_t i = 0; i < BTN_JOYSTICK; i++) {
++    if (TestBit(key_bits, i)) {
++      gamepad->key_map[i] = numButtons++;
++    }
++  }
++  for (uint16_t i = 0; i < ABS_MAX; ++i) {
++    if (TestBit(abs_bits, i)) {
++      gamepad->abs_info.emplace(i, input_absinfo{});
++      if (ioctl(fd, EVIOCGABS(i), &gamepad->abs_info[i]) < 0) {
++        continue;
++      }
++      if (gamepad->abs_info[i].minimum == gamepad->abs_info[i].maximum) {
++        gamepad->abs_info.erase(i);
++        continue;
++      }
++      gamepad->abs_map[i] = numAxes++;
++    }
++  }
++
++  bool defaultRemapper = false;
++  RefPtr<GamepadRemapper> remapper =
++      GetGamepadRemapper(id.vendor, id.product, defaultRemapper);
++  MOZ_ASSERT(remapper);
++  remapper->SetAxisCount(numAxes);
++  remapper->SetButtonCount(numButtons);
+ 
+   gamepad->handle = service->AddGamepad(
+-      gamepad->idstring, mozilla::dom::GamepadMappingType::_empty,
+-      mozilla::dom::GamepadHand::_empty, gamepad->numButtons, gamepad->numAxes,
+-      0, 0, 0);  // TODO: Bug 680289, implement gamepad haptics for Linux.
++      gamepad->idstring, remapper->GetMappingType(), GamepadHand::_empty,
++      remapper->GetButtonCount(), remapper->GetAxisCount(), 0,
++      remapper->GetLightIndicatorCount(), remapper->GetTouchEventCount());
++  gamepad->remapper = remapper.forget();
++  // TODO: Bug 680289, implement gamepad haptics for Linux.
+   // TODO: Bug 1523355, implement gamepad lighindicator and touch for Linux.
+ 
+   gamepad->source_id =
+@@ -257,7 +325,7 @@ bool LinuxGamepadService::is_gamepad(struct udev_device* dev) {
+   if (!devpath) {
+     return false;
+   }
+-  if (strncmp(kJoystickPath, devpath, sizeof(kJoystickPath) - 1) != 0) {
++  if (strncmp(kEvdevPath, devpath, sizeof(kEvdevPath) - 1) != 0) {
+     return false;
+   }
+ 
+@@ -292,7 +360,7 @@ gboolean LinuxGamepadService::OnGamepadData(GIOChannel* source,
+   if (condition & G_IO_ERR || condition & G_IO_HUP) return FALSE;
+ 
+   while (true) {
+-    struct js_event event;
++    struct input_event event = {0};
+     gsize count;
+     GError* err = nullptr;
+     if (g_io_channel_read_chars(source, (gchar*)&event, sizeof(event), &count,
+@@ -301,18 +369,125 @@ gboolean LinuxGamepadService::OnGamepadData(GIOChannel* source,
+       break;
+     }
+ 
+-    // TODO: store device state?
+-    if (event.type & JS_EVENT_INIT) {
+-      continue;
+-    }
+-
+     switch (event.type) {
+-      case JS_EVENT_BUTTON:
+-        service->NewButtonEvent(gamepad->handle, event.number, !!event.value);
++      case EV_KEY:
++        switch (event.code) {
++          /* The gamepad events are meaningful, and according to
++           * https://www.kernel.org/doc/html/latest/input/gamepad.html
++           * "No other devices, that do not look/feel like a gamepad, shall
++           * report these events" */
++          case BTN_SOUTH:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_PRIMARY,
++                                    !!event.value);
++            break;
++          case BTN_EAST:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_SECONDARY,
++                                    !!event.value);
++            break;
++          case BTN_NORTH:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_QUATERNARY,
++                                    !!event.value);
++            break;
++          case BTN_WEST:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_TERTIARY,
++                                    !!event.value);
++            break;
++          case BTN_TL:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_LEFT_SHOULDER,
++                                    !!event.value);
++            break;
++          case BTN_TR:
++            service->NewButtonEvent(gamepad->handle,
++                                    BUTTON_INDEX_RIGHT_SHOULDER, !!event.value);
++            break;
++          case BTN_TL2:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_LEFT_TRIGGER,
++                                    !!event.value);
++            break;
++          case BTN_TR2:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_RIGHT_TRIGGER,
++                                    !!event.value);
++            break;
++          case BTN_SELECT:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_BACK_SELECT,
++                                    !!event.value);
++            break;
++          case BTN_START:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_START,
++                                    !!event.value);
++            break;
++          case BTN_MODE:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_META,
++                                    !!event.value);
++            break;
++          case BTN_THUMBL:
++            service->NewButtonEvent(
++                gamepad->handle, BUTTON_INDEX_LEFT_THUMBSTICK, !!event.value);
++            break;
++          case BTN_THUMBR:
++            service->NewButtonEvent(
++                gamepad->handle, BUTTON_INDEX_RIGHT_THUMBSTICK, !!event.value);
++            break;
++          case BTN_DPAD_UP:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_DPAD_UP,
++                                    !!event.value);
++            break;
++          case BTN_DPAD_DOWN:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_DPAD_DOWN,
++                                    !!event.value);
++            break;
++          case BTN_DPAD_LEFT:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_DPAD_LEFT,
++                                    !!event.value);
++            break;
++          case BTN_DPAD_RIGHT:
++            service->NewButtonEvent(gamepad->handle, BUTTON_INDEX_DPAD_RIGHT,
++                                    !!event.value);
++            break;
++          default:
++            /* For non-gamepad events, this is the "anything goes" numbered
++             * handling that should be handled with remappers. */
++            gamepad->remapper->RemapButtonEvent(
++                gamepad->handle, gamepad->key_map[event.code], !!event.value);
++            break;
++        }
+         break;
+-      case JS_EVENT_AXIS:
+-        service->NewAxisMoveEvent(gamepad->handle, event.number,
+-                                  ((float)event.value) / kMaxAxisValue);
++      case EV_ABS:
++        if (!gamepad->abs_info.count(event.code)) continue;
++        switch (event.code) {
++          case ABS_HAT0X:
++            service->NewButtonEvent(
++                gamepad->handle, BUTTON_INDEX_DPAD_LEFT,
++                AxisNegativeAsButton(
++                    ScaleAxis(gamepad->abs_info[event.code], event.value)));
++            service->NewButtonEvent(
++                gamepad->handle, BUTTON_INDEX_DPAD_RIGHT,
++                AxisPositiveAsButton(
++                    ScaleAxis(gamepad->abs_info[event.code], event.value)));
++            break;
++          case ABS_HAT0Y:
++            service->NewButtonEvent(
++                gamepad->handle, BUTTON_INDEX_DPAD_UP,
++                AxisNegativeAsButton(
++                    ScaleAxis(gamepad->abs_info[event.code], event.value)));
++            service->NewButtonEvent(
++                gamepad->handle, BUTTON_INDEX_DPAD_DOWN,
++                AxisPositiveAsButton(
++                    ScaleAxis(gamepad->abs_info[event.code], event.value)));
++            break;
++          case ABS_HAT1X:
++          case ABS_HAT1Y:
++          case ABS_HAT2X:
++          case ABS_HAT2Y:
++          case ABS_HAT3X:
++          case ABS_HAT3Y:
++            break;
++          default:
++            gamepad->remapper->RemapAxisMoveEvent(
++                gamepad->handle, gamepad->abs_map[event.code],
++                ScaleAxis(gamepad->abs_info[event.code], event.value));
++            break;
++        }
+         break;
+     }
+   }
+diff --git dom/gamepad/moz.build dom/gamepad/moz.build
+index 5f55d5a95e96..b5d10e9d095a 100644
+--- dom/gamepad/moz.build
++++ dom/gamepad/moz.build
+@@ -59,7 +59,7 @@ elif CONFIG["MOZ_WIDGET_TOOLKIT"] == "windows":
+     UNIFIED_SOURCES += ["windows/WindowsGamepad.cpp"]
+ elif CONFIG["MOZ_WIDGET_TOOLKIT"] == "android":
+     UNIFIED_SOURCES += ["android/AndroidGamepad.cpp"]
+-elif CONFIG["OS_ARCH"] == "Linux":
++elif CONFIG["OS_ARCH"] == "Linux" or CONFIG["OS_ARCH"] == "FreeBSD":
+     UNIFIED_SOURCES += ["linux/LinuxGamepad.cpp"]
+ else:
+     UNIFIED_SOURCES += ["fallback/FallbackGamepad.cpp"]

Added: head/www/firefox/files/patch-bug1686713
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/www/firefox/files/patch-bug1686713	Mon Feb 15 21:28:15 2021	(r565343)
@@ -0,0 +1,76 @@
+commit 89e72841a8f5
+Author: Greg V <greg@unrelenting.technology>
+Date:   Thu Jan 14 22:16:53 2021 +0000
+
+    Bug 1686713 - Fix mozglue/misc/Uptime build on *BSD
+---
+ mozglue/misc/Uptime.cpp | 28 +++++++++++++++++-----------
+ 1 file changed, 17 insertions(+), 11 deletions(-)
+
+diff --git mozglue/misc/Uptime.cpp mozglue/misc/Uptime.cpp
+index bded4017ec13..0e953101994d 100644
+--- mozglue/misc/Uptime.cpp
++++ mozglue/misc/Uptime.cpp
+@@ -43,9 +43,7 @@ Maybe<uint64_t> NowIncludingSuspendMs() {
+   return Some(clock_gettime_nsec_np(CLOCK_MONOTONIC_RAW) / kNSperMS);
+ }
+ 
+-#endif  // macOS
+-
+-#if defined(XP_WIN)
++#elif defined(XP_WIN)
+ 
+ // Number of hundreds of nanoseconds in a millisecond
+ static constexpr uint64_t kHNSperMS = 10000;
+@@ -77,11 +75,23 @@ Maybe<uint64_t> NowIncludingSuspendMs() {
+   pQueryInterruptTime(&interrupt_time);
+   return Some(interrupt_time / kHNSperMS);
+ }
+-#endif  // XP_WIN
+ 
+-#if defined(XP_LINUX)  // including Android
++#else
++
+ #  include <time.h>
+ 
++#  ifdef CLOCK_UPTIME  // FreeBSD, OpenBSD
++#    define CLOCK_EXCLUDING_SUSPEND CLOCK_UPTIME
++#  else
++#    define CLOCK_EXCLUDING_SUSPEND CLOCK_MONOTONIC
++#  endif
++
++#  ifdef CLOCK_BOOTTIME  // Linux (including Android), OpenBSD (== MONOTONIC)
++#    define CLOCK_INCLUDING_SUSPEND CLOCK_BOOTTIME
++#  else
++#    define CLOCK_INCLUDING_SUSPEND CLOCK_MONOTONIC
++#  endif
++
+ // Number of nanoseconds in a millisecond.
+ static constexpr uint64_t kNSperMS = 1000000;
+ 
+@@ -92,23 +102,19 @@ uint64_t TimespecToMilliseconds(struct timespec aTs) {
+ Maybe<uint64_t> NowExcludingSuspendMs() {
+   struct timespec ts = {0};
+ 
+-  if (clock_gettime(CLOCK_MONOTONIC, &ts)) {
++  if (clock_gettime(CLOCK_EXCLUDING_SUSPEND, &ts)) {
+     return Nothing();
+   }
+   return Some(TimespecToMilliseconds(ts));
+ }
+ 
+ Maybe<uint64_t> NowIncludingSuspendMs() {
+-#  ifndef CLOCK_BOOTTIME
+-  return Nothing();
+-#  else
+   struct timespec ts = {0};
+ 
+-  if (clock_gettime(CLOCK_BOOTTIME, &ts)) {
++  if (clock_gettime(CLOCK_INCLUDING_SUSPEND, &ts)) {
+     return Nothing();
+   }
+   return Some(TimespecToMilliseconds(ts));
+-#  endif
+ }
+ 
+ #endif  // XP_LINUX

Modified: head/www/firefox/pkg-message
==============================================================================
--- head/www/firefox/pkg-message	Mon Feb 15 21:21:04 2021	(r565342)
+++ head/www/firefox/pkg-message	Mon Feb 15 21:28:15 2021	(r565343)
@@ -9,7 +9,6 @@ Some features found on Windows, macOS and Linux are no
 - Process sandboxing (requires Capsicum backend)
 - Reduced memory usage (requires mozjemalloc)
 - Crash Reporter (requires Google Breakpad and reproducible builds)
-- Gamepad API (requires libusbhid backend)
 - WebVR (requires open source runtime)
 - TCP fast open
 - `about:networking` (requires link state notification)
@@ -29,6 +28,11 @@ To force a specific backend open `about:config` page a
 Microphone selection only works in `oss`, `pulse`, `pulse-rust` backends.
 Other backends are limited to `default` which is usually `/dev/dsp`,
 so use virtual_oss to reroute microphones from non-default devices.
+
+## Gamepad API
+
+Requires evdev(4) joystick support. On FreeBSD 13.0 enable hgame(4)
+while older versions can use sysutils/iichid or multimedia/webcamd.
 
 ## smb:// issues
 Network group, machine, and share browsing does not work correctly.



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?202102152128.11FLSFWk045209>