Skip to content

Commit 158c0f2

Browse files
authored
permissions: add permission management for keyboards (#10367)
1 parent 44cb8f7 commit 158c0f2

File tree

5 files changed

+48
-12
lines changed

5 files changed

+48
-12
lines changed

src/config/ConfigManager.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2900,6 +2900,8 @@ std::optional<std::string> CConfigManager::handlePermission(const std::string& c
29002900
type = PERMISSION_TYPE_SCREENCOPY;
29012901
else if (data[1] == "plugin")
29022902
type = PERMISSION_TYPE_PLUGIN;
2903+
else if (data[1] == "keyboard" || data[1] == "keeb")
2904+
type = PERMISSION_TYPE_KEYBOARD;
29032905

29042906
if (data[2] == "ask")
29052907
mode = PERMISSION_RULE_ALLOW_MODE_ASK;

src/devices/IKeyboard.hpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,9 @@ class IKeyboard : public IHID {
7878
bool m_enabled = true;
7979
bool m_allowBinds = true;
8080

81+
// permission flag: whether this keyboard is allowed to be processed
82+
bool m_allowed = true;
83+
8184
// if the keymap is overridden by the implementation,
8285
// don't try to set keyboard rules anymore, to avoid overwriting the requested one.
8386
// e.g. Virtual keyboards with custom maps.

src/managers/input/InputManager.cpp

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@
3636
#include "../../managers/HookSystemManager.hpp"
3737
#include "../../managers/EventManager.hpp"
3838
#include "../../managers/LayoutManager.hpp"
39+
#include "../../managers/permissions/DynamicPermissionManager.hpp"
3940

4041
#include "../../helpers/time/Time.hpp"
4142

@@ -1054,6 +1055,27 @@ void CInputManager::applyConfigToKeyboard(SP<IKeyboard> pKeyboard) {
10541055
pKeyboard->m_resolveBindsBySym = RESOLVEBINDSBYSYM;
10551056
pKeyboard->m_allowBinds = ALLOWBINDS;
10561057

1058+
const auto PERM = g_pDynamicPermissionManager->clientPermissionModeWithString(-1, pKeyboard->m_hlName, PERMISSION_TYPE_KEYBOARD);
1059+
if (PERM == PERMISSION_RULE_ALLOW_MODE_PENDING) {
1060+
const auto PROMISE = g_pDynamicPermissionManager->promiseFor(-1, pKeyboard->m_hlName, PERMISSION_TYPE_KEYBOARD);
1061+
if (!PROMISE)
1062+
Debug::log(ERR, "BUG THIS: No promise for client permission for keyboard");
1063+
else {
1064+
PROMISE->then([k = WP<IKeyboard>{pKeyboard}](SP<CPromiseResult<eDynamicPermissionAllowMode>> r) {
1065+
if (r->hasError()) {
1066+
Debug::log(ERR, "BUG THIS: No permission returned for keyboard");
1067+
return;
1068+
}
1069+
1070+
if (!k)
1071+
return;
1072+
1073+
k->m_allowed = r->result() == PERMISSION_RULE_ALLOW_MODE_ALLOW;
1074+
});
1075+
}
1076+
} else
1077+
pKeyboard->m_allowed = PERM == PERMISSION_RULE_ALLOW_MODE_ALLOW;
1078+
10571079
try {
10581080
if (NUMLOCKON == pKeyboard->m_numlockOn && REPEATDELAY == pKeyboard->m_repeatDelay && REPEATRATE == pKeyboard->m_repeatRate && RULES != "" &&
10591081
RULES == pKeyboard->m_currentRules.rules && MODEL == pKeyboard->m_currentRules.model && LAYOUT == pKeyboard->m_currentRules.layout &&
@@ -1382,7 +1404,7 @@ void CInputManager::updateKeyboardsLeds(SP<IKeyboard> pKeyboard) {
13821404
}
13831405

13841406
void CInputManager::onKeyboardKey(std::any event, SP<IKeyboard> pKeyboard) {
1385-
if (!pKeyboard->m_enabled)
1407+
if (!pKeyboard->m_enabled || !pKeyboard->m_allowed)
13861408
return;
13871409

13881410
const bool DISALLOWACTION = pKeyboard->isVirtual() && shouldIgnoreVirtualKeyboard(pKeyboard);

src/managers/permissions/DynamicPermissionManager.cpp

Lines changed: 19 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -52,16 +52,18 @@ static const char* permissionToString(eDynamicPermissionType type) {
5252
case PERMISSION_TYPE_UNKNOWN: return "PERMISSION_TYPE_UNKNOWN";
5353
case PERMISSION_TYPE_SCREENCOPY: return "PERMISSION_TYPE_SCREENCOPY";
5454
case PERMISSION_TYPE_PLUGIN: return "PERMISSION_TYPE_PLUGIN";
55+
case PERMISSION_TYPE_KEYBOARD: return "PERMISSION_TYPE_KEYBOARD";
5556
}
5657

5758
return "error";
5859
}
5960

6061
static const char* permissionToHumanString(eDynamicPermissionType type) {
6162
switch (type) {
62-
case PERMISSION_TYPE_UNKNOWN: return "requesting an unknown permission";
63-
case PERMISSION_TYPE_SCREENCOPY: return "trying to capture your screen";
64-
case PERMISSION_TYPE_PLUGIN: return "trying to load a plugin";
63+
case PERMISSION_TYPE_UNKNOWN: return "An application <b>{}</b> is requesting an unknown permission.";
64+
case PERMISSION_TYPE_SCREENCOPY: return "An application <b>{}</b> is trying to capture your screen.<br/><br/>Do you want to allow it to do so?";
65+
case PERMISSION_TYPE_PLUGIN: return "An application <b>{}</b> is trying to load a plugin: <b>{}</b>.<br/><br/>Do you want to load it?";
66+
case PERMISSION_TYPE_KEYBOARD: return "A new keyboard has been plugged in: {}.<br/><br/>Do you want to allow it to operate?";
6567
}
6668

6769
return "error";
@@ -184,7 +186,7 @@ eDynamicPermissionAllowMode CDynamicPermissionManager::clientPermissionMode(wl_c
184186
return PERMISSION_RULE_ALLOW_MODE_PENDING;
185187
}
186188

187-
// if we are here, we need to ask.
189+
// if we are here, we need to ask, that's the fallback for all these (keyboards wont come here)
188190
askForPermission(client, LOOKUP.value_or(""), permission);
189191

190192
return PERMISSION_RULE_ALLOW_MODE_PENDING;
@@ -232,6 +234,10 @@ eDynamicPermissionAllowMode CDynamicPermissionManager::clientPermissionModeWithS
232234
} else if ((*it)->m_allowMode == PERMISSION_RULE_ALLOW_MODE_PENDING) {
233235
Debug::log(TRACE, "CDynamicPermissionManager::clientHasPermission: permission pending by config rule");
234236
return PERMISSION_RULE_ALLOW_MODE_PENDING;
237+
} else if ((*it)->m_allowMode == PERMISSION_RULE_ALLOW_MODE_ASK) {
238+
Debug::log(TRACE, "CDynamicPermissionManager::clientHasPermission: permission ask by config rule");
239+
askForPermission(nullptr, str, permission, pid);
240+
return PERMISSION_RULE_ALLOW_MODE_PENDING;
235241
} else
236242
Debug::log(TRACE, "CDynamicPermissionManager::clientHasPermission: permission ask by config rule");
237243
}
@@ -247,6 +253,10 @@ eDynamicPermissionAllowMode CDynamicPermissionManager::clientPermissionModeWithS
247253
return PERMISSION_RULE_ALLOW_MODE_PENDING;
248254
}
249255

256+
// keyboards are allow default
257+
if (permission == PERMISSION_TYPE_KEYBOARD)
258+
return PERMISSION_RULE_ALLOW_MODE_ALLOW;
259+
250260
// if we are here, we need to ask.
251261
askForPermission(nullptr, str, permission, pid);
252262

@@ -263,22 +273,20 @@ void CDynamicPermissionManager::askForPermission(wl_client* client, const std::s
263273

264274
std::string description = "";
265275
if (binaryPath.empty())
266-
description = std::format("An unknown application (wayland client ID 0x{:x}) is {}.", (uintptr_t)client, permissionToHumanString(type));
276+
description = std::format(std::runtime_format(permissionToHumanString(type)), std::format("unknown application (wayland client ID 0x{:x})", (uintptr_t)client));
267277
else if (client) {
268278
std::string binaryName = binaryPath.contains("/") ? binaryPath.substr(binaryPath.find_last_of('/') + 1) : binaryPath;
269-
description = std::format("An application <b>{}</b> ({}) is {}.", binaryName, binaryPath, permissionToHumanString(type));
279+
description = std::format(std::runtime_format(permissionToHumanString(type)), std::format("{}</b> ({})", binaryName, binaryPath));
270280
} else if (pid >= 0) {
271281
if (type == PERMISSION_TYPE_PLUGIN) {
272282
const auto LOOKUP = binaryNameForPid(pid);
273-
description = std::format("An application <b>{}</b> is {}:<br/><b>{}</b>", LOOKUP.value_or("Unknown"), permissionToHumanString(type), binaryPath);
283+
description = std::format(std::runtime_format(permissionToHumanString(type)), LOOKUP.value_or("Unknown"), binaryPath);
274284
} else {
275285
const auto LOOKUP = binaryNameForPid(pid);
276-
description = std::format("An application <b>{}</b> ({}) is {}.", LOOKUP.value_or("Unknown"), binaryPath, permissionToHumanString(type));
286+
description = std::format(std::runtime_format(permissionToHumanString(type)), LOOKUP.value_or("Unknown"), binaryPath);
277287
}
278288
} else
279-
description = std::format("An application is {}:<br/><b>{}</b>", permissionToHumanString(type), binaryPath);
280-
281-
description += "<br/><br/>Do you want to allow this?";
289+
description = std::format(std::runtime_format(permissionToHumanString(type)), binaryPath);
282290

283291
std::vector<std::string> options;
284292

src/managers/permissions/DynamicPermissionManager.hpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ enum eDynamicPermissionType : uint8_t {
1717
PERMISSION_TYPE_UNKNOWN = 0,
1818
PERMISSION_TYPE_SCREENCOPY,
1919
PERMISSION_TYPE_PLUGIN,
20+
PERMISSION_TYPE_KEYBOARD,
2021
};
2122

2223
enum eDynamicPermissionRuleSource : uint8_t {

0 commit comments

Comments
 (0)