Since `CheckArg`'s `aParam` is declared as `const CharT **`, it's
treated as a deduction parameter. Unfortunately, `nullptr` is of type
`nullptr_t`, and it doesn't get coerced before template argument
deduction takes place. To allow passing `nullptr`, people have been
using unwieldy constructs like `static_cast<const wchar_t**>(nullptr)`
when `aParam` isn't needed.
Centralize this by adding an overload of `CheckArg` that explicitly
takes `nullptr_t` and forwards it on to the primary implementation.
Strip out all the now-unnecessary `static_cast`s everywhere else.
No functional changes.
Differential Revision: https://phabricator.services.mozilla.com/D152327
Set the size-field of the struct before passing it to Windows, as one
customarily does.
(Given that STARTUPINFOEXW exists, it's not likely that this will ever
actually cause issues. But let's not rely on that.)
No functional changes.
Differential Revision: https://phabricator.services.mozilla.com/D152544
Write the deelevation-status enum value into the parent process, where
it will (hopefully) show up in the event of a crash report.
(Presenting this value more conveniently -- _e.g._, in `about:support`
and/or Firefox telemetry -- would require additional plumbing, and so
has been left to future work as bug 1774703.)
This commit was previously submitted as D149546, and has not changed.
Differential Revision: https://phabricator.services.mozilla.com/D152326
Add a new command-line flag `--attempting-deelevation` which prevents
the launcher from entering an infinite loop of deelevation attempts.
Additionally, produce an enum value indicating the decisions made by the
launcher process. (Nothing is done with this value yet; that will happen
in the following commit.)
A commit loosely analogous to this was previously submitted as D149545.
Differential Revision: https://phabricator.services.mozilla.com/D152325
Eliminate the need to keep Firefox's required-argument set in sync
across files by defining it only in a new header file.
No functional changes.
Differential Revision: https://phabricator.services.mozilla.com/D152543
`strimatch` attempts to perform a generic case-insensitive match.
However, it doesn't handle edge cases very well -- and, for deep Unicode
reasons, it can't reasonably do so without being far more complicated.
However, we also don't need it to. The `lowerstr` input of `strimatch`
is only ever a constant string naming a command-line option. These are
(and probably always should be) strictly composed of lowercase ASCII,
numerals, and hyphens. _That_ character set is one that a simple
function can properly handle.
Restricting `lowerstr` to be `const char *`, regardless of `CharT`, also
obviates the macro-machinery of `GetLiteral` and `DECLARE_FLAG_LITERAL`.
Strip it all out.
Additionally and relatedly:
* Add tests confirming that `strimatch` only matches things that it
should be testing against at all.
* Add a minor fix for a test which was discovered to crash rather than
report failure.
----
Although this commit involves significant internal functional changes,
most users will see no differences. (Some users operating in Turkish or
Azerbaijani locales may notice that "-PRİVATE-WINDOW" is no longer a
recognized command-line option.)
Differential Revision: https://phabricator.services.mozilla.com/D152321
Write the deelevation-status enum value into the parent process, where
it will (hopefully) show up in the event of a crash report.
(Presenting this value more conveniently -- _e.g._, in `about:support`
and/or Firefox telemetry -- would require additional plumbing, and so
has been left to future work.)
Depends on D149545
Differential Revision: https://phabricator.services.mozilla.com/D149546
Add a new command-line flag `--attempting-deelevation` which prevents
the launcher from entering an infinite loop of deelevation attempts.
Additionally, produce an enum value indicating the decisions made by the
launcher process. (Nothing is done with this value yet; that will happen
in the following commit.)
Depends on D149544
Differential Revision: https://phabricator.services.mozilla.com/D149545
When the launcher process is enabled, Puppeteer, or any other automation tools, cannot
have control of the lifetime of the browser process even though the `--wait-for-browser`
option is used.
This patch is to include the launcher process and the browser process to a job to enable
a launcher of the launcher process like Puppeteer to terminate the application by terminating
the launcher process if `--wait-for-browser` is set.
Differential Revision: https://phabricator.services.mozilla.com/D131170
When the launcher process is enabled, Puppeteer, or any other automation tools, cannot
have control of the lifetime of the browser process even though the `--wait-for-browser`
option is used.
This patch is to include the launcher process and the browser process to a job to enable
a launcher of the launcher process like Puppeteer to terminate the application by terminating
the launcher process if `--wait-for-browser` is set.
Differential Revision: https://phabricator.services.mozilla.com/D131170
A. The shell provides the startup shortcut in STARTUPINFOW when it
starts a process. If the launcher process runs, we must pass this along
to the real process being created.
B. lpTitle can be overwritten, in particular when the AUMID is set for
WinTaskbar, so save it in XREMain::XRE_mainStartup() in order to access
it later.
C. Add an accessor for the saved shortcut.
Differential Revision: https://phabricator.services.mozilla.com/D106343
This patch defines a new macro `MOZ_USE_LAUNCHER_ERROR` and keeps
the use of `LauncherError` behind `MOZ_USE_LAUNCHER_ERROR` instead of
`MOZILLA_INTERNAL_API` so that we can selectively use `LauncherError`
in locations where `MOZILLA_INTERNAL_API` is defined.
Differential Revision: https://phabricator.services.mozilla.com/D83638
If the process was elevated due to AppCompatFlags, we should not
use LaunchUnelevated to launch the browser process because it starts
an infinite loop of process launch.
The fix is to make GetElevationState return a new elevation state
if RUNASADMIN is set in AppCompatFlags. With that state, we use
CreateProcessAsUser to launch the browser process.
Differential Revision: https://phabricator.services.mozilla.com/D80114
Bug 1522830 added the call to `InitializeDllBlocklistOOP` in `SandboxBroker::LaunchApp`
to enable the new dll blocklist and telemetry in sandbox processes. If the browser
process fails to bootstrap a process for some reason, firefox starts without any crash
nor any content processes because of that change.
What is worse is that this problem persists even after the launcher process was disabled.
To mitigate it, this patch stops an attempt to bootstrap a child process if the launcher
process already failed to do it. With this, if something bad happens in the first launch,
the launcher process is automatically disabled via registry and next time firefox will work
normally. So a user will see the launching problem only once.
We will follow up the bootstrap issue.
Differential Revision: https://phabricator.services.mozilla.com/D62636
--HG--
extra : moz-landing-system : lando
We have the `LauncherRegistryInfo` class to check the launcher process was
launched successfully on Windows by comparing the timestamps in the registry
when each process was launched.
The problem was when the process is launched from an elevated process, we
relaunch a new launcher process via shell after we updated the launcher's
timestamp. As a result, `LauncherRegistryInfo` unexpectedly disabled the
launcher process even though there was nothing wrong.
A proposed fix is to introduce delay-write to the `LauncherRegistryInfo`. With
this, `LauncherRegistryInfo::Check` modifies only the image timestamp. To update
the launcher/browser timestamps, we need to call `LauncherRegistryInfo::Commit`.
When we ask shell to relaunch a new process, we hold back commit, delegating it
to the new process.
There is another consideration needed. If something fails during `LauncherMain`,
we call `DisableDueToFailure()` to disable the launcher until the image timestamp
is changed. In such a case, we should not change the stored timestamps even
though commit is attempted. The problem is we use a different instance to call
`DisableDueToFailure()` in `HandleLauncherError`. To deal with this design,
`LauncherRegistryInfo` has a static boolean to indicate disablement happens or not.
Differential Revision: https://phabricator.services.mozilla.com/D44928
--HG--
extra : moz-landing-system : lando
* We refactor the blocklist code. Code that may possibly run before
initialization of the Win32 subsystem and the CRT is contained within the
`freestanding` library.
* The `freestanding` library's static initializers are placed in their own
section so that they may be manually invoked separately from the remaining
initializers in the binary.
* `CheckBlockInfo` and `IsDllAllowed` are modified to return a `BlockAction`
enum instead of a `bool`. This will be used more extensively in the future for
LSP blocking.
* The launcher process now hooks `LdrLoadDll` in addition to
`NtMapViewOfSection`. This is necessary so that we can collect timing
information.
* Telemetry recorders must implement the `LoaderObserver` interface.
* `ModuleLoadFrame` is a RAII class that collects the information about the
DLL load and dispatches the information to `LoaderObserver`s.
* The launcher process exposes an implementation of the `LoaderAPI` interface
that may be called by either the launcher process blocklist or the legacy
blocklist in `mozglue`.
* During startup, the launcher process implements its own `LoaderObserver`.
Once mozglue is running, it connects its `LoaderObserver` to the launcher
process, receives a vector containing the module load events, and then
stores and forwards them into XUL.
Depends on D43155
Differential Revision: https://phabricator.services.mozilla.com/D43156
--HG--
rename : browser/app/winlauncher/DllBlocklistWin.cpp => browser/app/winlauncher/DllBlocklistInit.cpp
rename : browser/app/winlauncher/DllBlocklistWin.h => browser/app/winlauncher/DllBlocklistInit.h
rename : browser/app/winlauncher/DllBlocklistWin.cpp => browser/app/winlauncher/freestanding/DllBlocklist.cpp
rename : browser/app/winlauncher/DllBlocklistWin.h => browser/app/winlauncher/freestanding/DllBlocklist.h
rename : browser/app/winlauncher/moz.build => browser/app/winlauncher/freestanding/moz.build
extra : moz-landing-system : lando
We compare two file ids to check the current process is launched from the same
executable. However, our telemetry showed a number of Win7 users failed to open
a file handle of the parent process with STATUS_OBJECT_PATH_NOT_FOUND even
though we opened a process handle and retrieved a module path of the parent
process successfully. We don't have data to explain how this happens or why
this happens only on Win7, Win10 10240, and 10586.
To mitigate this situation, this patch introduces a logic to compare NT path
strings. The benefit from doing this is 1) we don't have to open a file handle
of a parent process executable and 2) when we get an NT path, a network drive
or a symbolic link is already solved.
This new logic is much faster, but we still compare file ids on the first
attempt to minimize the impact. We fall back to the new logic only if we
detect the STATUS_OBJECT_PATH_NOT_FOUND failure.
Differential Revision: https://phabricator.services.mozilla.com/D45476
--HG--
extra : moz-landing-system : lando
* We refactor the blocklist code. Code that may possibly run before
initialization of the Win32 subsystem and the CRT is contained within the
`freestanding` library.
* The `freestanding` library's static initializers are placed in their own
section so that they may be manually invoked separately from the remaining
initializers in the binary.
* `CheckBlockInfo` and `IsDllAllowed` are modified to return a `BlockAction`
enum instead of a `bool`. This will be used more extensively in the future for
LSP blocking.
* The launcher process now hooks `LdrLoadDll` in addition to
`NtMapViewOfSection`. This is necessary so that we can collect timing
information.
* Telemetry recorders must implement the `LoaderObserver` interface.
* `ModuleLoadFrame` is a RAII class that collects the information about the
DLL load and dispatches the information to `LoaderObserver`s.
* The launcher process exposes an implementation of the `LoaderAPI` interface
that may be called by either the launcher process blocklist or the legacy
blocklist in `mozglue`.
* During startup, the launcher process implements its own `LoaderObserver`.
Once mozglue is running, it connects its `LoaderObserver` to the launcher
process, receives a vector containing the module load events, and then
stores and forwards them into XUL.
Differential Revision: https://phabricator.services.mozilla.com/D43156
--HG--
rename : browser/app/winlauncher/DllBlocklistWin.cpp => browser/app/winlauncher/DllBlocklistInit.cpp
rename : browser/app/winlauncher/DllBlocklistWin.h => browser/app/winlauncher/DllBlocklistInit.h
rename : browser/app/winlauncher/DllBlocklistWin.cpp => browser/app/winlauncher/freestanding/DllBlocklist.cpp
rename : browser/app/winlauncher/DllBlocklistWin.h => browser/app/winlauncher/freestanding/DllBlocklist.h
rename : browser/app/winlauncher/moz.build => browser/app/winlauncher/freestanding/moz.build
extra : moz-landing-system : lando
* We refactor the blocklist code. Code that may possibly run before
initialization of the Win32 subsystem and the CRT is contained within the
`freestanding` library.
* The `freestanding` library's static initializers are placed in their own
section so that they may be manually invoked separately from the remaining
initializers in the binary.
* `CheckBlockInfo` and `IsDllAllowed` are modified to return a `BlockAction`
enum instead of a `bool`. This will be used more extensively in the future for
LSP blocking.
* The launcher process now hooks `LdrLoadDll` in addition to
`NtMapViewOfSection`. This is necessary so that we can collect timing
information.
* Telemetry recorders must implement the `LoaderObserver` interface.
* `ModuleLoadFrame` is a RAII class that collects the information about the
DLL load and dispatches the information to `LoaderObserver`s.
* The launcher process exposes an implementation of the `LoaderAPI` interface
that may be called by either the launcher process blocklist or the legacy
blocklist in `mozglue`.
* During startup, the launcher process implements its own `LoaderObserver`.
Once mozglue is running, it connects its `LoaderObserver` to the launcher
process, receives a vector containing the module load events, and then
stores and forwards them into XUL.
Differential Revision: https://phabricator.services.mozilla.com/D43156
--HG--
rename : browser/app/winlauncher/DllBlocklistWin.cpp => browser/app/winlauncher/DllBlocklistInit.cpp
rename : browser/app/winlauncher/DllBlocklistWin.h => browser/app/winlauncher/DllBlocklistInit.h
rename : browser/app/winlauncher/DllBlocklistWin.cpp => browser/app/winlauncher/freestanding/DllBlocklist.cpp
rename : browser/app/winlauncher/DllBlocklistWin.h => browser/app/winlauncher/freestanding/DllBlocklist.h
rename : browser/app/winlauncher/moz.build => browser/app/winlauncher/freestanding/moz.build
extra : moz-landing-system : lando
* We refactor the blocklist code. Code that may possibly run before
initialization of the Win32 subsystem and the CRT is contained within the
`freestanding` library.
* The `freestanding` library's static initializers are placed in their own
section so that they may be manually invoked separately from the remaining
initializers in the binary.
* `CheckBlockInfo` and `IsDllAllowed` are modified to return a `BlockAction`
enum instead of a `bool`. This will be used more extensively in the future for
LSP blocking.
* The launcher process now hooks `LdrLoadDll` in addition to
`NtMapViewOfSection`. This is necessary so that we can collect timing
information.
* Telemetry recorders must implement the `LoaderObserver` interface.
* `ModuleLoadFrame` is a RAII class that collects the information about the
DLL load and dispatches the information to `LoaderObserver`s.
* The launcher process exposes an implementation of the `LoaderAPI` interface
that may be called by either the launcher process blocklist or the legacy
blocklist in `mozglue`.
* During startup, the launcher process implements its own `LoaderObserver`.
Once mozglue is running, it connects its `LoaderObserver` to the launcher
process, receives a vector containing the module load events, and then
stores and forwards them into XUL.
Differential Revision: https://phabricator.services.mozilla.com/D43156
--HG--
rename : browser/app/winlauncher/DllBlocklistWin.cpp => browser/app/winlauncher/DllBlocklistInit.cpp
rename : browser/app/winlauncher/DllBlocklistWin.h => browser/app/winlauncher/DllBlocklistInit.h
rename : browser/app/winlauncher/DllBlocklistWin.cpp => browser/app/winlauncher/freestanding/DllBlocklist.cpp
rename : browser/app/winlauncher/DllBlocklistWin.h => browser/app/winlauncher/freestanding/DllBlocklist.h
rename : browser/app/winlauncher/moz.build => browser/app/winlauncher/freestanding/moz.build
extra : moz-landing-system : lando
`WindowsErrorResult` is a class to hold either a value or a Windows error
code based on the `Result` template. We also have `LauncherResult` for the
same purpose, which was introduced as a part of the launcher process feature
afterward. The difference is `LauncherResult` holds a filename and line
number along with an error code.
This patch integrates LauncherResult.h into WinHeaderOnlyUtils.h so that we
can use `LauncherResult` more broadly.
Differential Revision: https://phabricator.services.mozilla.com/D44512
--HG--
extra : moz-landing-system : lando