2013-04-22 9 views
7

मैं एक पुस्तकालय बना रहा हूं। जब मैं इसे स्थिर पुस्तकालय के रूप में संकलित करता हूं, तो यह ठीक काम करता है। अब मैं इसे एक साझा पुस्तकालय में बदलना चाहता था। लाइब्रेरी बनाई गई है और उचित जगह पर, लेकिन जब मैं क्लाइंट कोड संकलित करने का प्रयास करता हूं, तो लिंकिंग चरण कहता है कि यह लाइब्रेरी नहीं ढूंढ सकता है।साइगविन जी ++ लिंकर साझा लाइब्रेरी नहीं मिला

मैंने पहले ही इसे अल या डाइलिब में बदलने का प्रयास किया है, लेकिन इससे कोई मदद नहीं मिलती है। जब मैं लिंक पर -v ध्वज डालता हूं, तो मैं देख सकता हूं कि मेरा लाइब्रेरी पथ वहां है। मैंने विभिन्न पथों की भी कोशिश की। मैं एक सापेक्ष पथ का उपयोग करता हूं, लेकिन एक पूर्ण पथ के साथ भी यह नहीं मिलता है। आवेदन के लिए

.SUFFIXES: 
.SUFFIXES: .o .cpp 
.SUFFIXES: .o .d 

CC := g++ 
LNK:= g++ 

CXXFLAGS_RELEASE = -fPIC -shared -O2 -Wall -fmessage-length=0 
CXXFLAGS_DEBUG  = -fPIC -shared -g -Wall -fmessage-length=0 -D _DEBUG 

CXXFLAGS = $(CXXFLAGS_DEBUG) 

OBJDIR:=  obj 
SRCDIR:=  src 
HDIR:=   include 

INCLUDE_PATHS:= -Iinclude -Iinclude/interfaces -Iinclude/support 

CPP_FILES := propertyfile/propertyfile.cpp \ 
      propertyfile/propertyitem.cpp \ 
      propertyfile/propertyfactory.cpp \ 
      helper/string_helper.cpp 

OBJ :=  $(patsubst %.cpp,$(OBJDIR)/%.o, $(CPP_FILES)) 
SRC :=  $(patsubst %.cpp,$(SRCDIR)/%.o, $(CPP_FILES)) 

LIBS:=  

TARGET:= libsupport.so 

all: $(TARGET) 

$(TARGET): $(OBJ) 
    $(LNK) -o $(TARGET) $(OBJ) -shared 
    @cp $(TARGET) ../lib 
    @cp -r include .. 

clean: 
    rm -f $(OBJ) $(ASM) $(TARGET) 

-include $(patsubst %.cpp,$(OBJDIR)/%.d, $(CPP_FILES)) 

$(OBJDIR)/%.o: $(SRCDIR)/%.cpp $(OBJDIR)/%.d 
    @mkdir -p `dirname [email protected]` 
    $(CC) $(CXXFLAGS) -c $< -o [email protected] $(INCLUDE_PATHS) 

$(OBJDIR)/%.d: $(SRCDIR)/%.cpp 
    @mkdir -p `dirname [email protected]` 
    $(CC) $(CXXFLAGS) -MM -MT [email protected] -MF $(OBJDIR)/$*.d -c $< $(INCLUDE_PATHS) 

और यहाँ Makefile IST:

Makefile पुस्तकालय फार्म

.SUFFIXES: 
.SUFFIXES: .o .cpp 

CC := g++ 
LD := g++ 

CXXFLAGS_RELEASE = -O2 -Wall -fmessage-length=0 
CXXFLAGS_DEBUG  = -g -Wall -fmessage-length=0 -D _DEBUG 
CXXFLAGS = $(CXXFLAGS_DEBUG) 

OBJDIR:=  obj 
SRCDIR:=  src 

INCLUDE_PATHS:= -Iinclude -I../include 
LIBS:=  -L /cygdrive/d/src/c/lib -lsupport 

CPP_FILES := nohupshd.cpp \ 
      daemon.cpp \ 
      task.cpp 

OBJ :=  $(patsubst %.cpp,$(OBJDIR)/%.o, $(CPP_FILES)) 
SRC :=  $(patsubst %.cpp,$(SRCDIR)/%.o, $(CPP_FILES)) 

TARGET:= nohupshd 

