標籤:
好記性不如爛筆頭,今天要學習的是Android中Abi目錄下的代碼。下面是基本的學習的筆記的匯總。
首先是include中的標頭檔的說明。
在cxxabi的標頭檔中主要需要掌握下面的幾個點:
1、這個標頭檔中包含的主要的功能就是基於C++ 2.9.5中的驅動的類型的資訊。
2、驅動的類型這裡面主要定義了這麼幾類:
2、1 __fundamental_type_info 基本驅動類型的資訊
2、2 __array_type_info 數組驅動類型的資訊
2、3 __function_type_info函數驅動類型的資訊
2、4 __enum_type_info枚舉驅動類型的資訊
2、5 __class_type_info沒有父類的類的驅動類型的資訊
2、7 __si_class_type_info是__class_type_info的子類,其中包含了一個單例、公有非虛的,位移量為0的指向的是__class_type_info的類型的指標。
const __class_type_info *__base_type;
在new的標頭檔中主要需要掌握下面的幾個點:
1、主要是一些操作符的重載
2、被重載的操作符主要有:new 、new[ ]、delete、delete[ ]
2、同時每一個操作符的重載基本上都要聲明拋出異常
在typeinfo的標頭檔中需要掌握下面的幾個點:
1、主要是定義了type_info的一些操作(主要還是一些操作符的重載)(基於C++ 2.9.3的片段)
接下來是src中的源碼檔案的說明。
1、主要是一些驅動類型的資訊的實現,其中絕大多數的實現是一些空實現,僅僅包括一個解構函式。
2、其中數組驅動類型、類驅動類型、枚舉驅動類型、函數驅動類型、基本資料驅動類型、指標指向成員變數驅動類型、指標驅動類型等都是處了有一個解構函式的空的定義,其餘什麼都沒有的源碼。
3、對於delete運算子多載的實現是下面這樣的:
voidoperator delete(void* ptr) throw(){ if (ptr) free(ptr);}
調用free方法釋放指向的儲存空間。
4、對於new運算子的重載方法如下:
void*operator new(std::size_t size) throw (/*std::bad_alloc*/){ void* ptr = malloc(size);#if 0 if (ptr == NULL) throw std::bad_alloc();#endif return ptr;}
調用malloc函數分配需要的儲存空間,如果分配失敗,拋出異常。
5、在dynamic_cast的源碼中,需要注意下面的幾個點:
5、1 通過位移量調整一個指標的指向
5、2 返回一個通過指標指向的多態的對象的指標的虛擬表
5、3 返回在一個虛擬表中的一個指標指向的類驅動類型的資訊
5、4 返回在一個虛擬表中,相對於一個對象的位移量。
5、5 如何去迭代一個對象的類型的樹
const void * walk_object(const void *object, const abi::__class_type_info *type, const void *match_object, const abi::__class_type_info *match_type) {//如果當前的對象的類型與當前的等待迭代的指標是相同的 if (*type == *match_type) return (match_object == NULL || object == match_object) ? object : NULL; switch(type->code()) { case abi::__class_type_info::CLASS_TYPE_INFO_CODE: // This isn't not the class you're looking for. return NULL; case abi::__class_type_info::SI_CLASS_TYPE_INFO_CODE: // derived type has a single public base at offset 0. { const abi::__si_class_type_info* ti = static_cast<const abi::__si_class_type_info*>(type); return walk_object(object, ti->__base_type, match_object, match_type); } case abi::__class_type_info::VMI_CLASS_TYPE_INFO_CODE: { const void* vtable = get_vtable(object); const abi::__vmi_class_type_info* ti = static_cast<const abi::__vmi_class_type_info*>(type); // Look at all direct bases. const void* result = NULL; for (unsigned i = 0; i < ti->__base_count; ++i) { if (!ti->__base_info[i].is_public()) continue; const void *subobject = get_subobject(object, vtable, &ti->__base_info[i]); const void* walk_subobject_result = walk_object(subobject, ti->__base_info[i].__base_type, match_object, match_type); if (walk_subobject_result == ambiguous_object) return ambiguous_object; else if (walk_subobject_result != NULL) { if (result == NULL) { result = walk_subobject_result; } else if (result != walk_subobject_result) return ambiguous_object; } } return result; } default: assert(0); } return NULL; }
Android核心源碼Abi目錄學習筆記