aboutsummaryrefslogtreecommitdiffstats
path: root/erts/emulator/beam/erl_map.c
diff options
context:
space:
mode:
authorSverker Eriksson <[email protected]>2014-03-21 16:38:13 +0100
committerSverker Eriksson <[email protected]>2014-03-21 16:38:13 +0100
commit78b118bc5f503435b1d9216b3a3279e0c9fd9ecd (patch)
tree308b72d2a6306509f3d33d83d3e3ba3f96987a41 /erts/emulator/beam/erl_map.c
parenta74e66a68f3b4ed590f928b4fd4f0808c6287a32 (diff)
downloadotp-78b118bc5f503435b1d9216b3a3279e0c9fd9ecd.tar.gz
otp-78b118bc5f503435b1d9216b3a3279e0c9fd9ecd.tar.bz2
otp-78b118bc5f503435b1d9216b3a3279e0c9fd9ecd.zip
erts: Fix heap overflow in maps:remove/2 when key is not found
One key-value pair too many was copied.
Diffstat (limited to 'erts/emulator/beam/erl_map.c')
-rw-r--r--erts/emulator/beam/erl_map.c16
1 files changed, 9 insertions, 7 deletions
diff --git a/erts/emulator/beam/erl_map.c b/erts/emulator/beam/erl_map.c
index 2fff7f9390..fdd2d0c0f6 100644
--- a/erts/emulator/beam/erl_map.c
+++ b/erts/emulator/beam/erl_map.c
@@ -647,22 +647,24 @@ int erts_maps_remove(Process *p, Eterm key, Eterm map, Eterm *res) {
*mhp++ = tup;
if (is_immed(key)) {
- while(n--) {
+ while (1) {
if (*ks == key) {
goto found_key;
- } else {
+ } else if (--n) {
*mhp++ = *vs++;
*thp++ = *ks++;
- }
+ } else
+ break;
}
} else {
- while(n--) {
+ while(1) {
if (EQ(*ks, key)) {
goto found_key;
- } else {
+ } else if (--n) {
*mhp++ = *vs++;
*thp++ = *ks++;
- }
+ } else
+ break;
}
}
@@ -676,7 +678,7 @@ int erts_maps_remove(Process *p, Eterm key, Eterm map, Eterm *res) {
found_key:
/* Copy rest of keys and values */
- if (n) {
+ if (--n) {
sys_memcpy(mhp, vs+1, n*sizeof(Eterm));
sys_memcpy(thp, ks+1, n*sizeof(Eterm));
}