/src/mozilla-central/toolkit/xre/SafeMode.h
Line | Count | Source (jump to first uncovered line) |
1 | | /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ |
2 | | /* vim: set ts=8 sts=2 et sw=2 tw=80: */ |
3 | | /* This Source Code Form is subject to the terms of the Mozilla Public |
4 | | * License, v. 2.0. If a copy of the MPL was not distributed with this |
5 | | * file, You can obtain one at https://mozilla.org/MPL/2.0/. */ |
6 | | |
7 | | #ifndef mozilla_SafeMode_h |
8 | | #define mozilla_SafeMode_h |
9 | | |
10 | | // NB: This code must be able to run apart from XPCOM |
11 | | |
12 | | #include "mozilla/CmdLineAndEnvUtils.h" |
13 | | #include "mozilla/Maybe.h" |
14 | | |
15 | | #if defined(XP_WIN) |
16 | | #include "mozilla/PolicyChecks.h" |
17 | | #include <windows.h> |
18 | | #endif // defined(XP_WIN) |
19 | | |
20 | | // Undo X11/X.h's definition of None |
21 | | #undef None |
22 | | |
23 | | namespace mozilla { |
24 | | |
25 | | enum class SafeModeFlag : uint32_t |
26 | | { |
27 | | None = 0, |
28 | | Unset = (1 << 0), |
29 | | NoKeyPressCheck = (1 << 1), |
30 | | }; |
31 | | |
32 | | MOZ_MAKE_ENUM_CLASS_BITWISE_OPERATORS(SafeModeFlag) |
33 | | |
34 | | template <typename CharT> |
35 | | inline Maybe<bool> |
36 | | IsSafeModeRequested(int& aArgc, CharT* aArgv[], |
37 | | const SafeModeFlag aFlags = SafeModeFlag::Unset) |
38 | 3 | { |
39 | 3 | CheckArgFlag checkArgFlags = CheckArgFlag::CheckOSInt; |
40 | 3 | if (aFlags & SafeModeFlag::Unset) { |
41 | 3 | checkArgFlags |= CheckArgFlag::RemoveArg; |
42 | 3 | } |
43 | 3 | |
44 | 3 | ArgResult ar = CheckArg(aArgc, aArgv, |
45 | 3 | GetLiteral<CharT, FlagLiteral::safemode>(), |
46 | 3 | static_cast<const CharT**>(nullptr), |
47 | 3 | checkArgFlags); |
48 | 3 | if (ar == ARG_BAD) { |
49 | 0 | return Nothing(); |
50 | 0 | } |
51 | 3 | |
52 | 3 | bool result = ar == ARG_FOUND; |
53 | 3 | |
54 | | #if defined(XP_WIN) |
55 | | // If the shift key is pressed and the ctrl and / or alt keys are not pressed |
56 | | // during startup, start in safe mode. GetKeyState returns a short and the high |
57 | | // order bit will be 1 if the key is pressed. By masking the returned short |
58 | | // with 0x8000 the result will be 0 if the key is not pressed and non-zero |
59 | | // otherwise. |
60 | | if (!(aFlags & SafeModeFlag::NoKeyPressCheck) && |
61 | | (GetKeyState(VK_SHIFT) & 0x8000) && |
62 | | !(GetKeyState(VK_CONTROL) & 0x8000) && |
63 | | !(GetKeyState(VK_MENU) & 0x8000) && |
64 | | !EnvHasValue("MOZ_DISABLE_SAFE_MODE_KEY")) { |
65 | | result = true; |
66 | | } |
67 | | |
68 | | if (result && PolicyCheckBoolean(L"DisableSafeMode")) { |
69 | | result = false; |
70 | | } |
71 | | #endif // defined(XP_WIN) |
72 | | |
73 | | #if defined(XP_MACOSX) |
74 | | if (!(aFlags & SafeModeFlag::NoKeyPressCheck) && |
75 | | (GetCurrentEventKeyModifiers() & optionKey) && |
76 | | !EnvHasValue("MOZ_DISABLE_SAFE_MODE_KEY")) { |
77 | | result = true; |
78 | | } |
79 | | #endif // defined(XP_MACOSX) |
80 | | |
81 | 3 | // The Safe Mode Policy should not be enforced for the env var case |
82 | 3 | // (used by updater and crash-recovery). |
83 | 3 | if (EnvHasValue("MOZ_SAFE_MODE_RESTART")) { |
84 | 0 | result = true; |
85 | 0 | if (aFlags & SafeModeFlag::Unset) { |
86 | 0 | // unset the env variable |
87 | 0 | SaveToEnv("MOZ_SAFE_MODE_RESTART="); |
88 | 0 | } |
89 | 0 | } |
90 | 3 | |
91 | 3 | return Some(result); |
92 | 3 | } |
93 | | |
94 | | } // namespace mozilla |
95 | | |
96 | | #endif // mozilla_SafeMode_h |