map: fail if key is currently executing
If during execution of a mapping, that same mapping is replaced,
there is undefined behavior because we destroy a mapping that we are
still iterating over.
I have been using this mapping inside my kakrc to re-source the kakrc.
map global user s %{:source "%val{config}/kakrc"<ret>} -docstring 'source "%val{config}/kakrc"'
Now <space>s happens to not trigger undefined behavior because the
mapping stays the same.
However it triggers an assertion added by Commit e49c0fb04
(unmap:
fail if the mapping is currently executing, 2023-05-14), specifically
the destructor of ScopedSetBool that guards mapping execution.
Fix these by banning map of a key that is executing, just like we
did for unmap.
Alternative solution: we could allow mapping (and even unmapping)
keys at any time and keep them alive by moving them into a trash can,
like we do for clients and others.
This commit is contained in:
parent
661d1a0905
commit
42be0057a6
|
@ -13,6 +13,9 @@ namespace Kakoune
|
||||||
void KeymapManager::map_key(Key key, KeymapMode mode,
|
void KeymapManager::map_key(Key key, KeymapMode mode,
|
||||||
KeyList mapping, String docstring)
|
KeyList mapping, String docstring)
|
||||||
{
|
{
|
||||||
|
if (auto it = m_mapping.find(KeyAndMode{key, mode}); it != m_mapping.end())
|
||||||
|
if (it->value.is_executing)
|
||||||
|
throw runtime_error("cannot map key that is currently executing");
|
||||||
m_mapping[KeyAndMode{key, mode}] = {std::move(mapping), std::move(docstring)};
|
m_mapping[KeyAndMode{key, mode}] = {std::move(mapping), std::move(docstring)};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
3
test/regression/4896-remap-executing-mapping/cmd
Normal file
3
test/regression/4896-remap-executing-mapping/cmd
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
!printf $kak_opt_source_count<ret>l
|
||||||
|
<space>s
|
||||||
|
!printf $kak_opt_source_count<ret>
|
1
test/regression/4896-remap-executing-mapping/in
Normal file
1
test/regression/4896-remap-executing-mapping/in
Normal file
|
@ -0,0 +1 @@
|
||||||
|
|
1
test/regression/4896-remap-executing-mapping/out
Normal file
1
test/regression/4896-remap-executing-mapping/out
Normal file
|
@ -0,0 +1 @@
|
||||||
|
12
|
3
test/regression/4896-remap-executing-mapping/rc
Normal file
3
test/regression/4896-remap-executing-mapping/rc
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
try %{ map global user s %exp{:source %%{%val{source}}<ret>} -docstring "re-source my kakrc" }
|
||||||
|
declare-option int source_count
|
||||||
|
set-option -add global source_count 1
|
Loading…
Reference in New Issue
Block a user