2017-01-11 10:06:31 +08:00
|
|
|
#ifndef JEMALLOC_INTERNAL_BITMAP_INLINES_H
|
|
|
|
#define JEMALLOC_INTERNAL_BITMAP_INLINES_H
|
|
|
|
|
|
|
|
#ifndef JEMALLOC_ENABLE_INLINE
|
2017-03-24 08:59:47 +08:00
|
|
|
bool bitmap_full(bitmap_t *bitmap, const bitmap_info_t *binfo);
|
|
|
|
bool bitmap_get(bitmap_t *bitmap, const bitmap_info_t *binfo, size_t bit);
|
|
|
|
void bitmap_set(bitmap_t *bitmap, const bitmap_info_t *binfo, size_t bit);
|
|
|
|
size_t bitmap_ffu(const bitmap_t *bitmap, const bitmap_info_t *binfo,
|
|
|
|
size_t min_bit);
|
|
|
|
size_t bitmap_sfu(bitmap_t *bitmap, const bitmap_info_t *binfo);
|
|
|
|
void bitmap_unset(bitmap_t *bitmap, const bitmap_info_t *binfo, size_t bit);
|
2017-01-11 10:06:31 +08:00
|
|
|
#endif
|
|
|
|
|
|
|
|
#if (defined(JEMALLOC_ENABLE_INLINE) || defined(JEMALLOC_BITMAP_C_))
|
|
|
|
JEMALLOC_INLINE bool
|
2017-01-16 08:56:30 +08:00
|
|
|
bitmap_full(bitmap_t *bitmap, const bitmap_info_t *binfo) {
|
2017-01-11 10:06:31 +08:00
|
|
|
size_t i;
|
|
|
|
|
|
|
|
for (i = 0; i < binfo->ngroups; i++) {
|
2017-01-16 08:56:30 +08:00
|
|
|
if (bitmap[i] != 0) {
|
2017-01-20 10:15:45 +08:00
|
|
|
return false;
|
2017-01-16 08:56:30 +08:00
|
|
|
}
|
2017-01-11 10:06:31 +08:00
|
|
|
}
|
2017-01-20 10:15:45 +08:00
|
|
|
return true;
|
2017-01-11 10:06:31 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
JEMALLOC_INLINE bool
|
2017-01-16 08:56:30 +08:00
|
|
|
bitmap_get(bitmap_t *bitmap, const bitmap_info_t *binfo, size_t bit) {
|
2017-01-11 10:06:31 +08:00
|
|
|
size_t goff;
|
|
|
|
bitmap_t g;
|
|
|
|
|
|
|
|
assert(bit < binfo->nbits);
|
|
|
|
goff = bit >> LG_BITMAP_GROUP_NBITS;
|
|
|
|
g = bitmap[goff];
|
2017-01-20 10:15:45 +08:00
|
|
|
return !(g & (ZU(1) << (bit & BITMAP_GROUP_NBITS_MASK)));
|
2017-01-11 10:06:31 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
JEMALLOC_INLINE void
|
2017-01-16 08:56:30 +08:00
|
|
|
bitmap_set(bitmap_t *bitmap, const bitmap_info_t *binfo, size_t bit) {
|
2017-01-11 10:06:31 +08:00
|
|
|
size_t goff;
|
|
|
|
bitmap_t *gp;
|
|
|
|
bitmap_t g;
|
|
|
|
|
|
|
|
assert(bit < binfo->nbits);
|
|
|
|
assert(!bitmap_get(bitmap, binfo, bit));
|
|
|
|
goff = bit >> LG_BITMAP_GROUP_NBITS;
|
|
|
|
gp = &bitmap[goff];
|
|
|
|
g = *gp;
|
|
|
|
assert(g & (ZU(1) << (bit & BITMAP_GROUP_NBITS_MASK)));
|
|
|
|
g ^= ZU(1) << (bit & BITMAP_GROUP_NBITS_MASK);
|
|
|
|
*gp = g;
|
|
|
|
assert(bitmap_get(bitmap, binfo, bit));
|
|
|
|
}
|
|
|
|
|
2017-03-24 08:59:47 +08:00
|
|
|
/* ffu: find first unset >= bit. */
|
|
|
|
JEMALLOC_INLINE size_t
|
|
|
|
bitmap_ffu(const bitmap_t *bitmap, const bitmap_info_t *binfo, size_t min_bit) {
|
|
|
|
assert(min_bit < binfo->nbits);
|
|
|
|
|
|
|
|
size_t i = min_bit >> LG_BITMAP_GROUP_NBITS;
|
|
|
|
bitmap_t g = bitmap[i] & ~((1LU << (min_bit & BITMAP_GROUP_NBITS_MASK))
|
|
|
|
- 1);
|
|
|
|
size_t bit;
|
|
|
|
do {
|
|
|
|
bit = ffs_lu(g);
|
|
|
|
if (bit != 0) {
|
|
|
|
return (i << LG_BITMAP_GROUP_NBITS) + (bit - 1);
|
|
|
|
}
|
|
|
|
i++;
|
|
|
|
g = bitmap[i];
|
|
|
|
} while (i < binfo->ngroups);
|
|
|
|
return binfo->nbits;
|
|
|
|
}
|
|
|
|
|
2017-01-11 10:06:31 +08:00
|
|
|
/* sfu: set first unset. */
|
|
|
|
JEMALLOC_INLINE size_t
|
2017-01-16 08:56:30 +08:00
|
|
|
bitmap_sfu(bitmap_t *bitmap, const bitmap_info_t *binfo) {
|
2017-01-11 10:06:31 +08:00
|
|
|
size_t bit;
|
|
|
|
bitmap_t g;
|
|
|
|
unsigned i;
|
|
|
|
|
|
|
|
assert(!bitmap_full(bitmap, binfo));
|
|
|
|
|
|
|
|
i = 0;
|
|
|
|
g = bitmap[0];
|
|
|
|
while ((bit = ffs_lu(g)) == 0) {
|
|
|
|
i++;
|
|
|
|
g = bitmap[i];
|
|
|
|
}
|
|
|
|
bit = (i << LG_BITMAP_GROUP_NBITS) + (bit - 1);
|
|
|
|
bitmap_set(bitmap, binfo, bit);
|
2017-01-20 10:15:45 +08:00
|
|
|
return bit;
|
2017-01-11 10:06:31 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
JEMALLOC_INLINE void
|
2017-01-16 08:56:30 +08:00
|
|
|
bitmap_unset(bitmap_t *bitmap, const bitmap_info_t *binfo, size_t bit) {
|
2017-01-11 10:06:31 +08:00
|
|
|
size_t goff;
|
|
|
|
bitmap_t *gp;
|
|
|
|
bitmap_t g;
|
|
|
|
UNUSED bool propagate;
|
|
|
|
|
|
|
|
assert(bit < binfo->nbits);
|
|
|
|
assert(bitmap_get(bitmap, binfo, bit));
|
|
|
|
goff = bit >> LG_BITMAP_GROUP_NBITS;
|
|
|
|
gp = &bitmap[goff];
|
|
|
|
g = *gp;
|
|
|
|
propagate = (g == 0);
|
|
|
|
assert((g & (ZU(1) << (bit & BITMAP_GROUP_NBITS_MASK))) == 0);
|
|
|
|
g ^= ZU(1) << (bit & BITMAP_GROUP_NBITS_MASK);
|
|
|
|
*gp = g;
|
|
|
|
assert(!bitmap_get(bitmap, binfo, bit));
|
|
|
|
}
|
|
|
|
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#endif /* JEMALLOC_INTERNAL_BITMAP_INLINES_H */
|