在工程中用到使用python呼叫c++編寫的動態庫,結果報如下錯誤:
oserror: ./extract_str.so: undefined symbol: _znst8ios_base4initd1ev
python呼叫函式
1載入目錄檔案#coding:utf-8
2from ctypes import *
34 libpcre = cdll.loadlibrary("
./extract_str.so")
5 pcre="
^girlfriend\s+server\s+\d+\x2e\d+\s+\x2e\s+port\s+\d
"6 ret = libpcre.extract_exact_strings(pcre, len(pcre), 4, max_str, max_str_len, expr_str, expr_str_len)
7if ret == 1: #
解析成功
8print
(ret)
9print
(max_str)
10print
(expr_str)
11else: #
解析失敗
12print("
ret is not 1!
")
報錯:
執行nm命令
通過搜尋知道ios_base4init 是c++標準輸入輸出函式庫,說明該庫未被載入。搜尋知道是由於鏈結的問題。
檢視makefile
1 cc =gcc原始檔為c++,在生成動態庫時使用的是gcc,導致c++標準庫未被鏈結。兩種修改方式2 ccc = g++
3 cflags = -g -wall $(open_o2) -wstrict-prototypes -fpic
4 cppflags = -g -wall $(open_o2) -fpic
5 incs = -i../include
6 sources = $(wildcard *.c *.cpp)
7 objs = $(patsubst %.cpp,%.o, $(patsubst %.c, %.o, $(sources)))
8 targets =extract_str.a
9 shard_targets =extract_str.so
1011
.phony: all clean
1213
.c.o:
14 $(cc) -c $(cflags) -i. $(incs) $<
15.cpp.o:
16 $(ccc) -c $(cppflags) -i. $(incs) $<
1718
all: $(targets) $(shard_targets)
1920
clean:
21 rm -f *.a *.o core core.* *~
22 rm ../lib/$(targets)
23 rm ../lib/$(shard_targets)
2425
$(targets): $(objs)
26 ar -cr ../lib/$@ $^
2728
$(shard_targets): $(objs)
29 $(cc) -shared -o ../lib/extract_str.so $^
1. 用g++編譯,命令改為:
1 $(ccc) -shared -o ../lib/extract_str.so $^
2. 繼續使用gcc編譯,新增鏈結引數 –lstdc++ 命令改為:
1 $(cc) -shared -o ../lib/extract_str.so $^ -lstdc++
linux 下Python呼叫C模組
在c呼叫python模組時需要初始化python直譯器,匯入模組等,但python呼叫c模組卻比較簡單,下面還是以helloworld.c 和 main.py 做一說明 1 編寫c helloworld.c 很簡單,只是輸出 hello world!2 將編寫的c 編譯成動態鏈結庫的形式,具體命令 ...
Linux下C呼叫C 介面詳解
c 做久了,經常用c 的方式去思考問題,有時候就突然發現自己不太會寫c程式了。寫程式的時候,難免會用到第三方外掛程式或者是庫,而這些外掛程式或者庫很多時候都不能完全滿足我們的需求,遇到這種情況,如果全是c 那好辦,寫個介面卡就ok了,關於介面卡模式參考我的部落格 c adaptor 設計模式 如果要...
linux下Lua呼叫C函式
這篇文章 的基礎上編寫的,由於原文章採用的是lua 5.2以下的版本,但是lua 5.2的版本進行了很大的改動,導致之前的很多函式不能再使用。本文就解決了採用lua 5.3.0中的api函式之後,原文章中 存在的一些問題。這裡只講原文章中提到的第二種方法c函式庫成為lua的模組,以實現lua呼叫c函...