C linux 深入學習 errorfunction的建立

2020-08-12 11:39:39

C語言的傳參形式:

  1. .在C中,無法確定傳遞函數的所有實參時,可以用省略號代替形參列表
    void hello(…);
    void world(list,…);

va_list: 指的是傳入的參數列表 原型是 typedef char *arg;
va_start: 是一個宏定義,利用指針推算出其他參數的地址

原理:
在記憶體中棧結構是 自上而下的,所以函數的參數寫入的順序是根據誰先寫在前面,因爲編譯器是自左向右編譯寫入的
例如 :int hello(int a,int b,int c) 實際在記憶體中的位置就是a在棧底,c在棧頂,a是低地址,c是高地址,這也符合棧的數據結構先進後出的特性,所以就可以以最近寫入的地址(函數的棧頂地址),推算出其他參數的地址,然後使用相關的參數
va_end : 可以理解成free函數,但是兩者的機理不太一樣,所以爲了好理解,就當他是free吧

總結:
linux 系統程式設計的時候,程式碼量一大 ,錯誤就不太好定位,所以 這種方式我們通常是用來寫log的,用來定位,硬體驅動程式或者裝置監控程式的錯誤。
(如果你是用的是vim的話可以通過Youcomplete看到這些函數和宣告的原型)

範例程式舉例:

#include<stdio.h>
#include<stdarg.h>

void testLog(char*format,...)
{
	char tmp[50];
	va_list argsList;
	va_start(argsList,format);
	vsnprintf(tmp,sizeof(tmp),format,argsList);
	va_end(argsList);
	printf("%s\n",tmp);

}

int main(void)
{
	testLog("%d%d%d%d%d",1,2,3,4,5);
	return 0;
}

常見到的緩衝區:
緩衝區溢位(buffer overflow),是針對程式設計缺陷,向程式輸入緩衝區寫入使之溢位的內容(通常是超過緩衝區能儲存的最大數據量的數據),從而破壞程式執行、趁著中斷之際並獲取程式乃至系統的控制權。
緩衝區:輸入輸出數據的臨時儲存
fflush()可以清空緩衝區的快取,也就是臨時儲存的數據

gcc 關於編譯器的幾個宏定義總結 :
#ifdef GNUC //指的是檢查編譯器的版本,是否符合要編譯的版本(一般都會附加在標頭檔案中,爲不同的編譯環境的準備)

attribute 的使用(不是經常用到,但是可以讓C用的更靈活):
下面 下麪是寫的很全的兩個連線大家可以看看
https://www.cnblogs.com/embedded-linux/p/5801999.html
https://blog.csdn.net/weixin_38233274/article/details/82188997
也可以去官網 GNUC 裏面的使用會更加全面