Home | History | Annotate | Download | only in alloc
      1 /*
      2  * Copyright (C) 2008 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 #ifndef DALVIK_HEAP_BITMAPINLINES_H_
     18 #define DALVIK_HEAP_BITMAPINLINES_H_
     19 
     20 static unsigned long dvmHeapBitmapSetAndReturnObjectBit(HeapBitmap *hb, const void *obj) __attribute__((used));
     21 static void dvmHeapBitmapSetObjectBit(HeapBitmap *hb, const void *obj) __attribute__((used));
     22 static void dvmHeapBitmapClearObjectBit(HeapBitmap *hb, const void *obj) __attribute__((used));
     23 
     24 /*
     25  * Internal function; do not call directly.
     26  */
     27 static unsigned long _heapBitmapModifyObjectBit(HeapBitmap *hb, const void *obj,
     28                                                 bool setBit, bool returnOld)
     29 {
     30     const uintptr_t offset = (uintptr_t)obj - hb->base;
     31     const size_t index = HB_OFFSET_TO_INDEX(offset);
     32     const unsigned long mask = HB_OFFSET_TO_MASK(offset);
     33 
     34     assert(hb->bits != NULL);
     35     assert((uintptr_t)obj >= hb->base);
     36     assert(index < hb->bitsLen / sizeof(*hb->bits));
     37     if (setBit) {
     38         if ((uintptr_t)obj > hb->max) {
     39             hb->max = (uintptr_t)obj;
     40         }
     41         if (returnOld) {
     42             unsigned long *p = hb->bits + index;
     43             const unsigned long word = *p;
     44             *p |= mask;
     45             return word & mask;
     46         } else {
     47             hb->bits[index] |= mask;
     48         }
     49     } else {
     50         hb->bits[index] &= ~mask;
     51     }
     52     return false;
     53 }
     54 
     55 /*
     56  * Sets the bit corresponding to <obj>, and returns the previous value
     57  * of that bit (as zero or non-zero). Does no range checking to see if
     58  * <obj> is outside of the coverage of the bitmap.
     59  *
     60  * NOTE: casting this value to a bool is dangerous, because higher
     61  * set bits will be lost.
     62  */
     63 static unsigned long dvmHeapBitmapSetAndReturnObjectBit(HeapBitmap *hb,
     64                                                         const void *obj)
     65 {
     66     return _heapBitmapModifyObjectBit(hb, obj, true, true);
     67 }
     68 
     69 /*
     70  * Sets the bit corresponding to <obj>, and widens the range of seen
     71  * pointers if necessary.  Does no range checking.
     72  */
     73 static void dvmHeapBitmapSetObjectBit(HeapBitmap *hb, const void *obj)
     74 {
     75     _heapBitmapModifyObjectBit(hb, obj, true, false);
     76 }
     77 
     78 /*
     79  * Clears the bit corresponding to <obj>.  Does no range checking.
     80  */
     81 static void dvmHeapBitmapClearObjectBit(HeapBitmap *hb, const void *obj)
     82 {
     83     _heapBitmapModifyObjectBit(hb, obj, false, false);
     84 }
     85 
     86 /*
     87  * Returns the current value of the bit corresponding to <obj>,
     88  * as zero or non-zero.  Does no range checking.
     89  *
     90  * NOTE: casting this value to a bool is dangerous, because higher
     91  * set bits will be lost.
     92  */
     93 static unsigned long dvmHeapBitmapIsObjectBitSet(const HeapBitmap *hb,
     94                                                  const void *obj)
     95 {
     96     assert(dvmHeapBitmapCoversAddress(hb, obj));
     97     assert(hb->bits != NULL);
     98     assert((uintptr_t)obj >= hb->base);
     99     if ((uintptr_t)obj <= hb->max) {
    100         const uintptr_t offset = (uintptr_t)obj - hb->base;
    101         return hb->bits[HB_OFFSET_TO_INDEX(offset)] & HB_OFFSET_TO_MASK(offset);
    102     } else {
    103         return 0;
    104     }
    105 }
    106 
    107 #endif  // DALVIK_HEAP_BITMAPINLINES_H_
    108