From: Sage Weil Date: Sat, 28 Oct 2017 20:37:03 +0000 (-0500) Subject: include/interval_set: tolerate maps that invalidate iterator on change X-Git-Tag: v12.2.5~17^2~9 X-Git-Url: http://git-server-git.apps.pok.os.sepia.ceph.com/?a=commitdiff_plain;h=4b5103d4282db537c75b58a797a1b66db6563d1d;p=ceph.git include/interval_set: tolerate maps that invalidate iterator on change These changes picked out of the diff between the original btree_interval_set.h and interval_set.h (sadly I had it rolled into the initial commit so it was tedious to identify these). Signed-off-by: Sage Weil (cherry picked from commit 87aed2026a8f689540a92eeeea6b4054b6c69acd) --- diff --git a/src/include/interval_set.h b/src/include/interval_set.h index 9092b3b3ceb1..fd48c2a2be7c 100644 --- a/src/include/interval_set.h +++ b/src/include/interval_set.h @@ -22,6 +22,14 @@ #include "encoding.h" +/* + * *** NOTE *** + * + * This class is written to work with a variety of map-like containers, + * *include* ones that invalidate iterators when they are modified (e.g., + * flat_map and btree_map). + */ + #ifndef MIN # define MIN(a,b) ((a)<=(b) ? (a):(b)) #endif @@ -461,30 +469,34 @@ class interval_set { typename Map::iterator n = p; n++; + if (pstart) + *pstart = p->first; if (n != m.end() && start+len == n->first) { // combine with next, too! p->second += n->second; + if (plen) + *plen = p->second; m.erase(n); - } - if (pstart) - *pstart = p->first; - if (plen) - *plen = p->second; + } else { + if (plen) + *plen = p->second; + } } else { if (start+len == p->first) { - m[start] = len + p->second; // append to front if (pstart) *pstart = start; if (plen) *plen = len + p->second; + T psecond = p->second; m.erase(p); + m[start] = len + psecond; // append to front } else { assert(p->first > start+len); - m[start] = len; // new interval if (pstart) *pstart = start; if (plen) *plen = len; + m[start] = len; // new interval } } }