想著想著,
如果有永遠的事
永遠
這兩個字,
如此的遙不可及,
那如何做出承諾呢?
如果只是隨口說說,
那又有什麼意義?
人呀,
總不能活在騙自己的謊言中,
期望別人會遵守承諾,
感覺沒有太大意義.
三隻獅子
运行configure时,提示找不到包含文件(include files)或者GD、gdbm的Lib库等套件
你可以在编译配置文件时查找头文件和库文件,并按非标准的附加形式让C的预处理器和连接器通过。如下所示:
CPPFLAGS=-I/path/to/include LDFLAGS=-L/path/to/library ./configure
如你使用csh及相容的Shell脚本作为你登录的脚本,则应该设为:
env CPPFLAGS=-I/path/to/include LDFLAGS=-L/path/to/library ./configure
yangacer
https://github.com/yangacer/CBDOC
用gcc 自製 Library
Library可分成三種,static、shared與dynamically loaded。
1. Static libraries
Static 程式庫用於靜態連結,簡單講是把一堆object檔用ar(archiver)
包裝集合起來,檔名以 `.a’ 結尾。優點是執行效能通常會比後兩者快,
而且因為是靜態連結,所以不易發生執行時找不到library或版本錯置而
無法執行的問題。缺點則是檔案較大,維護度較低;例如library如果發
現bug需要更新,那麼就必須重新連結執行檔。
1.1 編譯
編譯方式很簡單,先例用 `-c’ 編出 object 檔,再用 ar 包起來即可。
____ hello.c ____
#include
void hello(){ printf(“Hello “); }
____ world.c ____
#include
void world(){ printf(“world.”); }
____ mylib.h ____
void hello();
void world();
$ gcc -c hello.c world.c /* 編出 hello.o 與 world.o */
$ ar rcs libmylib.a hello.o world.o /* 包成 limylib.a */
這樣就可以建出一個檔名為 libmylib.a 的檔。輸出的檔名其實沒有硬性規定,
但如果想要配合 gcc 的 ‘-l’ 參數來連結,一定要以 `lib’ 開頭,中間是你要
的library名稱,然後緊接著 `.a’ 結尾。
1.2 使用
____ main.c ____
#include “mylib.h”
int main() {
hello();
world();
}
使用上就像與一般的 object 檔連結沒有差別。
$ gcc main.c libmylib.a
也可以配合 gcc 的 `-l’ 參數使用
$ gcc main.c -L. -lmylib
`-Ldir’ 參數用來指定要搜尋程式庫的目錄,`.’ 表示搜尋現在所在的目錄。
通常預設會搜 /usr/lib 或 /lib 等目錄。
`-llibrary’ 參數用來指定要連結的程式庫 ,’mylib’ 表示要與mylib進行連結
,他會搜尋library名稱前加`lib’後接`.a’的檔案來連結。
$ ./a.out
Hello world.
2. Shared libraries
Shared library 會在程式執行起始時才被自動載入。因為程式庫與執行檔
是分離的,所以維護彈性較好。有兩點要注意,shared library是在程式起始
時就要被載入,而不是執行中用到才載入,而且在連結階段需要有該程式庫
才能進行連結。
首先有一些名詞要弄懂,soname、real name與linker name。
soname 用來表示是一個特定 library 的名稱,像是 libmylib.so.1 。
前面以 `lib’ 開頭,接著是該 library 的名稱,然後是 `.so’ ,接著
是版號,用來表名他的介面;如果介面改變時,就會增加版號來維護相容度。
real name 是實際放有library程式的檔案名稱,後面會再加上 minor 版號與
release 版號,像是 libmylib.so.1.0.0 。
一般來說,版號的改變規則是(印象中在 APress-Difinitive Guide to GCC中有
提到,但目前手邊沒這本書),最尾碼的release版號用於程式內容的修正,
介面完全沒有改變。中間的minor用於有新增加介面,但相舊介面沒改變,所以
與舊版本相容。最前面的version版號用於原介面有移除或改變,與舊版不相容
時。
linker name是用於連結時的名稱,是不含版號的 soname ,如: libmylib.so。
通常 linker name與 real name是用 ln 指到對應的 real name ,用來提供
彈性與維護性。
2.1 編譯
shared library的製作過程較複雜。
$ gcc -c -fPIC hello.c world.c
編譯時要加上 -fPIC 用來產生 position-independent code。也可以用 -fpic
參數。 (不太清楚差異,只知道 -fPIC 較通用於不同平台,但產生的code較大
,而且編譯速度較慢)。
$ gcc -shared -Wl,-soname,libmylib.so.1 -o libmylib.so.1.0.0
hello.o world.o
-shared 表示要編譯成 shared library
-Wl 用於參遞參數給linker,因此-soname與libmylib.so.1會被傳給linker處理。
-soname用來指名 soname 為 limylib.so.1
library會被輸出成libmylib.so.1.0.0 (也就是real name)
若不指定 soname 的話,在編譯結連後的執行檔會以連時的library檔名為
soname,並載入他。否則是載入soname指定的library檔案。
可以利用 objdump 來看 library 的 soname。
$ objdump -p libmylib.so | grep SONAME
SONAME libmylib.so.1
若不指名-soname參數的話,則library不會有這個欄位資料。
在編譯後再用 ln 來建立 soname 與 linker name 兩個檔案。
$ ln -s libmylib.so.1.0.0 libmylib.so
$ ln -s libmylib.so.1.0.0 libmylib.so.1
2.2 使用
與使用 static library 同。
$ gcc main.c libmylib.so
以上直接指定與 libmylib.so 連結。
或用
$ gcc main.c -L. -lmylib
linker會搜尋 libmylib.so 來進行連結。
如果目錄下同時有static與shared library的話,會以shared為主。
使用 -static 參數可以避免使用shared連結。
$ gcc main.c -static -L. -lmylib
此時可以用 ldd 看編譯出的執行檔與shared程式庫的相依性
$ldd a.out
linux-gate.so.1 => (0xffffe000)
libmylib.so.1 => not found
libc.so.6 => /lib/libc.so.6 (0xb7dd6000)
/lib/ld-linux.so.2 (0xb7f07000)
輸出結果顯示出該執行檔需要 libmylib.so.1 這個shared library。
會顯示 not found 因為沒指定該library所在的目錄,所找不到該library。
因為編譯時有指定-soname參數為 libmylib.so.1 的關係,所以該執行檔會
載入libmylib.so.1。否則以libmylib.so連結,執行檔則會變成要求載入
libmylib.so
$ ./a.out
./a.out: error while loading shared libraries: libmylib.so.1:
cannot open shared object file: No such file or directory
因為找不到 libmylib.so.1 所以無法執行程式。
有幾個方式可以處理。
a. 把 libmylib.so.1 安裝到系統的library目錄,如/usr/lib下
b. 設定 /etc/ld.so.conf ,加入一個新的library搜尋目錄,並執行ldconfig
更新快取
c. 設定 LD_LIBRARY_PATH 環境變數來搜尋library
這個例子是加入目前的目錄來搜尋要載作的library
$ LD_LIBRARY_PATH=. ./a.out
Hello world.
3. Dynamically loaded libraries
Dynamicaaly loaded libraries 才是像 windows 所用的 DLL ,在使用到
時才載入,編譯連結時不需要相關的library。動態載入庫常被用於像plug-ins
的應用。
3.1 使用方式
動態載入是透過一套 dl function來處理。
#include
開啟載入 filename 指定的 library。
void *dlsym(void *handle, const char *symbol);
取得 symbol 指定的symbol name在library被載入的記憶體位址。
int dlclose(void *handle);
關閉dlopen開啟的handle。
char *dlerror(void);
傳回最近所發生的錯誤訊息。
____ dltest.c ____
#include
#include
#include
void *handle;
void (*f)();
char *error;
/* 開啟之前所撰寫的 libmylib.so 程式庫 */
handle = dlopen(“./libmylib.so”, RTLD_LAZY);
if( !handle ) {
fputs( dlerror(), stderr);
exit(1);
}
/* 取得 hello function 的 address */
f = dlsym(handle, “hello”);
if(( error=dlerror())!=NULL) {
fputs(error, stderr);
exit(1);
}
/* 呼叫該 function */
f();
dlclose(handle);
}
編譯時要加上 -ldl 參數來與 dl library 連結
$ gcc dltest.c -ldl
結果會印出 Hello 字串
$ ./a.out
Hello
關於dl的詳細內容請參閱 man dlopen
—
參考資料:
Creating a shared and static library with the gnu compiler [gcc]
http://www.adp-gmbh.ch/cpp/gcc/create_lib.html
Program Library HOWTO
http://tldp.org/HOWTO/Program-Library-HOWTO/index.html
APress – Definitive Guide to GCC
BKDRHash
// BKDR Hash Function
unsigned int BKDRHash(char *str)
{
unsigned int seed = 131; // 31 131 1313 13131 131313 etc..
unsigned int hash = 0;
while (*str)
{
hash = hash * seed + (*str++);
}
return (hash & 0x7FFFFFFF);
}
里斯特資訊媒體股份有限公司
里斯特資訊媒體股份有限公司
公司簡介
里斯特資訊媒體(Richi)成立於2007年7月,以數位內容加值服務為核心,不斷嘗試創新網路服務模式,期望在個人化的網路時代裡,為產業尋找新形態的服務架構,為消費者提供更符合個人化需求的服務支援。
成立3年,Richi屢獲國內外創新商業模式獎項。2010年在號稱「矽谷創投聖經」、足以影響全球科技業趨勢的雜誌「紅鯡魚」(Red Herring)年度新創公司評選中,以「虛擬貨幣交換中心」機制的概念,擊敗上百家公司,與台灣興櫃股王PChome商店街並列「2010亞州科技 100強」;並在2011年1月底在美國洛杉磯獲頒「2010 全球科技100強」,是台灣唯一獲得此殊榮的公司,也是台灣暌違已久,再度拿下這個全球新創團隊聖盃的唯一團隊。國內知名雜誌「商業週刊」專訪Richi 創業團隊,將Richi喻為未來的網路央行,並認為Richi是目前台灣最具發展潛力的新創網路公司之一。
看準社群行銷、行動裝置、小額付費與個人化內容等趨勢將帶來的龐大商機,Richi 未來將持續專注於發展社群貨幣(Social Payments)機制,並在台灣網路產業起飛的歷史中,成為所有網路創新團隊與創作者的最佳技術支援後盾。
你也想要在這個產業轉型的歷史性時刻中,占有一席之地嗎?Richi正在尋找一起實現夢想的夥伴。
透過嚴謹的軟體專案管理流程訓練,Richi團隊裡的各個不同部門,不管是業務、行銷、設計或是研發,所有成員都能共同參與創新網路服務的發想、討論與實現,與不同專業的夥伴分工合作,共同實現網路世界裡無限可能的創意。
Richi認為,在網路的時代裡,「人」才是最重要的價值。如果你對於網路的未來充滿無限想像,如果你也認為堅持和努力是實現夢想的最重要特質,我們非常期待你的加入。
主要商品及服務
– 線上虛擬點數交換平台金流機制
– 社群貨幣(Social Payments)與贊助機制
– 內容社群。包含數位時代OpenCrunch、財訊Wealth、河岸留言Open Jam
– 協辦Tech Orange新媒體。以台灣的TechCrunch為目標,創立三周即進入台灣前千大網站。
– 數位內容與數位廣告服務
– Skype VOIP加值服務
– 移動設備之通訊軟體與加值服務
經營理念
Richi在更開放與自由的資訊環境中,以數位內容加值服務為核心,不斷嘗試創新網路服務模式,期望在個人化的網路時代裡,為產業尋找新形態的服務架構,為消費者提供更符合個人化需求的服務支援。並以台灣為出發點,將服務輻射式推廣至不同語系的國家與地區。
php function pointer
call_user_func
php curl multi interface
// create the multi curl handle
$mh = curl_multi_init();
$handles = array();
for($i=0;$i<5;$i++)
{
// create a new single curl handle
$ch = curl_init();
// setting several options like url, timeout, returntransfer
// simulate multithreading by calling the wait.php script and sleeping for $rand seconds
curl_setopt($ch, CURLOPT_URL, "http://put your url here/wait.php?seconds=".($i+1));
curl_setopt($ch, CURLOPT_HEADER, 0);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_TIMEOUT, 30);
// add this handle to the multi handle
curl_multi_add_handle($mh,$ch);
// put the handles in an array to loop this later on
$handles[] = $ch;
}
// execute the multi handle
$running=null;
do
{
curl_multi_exec($mh,$running);
// added a usleep for 0.25 seconds to reduce load
usleep (250000);
} while ($running > 0);
// get the content of the urls (if there is any)
for($i=0;$i<count($handles);$i++)
{
// get the content of the handle
$output.= curl_multi_getcontent($handles[$i]);
// remove the handle from the multi handle
curl_multi_remove_handle($mh,$handles[$i]);
}
// echo the output to the screen
echo $output;
// close the multi curl handle to free system resources
curl_multi_close($mh);
?>