看板 C_and_CPP 關於我們 聯絡資訊
推文頗長,拋磚引玉,小提幾個點,有誤請指正。 ※ 引述《QQ29 (我愛阿蓉)》之銘言: : 大家好~ : 有一個疑惑始終無法找到解答 : 因為在某些Windows平台寫程式 : 會發現 假如他提供一個 : kernel32.dll 裡面含有export a(), b(), c()三個function. : 可是他給我們的header and lib 裡面用dumpbin 看 只有a和b...c看不到 ^^^^^^ keyword , 我假定你的環境是 Windows , Compiler Visual C++。 : 對我們寫程式來說 會發現link error, 因為用到c了 如果你確信用過 c(), 知道 c() 之正確的 prototype , 或確信該 dll - c() 功能無誤的話, 你可以直接用 LoadLibrary、GetProcAddress、FreeLibrary 這三個來完成即可, 這時根本用不到 .lib / .h; 如果你無法確信 c() 函式的品質,建議別強求。 : 但我在想 : 為啥他有能力提供 部分的 symbol包含在lib裡面? lib和dll不是一起 產生出來的嗎? ^^^^^^^^^^^^^^^^^ 我不確定這段話是完全正確, 「印象中」,是有只產生 dll,或只產生 lib ,其他的都不產生, 這點沒確認過,待查證。 我不是很清楚這部份是什麼情況,甚至不知道這份 dll 是「附著他的執行檔使用」, 還是給你「開發時調用」,若是「附著他的執行檔使用」時,只需給 dll , exe 便行, 其他都是多餘的, 如一般 user 電腦大概找不到 user32.lib 這東西吧 < 沒確認 > ? 但一般 user 電腦卻大量使用了 user32.dll 這東西, 當然你的情況較明顯是開發端。 對開發端而言,不難想像的是, 一份 project , dll 在 update 時,正常會連 .lib / .h 一起更新無誤, 但這是一般 coder 會做的事。 另一種更新方式是鑑於 .lib / .h 本身只是做「引導」動作, < 把 function entry 引到 dll 裡面去 > 所以更新時並不連 .lib / .h 一起附上,或是只附上舊版本的 .lib / .h, 很明顯的,這種更新方式對 coder 而言幾乎不會有人這麼幹! 會這麼幹的原因大概是忘了把 .lib / .h 做引導的 prototype 放進去而已, 不過大概不會有人真的那麼傻。 真正的原因我想是,那個 c() 被納成 un-document function, undocument function 在 Win32 API 裡面也是一狗票, 不公開 prototype 、不提供 .lib / .h 讓人調用, 可能只有內部開發的人才知道怎用、有哪些危險性、穩定性如何等, 只是用 dumpbin.exe 看得到 function name 而已。 : 我在想 : 他會不會是先build出一版 含有abc三個function的lib和dll.. : 然後再把__declspec(dllexport) 從.h的c function拔掉 如我所說,只要給正確的 dll 即可,其它的 lib, .h 都只是「導引」作用, 如果你知道該 function 之 prototype , .lib / .h 本身並沒太大義意存在。 < 雖這句話有點過誇張,不過現在和你講 延遲載入 的議題可能會暴 > 提一點我覺得納悶的地方, 既然你要用 c() , 為什麼不直接找供應商要完整的 .lib / .h 或 prototype ? 如果不能提供的話我想會給你滿意理由的,這比你在這裡猜半天來得有效率多了。 : 再次build一版....然後給我們新的lib和.h 而我們使用者還是用舊的含有abc的dll : 這是我認為的方法...但總覺得有更高深的作法 你想的方法沒錯,效果一樣,但較簡單。 另一種方式較麻煩,在生成 dll 之後,自己額外撰寫導引的 lib / header, 這些也是一般 IDE / compile 幫你做完的事。 : 另外有一個疑問... : 有沒有能力做出 : 多個lib 其實都mapping到同一個dll? : 謝謝 再強調,「有一種 lib」 只是導引到 dll, 而且這種 lib 可以自己寫, 所以你想把一個 dll ,依不同性質分類, 拆成數個 lib 做導引, 這又有無不可? 結論, lib / dll 並非成對產生,可以只有 lib , 也可以只有 dll, 而在調用 dll 時,為了呼叫方便,有時開發端會提供做導引的 lib, header; 但即使不提供,只要知道 dll 裡,某個 function 之 prototype, 一樣可以正常使用。 -- 「自從我學了 C# , 人都變聰明 , 考試都考一百分」 「自從我學了 VB , 皮膚都變好 , 人也變漂亮了 」 「自從我學了 Java , 明顯變壯 , 個子也變高了 」 「自從我學了 C++ , 內分泌失調 , 頭都禿了... 」 -- ※ 發信站: 批踢踢實業坊(ptt.cc) ◆ From: 180.177.76.161 ※ 編輯: EdisonX 來自: 180.177.76.161 (07/12 18:27)
diabloevagto:一般要自己選擇要dll還是lib,這兩個不絕對會一起出 07/12 20:58
diabloevagto:現,一般我自己寫的我都只產生dll,反正.h我有 07/12 20:59
diabloevagto:另外我記得lib是讓coder產生static link的吧? 07/12 20:59
littleshan:dynamic linked dll 是需要 lib 的 (在windows上) 07/12 21:16
diabloevagto:不過我在windows上,不需要lib產生出的exe就能讀dll 07/12 21:28
EdisonX:看來那段話真的是議題了,翻過自我修養,這裡沒講細,有文可 07/12 21:51
EdisonX:供參閱嗎 ? 07/12 21:51
QQ29:謝謝~ 我消化一下... 07/13 00:25
QQ29:藉此請教一下 我編譯一個exe給對方run會寫缺少msvcr100.dll 07/13 00:26
QQ29:這不是VS2010慣了才有的dll嗎? 一般人電腦不會有這dll吧... 07/13 00:26
james732:上面這個問題可以用靜態連結來解決 07/13 00:30
QQ29:是MD改成MT嗎? 所以一般外面商用軟體也是選MT 這選項嗎 07/13 00:30
purincess:一般外面商用軟體可能會整個包成installer或是另外幫你 07/13 00:32
purincess:裝redistributable 07/13 00:32
purpose:我這一般人的電腦硬碟裡,莫名就有了九十幾份 msvcr*.dll 07/13 00:34
EdisonX:< p大應不算一般人了吧 orz > 07/13 00:59
EdisonX:解決方式大多如 purincess 大所言,所以vs才有什麼散佈套裝 07/13 01:00
EdisonX:軟體,這時候編譯模式只要用MD就行,執行檔會小很多,但若你 07/13 01:01
EdisonX:不想別人為了自己寫的一個小程式,就裝肥大的 red~ 套件, 07/13 01:02
EdisonX:這時就會考慮用 MT 模式編譯,但不論是 MT,MD,一定不會是給 07/13 01:03
EdisonX:debug 版的 exe,因那些 dll 沒裝 vs 大概拿不到或拿不全吧 07/13 01:03
littleshan:debug版的dll拿得到,但依照license是不能散布的 07/13 01:18
littleshan:至於外面的商用軟體是不是用MT 這點可以自行確認... 07/13 01:21
EdisonX:難怪 vs redistribution 一直沒 ms??d??.dll 的東西. 07/13 01:29
EdisonX:感謝 l 大補充。 07/13 01:30
Chikei:dll的lib是做load time linking用的,跟static lib不一樣 07/13 10:16
Chikei:只有dll就必須用LoadLibrary來做runtime linking 07/13 10:17
EdisonX:謝謝 Chikei 補充 :) 07/13 18:45