The Xiaomi Mi Notebook Pro keyboard has a "star" key that
generates AT keyboard scancode 0x72 but is not mapped in
the default hwdb.
Map it to KEY_MACRO so it appears as a usable input key.
Verified using evtest.
Signed-off-by: Arjun <arjunchoozhi1234@gmail.com>
Add a simple fuzzer that verifies our machinery for parsing user records
from JSON works as intended.
The initial corpus was created with the help of Claude, so we have a
bunch of valid user records with as much fields as possible for the
initial corpus.
The fido2_hmac_salt/fido2_hmac_credential/recovery_key fields kept
leaking memory as the array itself wasn't deallocated after deallocating
each of its elements data:
$ build-san/userdbctl -F fuzz-corpus-userdb/auth-fido2.json
...
=================================================================
==1292840==ERROR: LeakSanitizer: detected memory leaks
Direct leak of 112 byte(s) in 1 object(s) allocated from:
#0 0x7f56f00e5e4b in realloc.part.0 (/lib64/libasan.so.8+0xe5e4b) (BuildId: 25975f766867e9e604dc5a71a8befeaed3301942)
#1 0x7f56ed869e42 in greedy_realloc ../src/basic/alloc-util.c:65
#2 0x7f56ed7ff5e9 in dispatch_fido2_hmac_salt ../src/shared/user-record.c:836
#3 0x7f56edd73cbc in sd_json_dispatch_full ../src/libsystemd/sd-json/sd-json.c:5204
#4 0x7f56edd745fc in sd_json_dispatch ../src/libsystemd/sd-json/sd-json.c:5276
#5 0x7f56ed80100b in dispatch_privileged ../src/shared/user-record.c:998
#6 0x7f56edd73cbc in sd_json_dispatch_full ../src/libsystemd/sd-json/sd-json.c:5204
#7 0x7f56edd745fc in sd_json_dispatch ../src/libsystemd/sd-json/sd-json.c:5276
#8 0x7f56ed80622c in user_record_load ../src/shared/user-record.c:1697
#9 0x000000408c15 in display_user ../src/userdb/userdbctl.c:447
#10 0x7f56ed83cc9a in dispatch_verb ../src/shared/verbs.c:137
#11 0x00000041df2b in run ../src/userdb/userdbctl.c:1908
#12 0x00000041dfbe in main ../src/userdb/userdbctl.c:1911
#13 0x7f56ec8105b4 in __libc_start_call_main (/lib64/libc.so.6+0x35b4) (BuildId: 2b5beec0fd24fe9c9f43eddfdd5facf0b8a1b805)
#14 0x7f56ec810667 in __libc_start_main@@GLIBC_2.34 (/lib64/libc.so.6+0x3667) (BuildId: 2b5beec0fd24fe9c9f43eddfdd5facf0b8a1b805)
#15 0x000000404a44 in _start (/home/fsumsal/repos/@systemd/systemd/build-san/userdbctl+0x404a44) (BuildId: 19e8b7e7b7038d2cea20bc18a55bea2a9e4406d5)
Direct leak of 64 byte(s) in 1 object(s) allocated from:
#0 0x7f56f00e5e4b in realloc.part.0 (/lib64/libasan.so.8+0xe5e4b) (BuildId: 25975f766867e9e604dc5a71a8befeaed3301942)
#1 0x7f56ed869e42 in greedy_realloc ../src/basic/alloc-util.c:65
#2 0x7f56ed7fe779 in dispatch_fido2_hmac_credential_array ../src/shared/user-record.c:775
#3 0x7f56edd73cbc in sd_json_dispatch_full ../src/libsystemd/sd-json/sd-json.c:5204
#4 0x7f56edd745fc in sd_json_dispatch ../src/libsystemd/sd-json/sd-json.c:5276
#5 0x7f56ed80622c in user_record_load ../src/shared/user-record.c:1697
#6 0x000000408c15 in display_user ../src/userdb/userdbctl.c:447
#7 0x7f56ed83cc9a in dispatch_verb ../src/shared/verbs.c:137
#8 0x00000041df2b in run ../src/userdb/userdbctl.c:1908
#9 0x00000041dfbe in main ../src/userdb/userdbctl.c:1911
#10 0x7f56ec8105b4 in __libc_start_call_main (/lib64/libc.so.6+0x35b4) (BuildId: 2b5beec0fd24fe9c9f43eddfdd5facf0b8a1b805)
#11 0x7f56ec810667 in __libc_start_main@@GLIBC_2.34 (/lib64/libc.so.6+0x3667) (BuildId: 2b5beec0fd24fe9c9f43eddfdd5facf0b8a1b805)
#12 0x000000404a44 in _start (/home/fsumsal/repos/@systemd/systemd/build-san/userdbctl+0x404a44) (BuildId: 19e8b7e7b7038d2cea20bc18a55bea2a9e4406d5)
SUMMARY: AddressSanitizer: 176 byte(s) leaked in 2 allocation(s).
1 and 10000 are valid cgroup weight values, but the condition was
incorrectly excluding them:
$ echo '{"userName":"crashhostarray","cpuWeight":1}' | userdbctl -F -
<stdin>:1:42: JSON field 'cpuWeight' is not in valid range 1…10000.
$ echo '{"userName":"crashhostarray","cpuWeight":10000}' | userdbctl -F -
<stdin>:1:42: JSON field 'cpuWeight' is not in valid range 1…10000.
We don't always return d->formatted, even if it is available. And
depending on the cell type, we'd either overwrite it directly or free
first. Let's always free it upfront and then set unconditionally.
(In this case, we don't need to spend effort on preserving the
existing value. It's just a cache.) Setting the variable directly
allows many temporary variables to be eliminated.
Also use asprintf_safe() to simplify the allocation of the buffer.
This is probably a tiny bit slower than the direct allocation, but
table formatting shouldn't be a hot path.
asprintf is nice to use, but the _documented_ error return convention is
unclear:
> If memory allocation wasn't possible, or some other error occurs,
> these functions will return -1, and the contents of strp are undefined.
What exactly "undefined" means is up for debate: if it was really
undefined, the caller wouldn't be able to meaningfully clean up, because
they wouldn't know if strp is a valid pointer. So far we interpreted
"undefined" — in some parts of the code base — as "either NULL or a
valid pointer that needs to be freed", and — in other parts of the
codebase — as "always NULL". I checked glibc and musl, and they both
uncoditionally set the output pointer to NULL on failure.
There is also no information _why_ asprintf failed. It could be an
allocation error or format string error. But we just don't have this
information.
Let's add a wrapper that either returns a good string or a NULL pointer.
Since there's just one failure result, we don't need a separate return
value and an output argument and can simplify callers.
It's actually only used in one place in libsystemd and moving it even makes
libsystemd smaller (in a non-optimized build):
$ ls -l build/libsystemd.so.0.43.0*
-rwxr-xr-x 1 zbyszek zbyszek 5763336 Mar 3 09:54 build/libsystemd.so.0.43.0-old
-rwxr-xr-x 1 zbyszek zbyszek 5763216 Mar 3 09:54 build/libsystemd.so.0.43.0
Also, move the definitions in the .h file so that similar functions are
grouped together and then move the definitions around in the .c file so
that they are in the same order as in the header.
Let's make sure the parameters/error pointers into the message remain
valid as long as the reply callback is running, even if the reply
otherwise resets the pending message.
Let's only keep instructions for stuff that we've seen the AI
mess up in practice rather than having a bunch of AI generated
text that it can figure out for itself these days (given it was
trained on systemd's source code in the first place).
Also add a rule to use git worktrees and check out PRs locally when
reviewing them, since I've seen it mess that up in practice.
This will allow maintainers to mention claude in comments on issues and
prs to do stuff like review something or try to reproduce a bug or other
stuff. Let's give it a try and see whether we like it or not.
This seems to be what all the tools are standardizing on, except
claude (https://github.com/anthropics/claude-code/issues/6235) so
add a symlink from CLAUDE.md to AGENTS.md for now until they support
it as well.
I also had claude extend the instructions a bit.
Co-developed-by: Claude <claude@anthropic.com>
These two completers are written in a stacked _arguments style, and some
generic options are valid before or after the verb. If the toplevel
_arguments is permitted to match options after the verb, it will halt
completion prematurely, so stop toplevel matching after the verb.
This corrects the following error:
$ userdbctl --output=class user <TAB> # completes users
$ userdbctl user --output=class <TAB> # completes nothing
This will allow maintainers to mention claude in comments on issues
and prs to do stuff like review something or try to reproduce a bug
or other stuff. Let's give it a try and see whether we like it or
not.
Suppress warnings like the following from clang tidy:
```
../src/boot/addon.c:11:19: error: function 'efi_main' can be made static to enforce internal linkage [misc-use-internal-linkage,-warnings-as-errors]
11 | EFIAPI EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *system_table);
| ^
```
Some warnings are suppressed simply by setting comments to ignore the warning,
some are by making global variables static, or include a suitable header.