fgets()與gets()函式的區別,並用gdb工具除錯驗證
南昌大學工程實驗報告
學生姓名:秦琦琛 學 號: 8000116350 專業班級:軟工1611班
實驗型別:■ 驗證 □ 綜合 □ 設計 □ 創新 實驗日期: 2018、10、8 實驗成績:
一、實驗目的
熟悉linux程式設計環境,學會使用gcc、gdb和編寫工程管理檔案makefile。
- 實驗內容
- 將書中例題2-2和2-3調出結果,並編寫對應的帶引數的makefile檔案。
- 實驗要求
1.必須編制測試樣例,將程式中兩函式的區別體現。提交程式碼截圖和執行結果截圖並附文字說明情況。
2.使用gdb工具,進行動態除錯。檢視在輸入測試用例時,程式執行的情況。
3.實驗報告必須用南昌大學統一的實驗報告格式模板製作,報告以sybg1.doc命名提交。
四、主要實驗步驟
1.建立如下檔案
如圖所示程式碼,為本實驗標頭檔案my.h。包含函式的定義以及必要標頭檔案宣告
2.使用makefile管理檔案進行編譯
3.除錯: 使用gdb命令除錯,除錯之前首先用gcc –g命令來生成除錯資訊,否則除錯失敗:
五、實驗資料及處理結果
1.測試樣例分析:兩函式的區別
(1)
使用fgets()函式:
輸入:1234567890 輸出:1234567 890\n
分析:p2-2.c
此外,fgets()函式的讀取,並沒有發生溢位。每次讀取到n位空間時,從緩衝區讀取n-1位,最後一位函式自動設為’\0’作為結束符,剩下的留待下次讀取,不會出現溢位。
(2)
使用fgets()函式:
輸入:123456
分析:此種情景,同上示例第二次讀取
(3)
使用gets()函式:
輸入:123456789123456789 輸出:123456789123456789
溢位:9123456789
分析:gets()函式以’\n’作為結束符。當如上輸入時,gets()函式從首位讀取,直到碰到第一個’\0’位置,並輸出’\0’之前的全部字元。不會因為buffer.buf的定義大小而停止讀取,此時發生溢位。(此種方式容易發生溢位攻擊)
Buffer.buf發生溢位,前八個字元被讀取到buffer.buf內,剩下的依舊被gets()函式一同讀取,順位被讀取到記憶體地址中。故buffer.others讀取剩下的全部字元,包括最後的’\n’字元,並作為輸出buffer.others的結束符。
- gdb除錯跟蹤:
- fgets()函式除錯
未輸入資料時,buffer.buf的內容有’\0’填充
輸入1234567890後,讀取1234567到buffer.buf前七個位元組,最後一個位元組被’\0’填充
並且沒有溢位。剩餘資料,留待下次讀取
下次讀取890’\n’ 共四個字元,最後由’\0’作為結束符。
- gets()函式除錯
輸入1234567890後,函式讀取的資料如下
發生溢位,資料超出BUF_SIZE的部分被讀取到buffer.others中。發生溢位
不會因為’\n’作為結束符,將其作為‘普通’字元,進行輸出