Retry mmap if it fails
Sometimes, mmap returns ENOMEM even though there is enough memory, in
that case, retried mmap mostly succeeds.
So as a workaround, let MemMapArena::Allocate retry at most 3 time.
(to resolve flaky build failure)
Bug: 278665389
Test: run dex2oat repeatedly
Change-Id: Icbde6a06fe8d1b189486ea2ab10003425248df52
diff --git a/runtime/base/mem_map_arena_pool.cc b/runtime/base/mem_map_arena_pool.cc
index ae7db45..fc1a61e 100644
--- a/runtime/base/mem_map_arena_pool.cc
+++ b/runtime/base/mem_map_arena_pool.cc
@@ -57,13 +57,24 @@
// and we want to be able to use all memory that we actually allocate.
size = RoundUp(size, kPageSize);
std::string error_msg;
- MemMap map = MemMap::MapAnonymous(name,
- size,
- PROT_READ | PROT_WRITE,
- low_4gb,
- &error_msg);
- CHECK(map.IsValid()) << error_msg;
- return map;
+ // TODO(b/278665389): remove this retry logic if the root cause is found.
+ constexpr int MAX_RETRY_CNT = 3;
+ int retry_cnt = 0;
+ while (true) {
+ MemMap map = MemMap::MapAnonymous(name, size, PROT_READ | PROT_WRITE, low_4gb, &error_msg);
+ if (map.IsValid()) {
+ if (retry_cnt > 0) {
+ LOG(WARNING) << "Succeed with retry(cnt=" << retry_cnt << ")";
+ }
+ return map;
+ } else {
+ if (retry_cnt == MAX_RETRY_CNT) {
+ CHECK(map.IsValid()) << error_msg << "(retried " << retry_cnt << " times)";
+ }
+ }
+ retry_cnt++;
+ LOG(ERROR) << error_msg << " but retry(cnt=" << retry_cnt << ")";
+ }
}
MemMapArena::~MemMapArena() {