安全程式碼撰寫

安全程式碼撰寫（Secure coding）是依照安全指引開發電腦軟體，避免引入漏洞的軟體開發實務。設計缺陷、程序错误及邏輯謬誤是最常被利用軟體漏洞的主要原因。若識別出這些不安全的程式碼撰寫實務，教育程式設計師改用較安全的軟體寫法，組織可以有主動的措施，在程式佈置之前就消除或大幅減少軟體漏洞。

有些研究者建議，為了有效的面對網路安全相關的威脅，應該在程式碼撰寫時加入適當的安全性。若在軟體設計時就已考慮安全性，這可以避免內部人士的攻擊，也減少和應用程式安全有關的威脅。

 避免缓冲区溢出 
缓冲区溢出是常見的軟體安全漏洞，若程序要在固定長度的緩衝區儲存超過其大小的資料，就會出現此一問題。例如，有8個位置可以儲存資料，但程式卻試著要儲存9個資料，就會出現問題。缓冲区溢出會覆寫到鄰近位置的記憶體，造成安全漏洞（棧緩衝區溢出）或是程式中止執行（例如出現記憶體區段錯誤）

以下是一個容易出現缓冲区溢出的C語言程式例子：
int vulnerable_function(char * large_user_input) {
    char dst[SMALL];
    strcpy(dst, large_user_input);
}
若使用者輸入的資料比緩衝區的大小要大，就會出現缓冲区溢出。

若要修正此一問題，可以用strncpy來避免缓冲区溢出int secure_function(char * user_input) {
    char dst[BUF_SIZE];
    // copy a maximum of BUF_SIZE bytes
    strncpy(dst, user_input, BUF_SIZE);
}
另一種作法是用malloc指令，在heap裡動態分配記憶體char * secure_copy(char * src) {
    size_t len = strlen(src);
    char * dst = (char *) malloc(len + 1);
    if (dst != NULL) {
        strncpy(dst, src, len);
        // append null terminator 
        dst[len] = '\0';
    }
    return dst;
}
在上述的程式片段裡，程式設法將src的內容複製到dst，不過也會檢查malloc的傳回值，確定有足夠的記憶體可以分配記憶體給dst。

 避免格式字串攻擊 
是惡意用戶在輸入一些會提供給格式設定函式（如printf()）的資料時，輸入特殊的內容，讓函式的動作異常。此攻擊會破壞性的讀取或寫入呼叫堆疊。

C語言的printf函式會將輸出寫到stdout。若其引數的格式有誤時，會造成一些嚴重的安全錯誤。以下是一個格式字串攻擊的例子。
int vulnerable_print(char * malicious_input) {
	printf(malicious_input);
}
像是"%s%s%s%s%s%s%s"就屬於惡意輸入，會因為不正確的記憶體讀取而讓程式崩潰。
 避免整數溢位 
整數溢位會出現在整數運算的結果太大，用規劃的記憶體空間無法正確表示的情形。若程式沒有檢查整數運算的結果，設法避免整數溢位，可能會造成軟體錯誤或是漏洞。

以下是C++的函式，原始目的是要確認x和y相加的結果小於等於已定義好的數值MAX:
bool sumIsValid_flawed(unsigned int x, unsigned int y) {
	unsigned int sum = x + y;
	return sum <= MAX;
}
這段程式的問題是在進行整數的加法之後才進行檢查。若x和y的和大於unsigned int可以表示的最大值，在進行加法之後就已出現溢位，因此雖然x和y的和大於MAX，但是其溢位後的結果可能會小於MAX。

以下也是檢查溢位的程式，加上了檢查x和y的和是否有大於等於x,y二個數值的判斷，因為x和y是無號數整數，二者的和不會小於其中的任一數字。若是若計算出來的和小於任一數字，就代表已經溢位了。
bool sumIsValid_secure(unsigned int x, unsigned int y) {
	unsigned int sum = x + y;
	return sum >= x && sum >= y && sum <= MAX;
}

 避免目錄遍歷 
目錄遍歷是由不可靠來源提供的路徑產生的漏洞，該路徑造成了未授權的伺服器目錄或是檔案存取。

例如，考慮一個接受檔案名稱，讀取文章的腳本，腳本會讀檔案名稱輸入，之後進行處理。這樣腳本可能會用類似以下的的URL 來找有關dog food的文章。
 https://www.example.net/cgi-bin/article.sh?name=dogfood.html
若此腳本沒有輸入檢查，相信使用者輸入的檔案都是有效的，惡意使用者可能會產生以下的URL來取得網站伺服器的組態：
 https://www.example.net/cgi-bin/article.sh?name=../../../../../etc/passwd
若是在类Unix系统中，這可能會洩漏/etc/passwd檔，其中包括了用户ID、用户名稱、家目录路徑等。（SQL注入也是類似情境下的攻擊）。
 相關條目 
 應用程式安全
 防御性编程
 安全錯誤
 預設安全

 參考資料 

 參考書目 


Category:電腦安全