2009-09-13 2 views
3

최근에 내가 사용해야하는 것에 대해 질문했습니다. create self-contained executables that would be deployed under a number of Linux distribution. 처음에는 무서워했지만 C++에 관해 읽은 후에는 실행 파일의 첫 번째 버전을 얻을 수있었습니다.C++ 실행 가능 배포 전략

하루가 기쁨으로 가득한 후 나는 방금 또 다른 딜레마로 벽에 부딪쳤다. 생성 된 실행 파일은 여러 Linux 배포판 (Slackware, Arch, Ubuntu, Debian, CentOS 등)에 설치해야하며, 그 방법을 완전히 알지 못합니다. CentOS 및 Debian 기반 OS에는 apt 또는 yum과 같은 패키지 관리자가 있지만이 점이 내 경우에 적용되는지 확신 할 수 없습니다.

가 내가 쓴 코드는 더 구체적으로 RudeSocketyaml-cpp 라이브러리 (몇 가지에 달려있다. 내가 실행 파일을 컴파일하고 동적으로 연결할 수있을 것이라고 말되었다, 그래서 난 그냥 실행 파일을 배포 할 필요가 있었다.

나는 동적 링크 만 (명백하게) 때 함께 갔다, 처음에는

:

내 문제는 지금까지의 제가 여기 (단지 RudeSocket 용) YAML-CPP 라이브러리에 대한 운영자와 파일을 찾을 수 없음을 발생합니다. 실행 파일을 다른 상자에 복사 :

$ ./main 
./main: error while loading shared libraries: libyaml-cpp.so.0.2: cannot open shared object file: No such file or directory 
정적으로 컴파일하려고 할 때 (내가 언급 한 바와 같이 나는 YAML-CPP의 .A 파일이 없기 때문에)

, 내가 너무 오류가 발생합니다 :

$ g++ main.cpp parse.cpp parse.h rudesocket-1.3.0/.libs/librudesocket.a -o main -static -L/usr/local/librudesocket-1.3.0/.libs/librudesocket.a(socket_connect_normal.o): In function `rude::sckt::Socket_Connect_Normal::simpleConnect(int&, char const*, int)': 
/root/webbyget/sockets/rudesocket-1.3.0/src/socket_connect_normal.cpp:250: warning: Using 'gethostbyname' in statically linked applications requires at runtime the shared libraries from the glibc version used for linking 
/tmp/cc3cEVK1.o: In function `operator>>(YAML::Node const&, Job&)': 
parse.cpp:(.text+0x1a83): undefined reference to `YAML::Node::size() const' 
/tmp/cc3cEVK1.o: In function `handle_job(rude::Socket, char const*)': 
parse.cpp:(.text+0x1b79): undefined reference to `YAML::Parser::Parser(std::basic_istream<char, std::char_traits<char> >&)' 
parse.cpp:(.text+0x1bfd): undefined reference to `YAML::Node::Node()' 
parse.cpp:(.text+0x1c10): undefined reference to `YAML::Parser::GetNextDocument(YAML::Node&)' 
parse.cpp:(.text+0x1dc6): undefined reference to `YAML::Node::size() const' 
parse.cpp:(.text+0x1dee): undefined reference to `YAML::Node::~Node()' 
parse.cpp:(.text+0x1e18): undefined reference to `YAML::Node::~Node()' 
parse.cpp:(.text+0x1e37): undefined reference to `YAML::Parser::~Parser()' 
parse.cpp:(.text+0x1e61): undefined reference to `YAML::Parser::~Parser()' 
(...) 

그것은 나에게 그 g ++ 컴파일 할 수 없습니다 꽤 명백하다 yaml-cpp에 대한 클래스를 어디에서 찾을지를 정적으로 알려주지 않습니다.

사람이 개입하지 않고 설치가 자동으로 이루어져야한다는 것이 매우 중요합니다.

그래서 제 질문은 정말 두 가지이다 :

  • 가 어떻게 모든 배포판을 대상으로 가장 복잡한 방법으로이 컴파일 된 프로그램을 배포 할 수 있습니다?

  • 이런 종류의 문제에 대한 사실상의 표준 해결책은 무엇입니까?

사전에

펠리페을 주셔서 감사합니다.

답변

4

당신은 시도 this technique 줄 수 있습니다.

+1

아주 좋은 옵션입니다. 기본적으로, 동적으로 링크하지만, 특수한 -rpath 옵션을 사용하여 런타임 링커가 실행 파일과 동일한 디렉토리에서 lib를 찾도록합니다. 그런 다음 실행 파일과 함께 동적 라이브러리를 배포했습니다. – divegeek

+1

이것은 좋은 기술이지만 [Ermine] (http://www.magicermine.com/)의 사본을 얻었습니다. 그래서 가치가있는 :-) – kolrie

0

많은 사실상 표준이 있지만 어느 것도 표준화되지 않았습니다. :(컴파일 된 바이너리를 배포하고 싶다면, 타겟으로하고 싶은 플랫폼마다 패키지를 만들고 싶을 것입니다. rpm과 deb을 생성하면 90 %가됩니다. 빌드를 자동화하고 싶다면 과정은 autoconf를/Automake는 아직 갈 (아마도) 가장 좋은 방법입니다.

0

당신이 플랫폼 패키지 관리자를 사용하는 경우 (.rpm을 또는 뎁) 시스템이 확인합니다 공유 라이브러리의 올바른 버전이 필요하면 다운로드하십시오.

CPack은 아마도 가장 쉬운 패키지 생성기입니다.

0

아마도 가장 좋은 해결책은 CMake입니다.

CMake은 크로스 플랫폼, 오픈 소스 빌드 시스템입니다. 이 도구는 소프트웨어를 작성, 테스트 및 패키지하기 위해 설계된 도구 모음입니다. 패키징을 위해서는 Mgb가 적합합니다. CMake는 CPack과 쉽게 연결할 수 있습니다.

KDE는이 솔루션과 automake/autoconf에 대한 좋은 대안을 사용하고 있습니다.