1. 程式人生 > >[從0到1搭嵌入式工程]嵌入式應用層判斷SD卡是否存在,獲取大小和剩餘空間

[從0到1搭嵌入式工程]嵌入式應用層判斷SD卡是否存在,獲取大小和剩餘空間

1,判斷是否存在
    如果sd卡裝置存在, 在生成/sys/block/mmcblk0/device/cid檔案,存放sd卡的cid資訊, 同目錄下type檔案可以判斷卡型別,如果裝置只支援sd卡,就不需要判斷型別了。
    在程式碼中使用popen執行命令:cat /sys/block/mmcblk0/device/cid 2>/dev/null 。獲取返回值,如果有返回值,則認為sd卡存在。如果cid檔案或者目錄不存在,因為2>重定向,把錯誤輸入都丟到/dev/null中,所以如果出錯,就不會有返回。只有cid檔案存在,且讀出了值,返回返回結果。(1>/dev/null 是標準輸出到/dev/null)。
    在一個迴圈執行緒裡一直監測。
2,判斷是否存在,還有一種方法

    就是去access /dev/mmcblk0p1, /dev/mmcblk0px, x是因為sd卡不一定是p1分割槽, 甚至有的sd卡只有/dev/mmcblk0,來判斷,顯然不如第一種方法簡單。或者執行命令 fdisk -l, 在裝置列表裡面去找mmcblk0,都比較麻煩。

3,獲取總大小和剩餘空間大小
    sd卡mount目錄為/sdcard。
    使用statvfs系統呼叫,來獲取sd卡的block size和塊數,從而計算出大小。
    statvfs能夠根據目錄,返回已經mount的檔案系統的資訊,詳細介紹見:https://www.yiibai.com/unix_system_calls/fstatvfs.html

struct statvfs sdinfo;
memset(&sdinfo, 0x00, sizeof(struct statvfs));
if(0 == statvfs("/sdcard", &sdinfo))
{
    block_size = sdinfo.f_bsize;
	total_size = sdinfo.f_blocks * block_size;
	free_size = sdinfo.f_bfree * block_size;
}
else
{
	//bad card
}

    這裡存在一個問題,假設是total_size 是unsigned int型別,32位,那麼最大值為4294967295(2^32-1),4GB 對於sd卡容量顯然是不夠的, 直接賦值,會溢位。 
    程式碼進一步優化為:
        total_size = sdinfo.f_blocks/1024 * block_size;
        free_size = sdinfo.f_bfree/1024 * block_size;


    這樣total_size的單位就是KB,可以容納4*1024GB,足夠了。
    保險起見,在計算free_size時,應該表示為:
        free_size = min(total_size, sdinfo.f_bfree/1024 * block_size);
    保證不會比totalsize還大。