首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> 關於C語言

Linux C 函式庫建立與呼叫完整教學:靜態與動態庫實作

     編輯:關於C語言

Linux C 函式庫建立與呼叫完整教學

在大型專案開發中,將數百 MB 甚至數 GB 的程式碼全部置於單一執行檔中,不僅編譯耗時,後續維護修改極為繁瑣。透過將不同功能模組封裝為共享函式庫,可實現程式碼複用、減少磁碟佔用、支援獨立更新部署,大幅提升開發效率。本文詳解 Linux 下 C 函式庫的建立、編譯參數、路徑解析與跨語言呼叫實戰。

專案目錄結構規劃

library/
├── file1/
│   ├── file1.c
│   ├── hello.h
│   └── hello.c
├── file2/
│   ├── file2.c
│   ├── hi.c
│   └── hi.h
├── file3/
│   ├── file3.h
│   └── file3.cpp
└── LIB/                 # 存放編譯產出的 .so 檔案

動態函式庫建立關鍵步驟

1. 位置無關程式碼編譯

直接編譯共享庫常報錯:relocation R_X86_64_32 against `.rodata' can not be used when making a shared object; recompile with -fPIC。解決方案:加入 -fPIC 參數。

gcc -fPIC --shared play1.c -o libplay1.so

2. 執行期動態連結路徑問題

編譯成功但執行報錯 error while loading shared libraries: libplay1.so: cannot open shared object file,因載入器找不到庫檔案。解決方法:

  • 編譯時指定路徑:gcc -o file1 file1.c ./libplay1.so
  • 或設定環境變數 LD_LIBRARY_PATH
  • 或將庫複製至系統目錄 /usr/lib 並執行 ldconfig

完整實作範例:從原始碼到跨語言呼叫

file1 模組 (C 語言)

// file1.h
void play1(void);

// play1.c
#include 
void play1(void) { printf("hello file1\n"); }

// file1.c (主程式)
#include 
#include "file1.h"
int main(void) { play1(); return 0; }

file2 模組 (C 語言)

// hi.h
void hi(void);

// hi.c
#include 
void hi(void) { printf("hi file2\n"); }

// file2.c (主程式)
#include 
#include "hi.h"
int main(void) { hi(); return 0; }

file3 模組 (C++ 呼叫 C 庫)

// file3.h
#ifdef __cplusplus
extern "C" {
#endif
void hi(void);
void play1(void);
#ifdef __cplusplus
}
#endif

// file3.cpp
#include 
extern "C" { void play1(void); void hi(void); }
int main(void) { play1(); hi(); return 0; }

編譯與部署流程

# 1. 建立動態庫
gcc -fPIC --shared play1.c -o libplay1.so
gcc -fPIC --shared hi.c -o libfile2.so

# 2. 複製至統一目錄
cp libplay1.so ../LIB/
cp libfile2.so ../LIB/

# 3. C++ 程式連結 C 庫
g++ -o file3 file3.cpp ../LIB/libplay1.so ../LIB/libfile2.so
./file3
# 輸出:
# hello file1
# hi file2

C/C++ 混合編程關鍵點

  • C++ 呼叫 C 函式:需在頭檔以 extern "C" 包裹宣告,防止名稱修飾
  • C 呼叫 C++ 函式:C++ 端提供 extern "C" 包裹的介面函式
  • 編譯器選擇:C 代碼用 gcc,C++ 代碼用 g++,連結時統一用 g++

常見問題排查

錯誤現象原因解決方案
relocation R_X86_64_32缺少 -fPIC 參數加入 -fPIC 重新編譯
cannot open shared object file執行期找不到 .so指定相對路徑 ./libxxx.so 或設定 LD_LIBRARY_PATH
undefined reference連結順序錯誤或缺少 extern "C"調整庫連結順序、檢查 C/C++ 混合宣告
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved