在openmv對影像提取roi,這里用到了提取像素位的函式,
在collections.h中定義了相關的結構體和功能函式宣告,
// bitmap //
typedef struct bitmap
{
size_t size;
char *data;
}
__attribute__((aligned(8)))bitmap_t;
void bitmap_alloc(bitmap_t *ptr, size_t size);
void bitmap_free(bitmap_t *ptr);
void bitmap_clear(bitmap_t *ptr);
void bitmap_bit_set(bitmap_t *ptr, size_t index);
bool bitmap_bit_get(bitmap_t *ptr, size_t index);
- void bitmap_alloc(bitmap_t *ptr, size_t size);
為bitmap申請記憶體單元,如何通過bit數來申請記憶體單元?
#define CHAR_BITS (sizeof(char) * 8) //計算一個位元組所需要的的bit數
#define CHAR_MASK (CHAR_BITS - 1) //
#define CHAR_SHIFT IM_LOG2(CHAR_MASK) //求解log2 計算偏移量,
// bitmap //
void bitmap_alloc(bitmap_t *ptr, size_t size)
{
ptr->size = size;
ptr->data = (char *) fb_alloc0(((size + CHAR_MASK) >> CHAR_SHIFT) * sizeof(char));
}
通過上面代碼,可以看到給定的單位長度:size,通過((size + CHAR_MASK) >> CHAR_SHIFT) * sizeof(char) ,其中的size+CHAR_MASK類似于四舍五入的思想,將不夠一個char的拼接成一個char,后面執行>>CHAR_SHIFT是將bit數轉化為對用的char數,最后*sizeof(char),求出最終記憶體單元大小,呼叫的fb_alloc0函式是具有一定記憶體管理的(基于malloc),這個在這里就不細說,可以在后面的隨筆記錄里面書寫,
2、void bitmap_free(bitmap_t *ptr); 釋放已經申請的記憶體單元
void bitmap_free(bitmap_t *ptr)
{
if (ptr->data) {
fb_free();
}
}
很有趣的是:這里給了引數bitmap_t *ptr,但是在函式中只用到了檢測是否含有資料,ptr->data,之后便呼叫fb_free();沒有引數,沒有引數怎么知道釋放哪些記憶體單元?這就很有趣了,
進一步查看一下fb_free()
void fb_free()
{
uint8_t i;
for(i=0; i<FB_MAX_ALLOC_TIMES; ++i)
{
if( m_fb_alloc_addr[i].valid && m_fb_alloc_addr[i].count==m_count_max_now)
{
free(m_fb_alloc_addr[i].p);
m_fb_alloc_addr[i].p = NULL;
m_fb_alloc_addr[i].valid = false;
--m_count_max_now;
break;
}
}
}
通過函式可以知道,這里的記憶體塊是具有一定管理能力的,通過 m_fb_alloc_addr[i].valid && m_fb_alloc_addr[i].count==m_count_max_now 這個條件來匹配當前需要釋放的記憶體單元是哪個,這種方式應該是用在一些臨時變數里面不適用于全域記憶體管理,在一些臨時變數申請之后,函式的最后在釋放其記憶體,防止堆疊溢位,關于這一塊的管理是在fb_alloc.c中說明,可以在以后的隨筆中書寫,
3、void bitmap_clear(bitmap_t *ptr); 清楚記憶體單元,其實就是講資料bit全部變為0
void bitmap_clear(bitmap_t *ptr)
{
memset(ptr->data, 0, ((ptr->size + CHAR_MASK) >> CHAR_SHIFT) * sizeof(char));
}
這里就沒有什么好說的,利用memset設定所欲申請記憶體單元為0.
4、void bitmap_bit_set(bitmap_t *ptr, size_t index) 置位某一位bit,
void bitmap_bit_set(bitmap_t *ptr, size_t index)
{
ptr->data[index >> CHAR_SHIFT] |= 1 << (index & CHAR_MASK);
}
這里面有幾個簡單計算說一下:第一個如果通過給的bit位置算出char的位置,
這里使用的是 index>>CHAR_SHIFT來完成的,
第二個問題是確定了那個char,那么在這個char里面的那個位,通過index&CHAR_MASK來確定.,
以上就是自己對于openmv原始碼中的bitmap的簡單理解,記錄一下,方便自己以后加深理解,
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/279324.html
標籤:其他
上一篇:單片機 -- -- 數碼管
