C語言尋找絕對路徑方法

前言

近期因客戶臨時要求須要把原先相對路徑的指向,全部修改成絕對路徑,查詢後這個方式僅能使用windows API去組合,但因開發工具特別被綁定只能使用C,C++的語法會出現無法編譯現象,因此這邊會搭配特數字串裁切方式協助各位製作出尋找絕對路徑的方式

相對位置

這邊先介紹相對位置,因撰寫比較簡單而且只要確定執行檔案開啟參照點使用以下方式去撰寫即可操作
可以看到這邊僅從exe執行檔位置起走,找尋對應參照

 const char* infFilePath = "./Driver/STM32Bootloader.inf";
char command1[512];
 snprintf(command1, sizeof(command1), "start /MIN cmd.exe /C \"pnputil -i -a %s\"", infFilePath);

但使用相對位置會出現從其他地方指向該資料夾執行exe會導致,周邊相對位置無法正常被執行,因路徑找不到,因此這邊如果有需求是需要從其他路徑指向或CMD方式從其他目錄去開起執行檔,就需要改成絕對位置

絕對位置

絕對位置這邊就會需要使用到windows API,因但純C會有點難實作主要借助
主要使用到的Function為GetModuleHandleEx與GetModuleFileName,這邊就可以獲取到目前執行檔的絕對位置,但這邊還包含執行檔本身名稱,因此會需要再把執行檔名稱去除,但目前有些project不支援C++因此PathRemoveFileSpec可能會無法使用
下面提供一小段範例去找出絕對路徑

	HMODULE hModule = NULL;// for get file path
	int iLength;
	// Initialize a file name, and New a logfile
	memset(g_filename, 0, sizeof(g_filename)); //filename
	 if (GetModuleHandleEx(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS, (LPCTSTR)HPFI_Initialize, &hModule) == 0) {
        int ret = GetLastError();
       // logToFile( "[HPFI_Initialize]INFO:GetModuleHandle failed, error = %d", ret);
        // Return or however you want to handle an error.
    }

    if (GetModuleFileName(hModule, szEntryDirectory, MAX_PATH) == 0) {
        int ret = GetLastError();
        //logToFile( "[HPFI_Initialize]INFO:GetModuleFileName failed, error = %d", ret);
        // Return or however you want to handle an error.
    }

結果圖如下

去除執行檔字串

這邊提供2種方法第一種是使用C++ windows API

    TCHAR szEntryDirectory[MAX_PATH];
    HMODULE hModule = NULL;
    if (GetModuleHandleEx(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS, (LPCTSTR)HPFI_GetPackagedFirmwareInfo, &hModule) == 0) {
        int ret = GetLastError();
        fprintf(stderr, "GetModuleHandle failed, error = %d\n", ret);
        // Return or however you want to handle an error.
    }
    if (GetModuleFileName(hModule, szEntryDirectory, MAX_PATH) == 0) {
        int ret = GetLastError();
        fprintf(stderr, "GetModuleFileName failed, error = %d\n", ret);
        // Return or however you want to handle an error.
    }
    if(PathRemoveFileSpec(szEntryDirectory) == 0)
        fprintf(stderr, "PathRemoveFileSpec failed!!\n");

另一種方式須先轉義成char在操作,基本上就是搜尋關鍵字位置,然後再複製到新的區域截掉不需要部分

  char *pch;
      pch = strstr(moduleFileName, "\\Firmware");
     // logToFile("[HPFI_Initialize]INFO: found at %d ",(pch-moduleFileName+1));
    strncpy(moduleFilepath, moduleFileName, (pch-moduleFileName));
    moduleFilepath[(pch-moduleFileName+1)]='\0';

Leave a Comment

Your email address will not be published. Required fields are marked *

Shopping Cart