all: $(TARGET) 

$(TARGET): $(OBJ) 
    $(LD) -o $(TARGET) $(OBJ) $(LIBS) 

clean: 
    rm -f $(OBJ) $(ASM) $(TARGET) 

-include $(patsubst %.cpp,$(OBJDIR)/%.d, $(CPP_FILES)) 

$(OBJDIR)/%.o: $(SRCDIR)/%.cpp $(OBJDIR)/%.d 
    @mkdir -p `dirname [email protected]` 
    $(CC) $(CXXFLAGS) -c $< -o [email protected] $(INCLUDE_PATHS) 

$(OBJDIR)/%.d: $(SRCDIR)/%.cpp 
    @mkdir -p `dirname [email protected]` 
    $(CC) $(CXXFLAGS) -MM -MT [email protected] -MF $(OBJDIR)/$*.d -c $< $(INCLUDE_PATHS) 

उत्तर

11

कुछ मैं कैसे cygwin के तहत एक शेयर की गई लाइब्रेरी को संकलित करने पर एक समाधान पाया प्रयोग करने के बाद।

स्पष्ट रूप से संकलक एक डीएलएल फ़ाइल की तलाश में है, भले ही यह सिगविन के अंदर है। तो पहला कदम अपने पथ को जोड़ना है, जहां पुस्तकालय पैथ चर के लिए जा रहा है।

export PATH=$PATH:/cygdrive/d/src/c/lib 

स्पष्ट रूप से साझा लाइब्रेरी के विरुद्ध लिंक करते समय, लिंकर डिफ़ॉल्ट रूप से एक डीएलएल फ़ाइल की तलाश में प्रतीत होता है। मुझे नहीं पता क्यों, क्योंकि सिग्विन के अंदर मैं उम्मीद करता हूं कि यह अन्य यूनिक्स सिस्टम की तरह एक .so फ़ाइल की तलाश करेगी।

हालांकि, इसके लिए दो समाधान हैं, जो दोनों काम करते हैं।

सबसे पहले, आप .dll

ln -s /cygdrive/d/src/lib/libsupport.so libsupport.dll 

इस मामले makefile नहीं है में नाम के साथ अपने .so लाइब्रेरी का लिंक बना सकते हैं परिवर्तित करने की और जब तक जोड़ने -lsupport पुस्तकालय मिल जाएगा। मैं इस समाधान को पसंद करता हूं।

दूसरा, आप पूर्ण नाम के साथ लिंकर विकल्प निर्दिष्ट कर सकते हैं।

LIBS:=  -L /cygdrive/d/src/c/lib -l:libsupport.so 

तो आपको एक लिंक बनाने की आवश्यकता नहीं है।

तो महत्वपूर्ण बात यह प्रतीत होती है कि साझा लाइब्रेरी साइगविन के तहत पाथ में होना चाहिए। LD_LIBRARY_PATH का उपयोग उस मामले में मदद नहीं करता है क्योंकि आप निष्पादन योग्य को लिंक कर सकते हैं, लेकिन इसे चलाने का प्रयास करते समय, यह नहीं मिलेगा।

ldd nohupshd.exe 

libsupport.so => not found 

अपडेट: किसी कारण से जब मैंने ldd के साथ चेक किया, तो मेरी लाइब्रेरी अचानक सूची से चली गई। मुझे पता चला कि साइगविन एमएस विंडोज और यूनिक्स साझा पुस्तकालयों के बीच अंतर करने के लिए नाम का उपयोग करता है। तो इसे काम करने के लिए, लाइब्रेरी का नाम इसे काम करने के लिए cyg.so होना चाहिए, अन्यथा एक्सेक्टेबल कुछ विंडोज़ बिल्ड लगता है। इस मामले में आपको x.dll नामक लिंक बनाने की आवश्यकता नहीं है क्योंकि साझा लाइब्रेरी यूनिक्स पर्यावरण के अंदर रहता है।

$(LNK) -o cyg$(TARGET).so $(OBJ) -shared 

डीबगिंग के लिए ग्रहण का उपयोग करते समय, साझा लाइब्रेरी का पथ विंडोज पथ पर्यावरण चर में भी होना चाहिए। अन्यथा डीबग सत्र तुरंत त्रुटि के बिना समाप्त हो जाता है।

संबंधित मुद्दे