2009년 1월 21일 수요일

라이브러리 이해하기 2 - 공유 라이브러리 버전 관리.

공유 라이브러리는 보통 아래와 같이 명명된다.

libMyLibrary.so.1.2.3

라이브러리는 용도에 따라 몇가지 서로 다른 이름을 가지고 있는데 혼돈되기 쉬우니 주의가 필요하다.

1. 링커 이름.(linker name)

링커 이름은 라이브러리 파일 명에서 버젼을 나타내는 숫자를 뺀 so까지의 이름이다. 즉 위에서는 libMyLibrary.so까지가 linker name이 된다. 링커 이름은 해당 라이브러리를 사용하는 프로그램을 빌드 할 때 사용되는 이름이다. 더 정확히 말하면, 프로그램이 빌드될 때 해당 프로그램이 사용하는 공유 라이브러리를 찾기 위해 링커 이름을 가진 파일이 빌드하는 시스템에 있어야 한다. 예를들어 어떤 어플리케이션이 libMyLibrary.so.1.2.3을 사용하여 컴파일 할 경우 빌드 옵션에 -lMyLibrary를 추가하게 되는데 이때 기본 라이브러리 경로나 혹은 –L 옵션을 사용하여 지정한 디렉토리에 libMyLibrary.so 파일, 즉 링커 이름으로 된 라이브러리 파일이 있어야 한다. (보통은 libMyLibrary.so.1.2.3에 대한 심볼링 링크로 이 파일을 만든다 이렇게 하는 이유는 호스트 개발 환경에 해당 라이브러리의 여러 버젼이 존재할 경우 이를 관리하기 위함이다. ) 크로스 컴파일을 하는 환경에서는 빌드시에만 링커 이름을 가진 파일이 필요하며, 타겟에서 실행 시에는 이 파일이 필요치 않다. 즉 개발하는 호스트 컴퓨터에는 라이브러리 파일 이름이 링커 이름으로 되어 있거나 이를 심볼링 링크로 만들어야 한다. 컴파일러/링커는 링커 이름을 가진 파일에서 이 라이브러리의 soname을 읽어오게 된다. 따라서 공유 라이브러리는 빌드시 실행 파일에 포함되지는 않지만 soname을 읽어와야 하기 때문에 공유 라이브러리가 빌드하는 호스트 시스템에 없으면 빌드가 되지 않는다.

2. soname

이 이름은 로더가 라이브러리를 실행할 때 찾는 이름으로 타겟에는 soname을 가진 파일이 반드시 있어야 한다. 때때로 이 파일은 심볼릭 링크로 다른 파일로 링크되어 있다.

일반적으로 soname은 so뒤에 숫자 하나를 추가하여 만든다.  예를 들어  libMyLibrary.so.1 가 위 라이브러리의 soname으로 적합하다. 아래와 같은 명령으로  soname을 지정할 수 있다.

gcc –shared –Wl,-soname libMyLibrary.so.1 –o libMyLibrary.so.1.2.3 MyLibrary.o

so뒤에 오는 첫번째 숫자는 라이브러리의 Major version number로 일반적으로 호환성이 변경되는 경우에 증가시킨다. 이렇게 라이브러리를 빌드하고 또 이 라이브러리를 사용하는 프로그램을 빌드하면 해당 프로그램 실행 시 로더에 의해서 soname을 가진 파일을 라이브러리 경로에서 찾게 된다. 즉 프로그램이 실행될 때에는 soname을 가진 라이브러리 파일이 필요하다. 크로스 컴파일을 하는 환경에서는 빌드 시에는 soname을 가진 파일이 아닌 링커이름을 가지는 파일(일반적으로 xxx.so로 끝나는 파일)이 필요하고 실행시에는 soname을 가지는 라이브러리(혹은 이에 대한 심볼릭 링크 )가 필요한 것이다.

라이브러리 full name에서 두번째 숫자는 라이브러리의 minor version number로 호환성에는 변경이 없지만 새로운 함수등이 추가되는 경우에 변경되며, 세번째 자리는 release 버전으로 버그 수정 등으로 라이브러리가 새로 릴리즈되는 경우에 변경된다.

따라서 크로스 컴파일 환경에서, 호스트에서 공유 라이브러리 libMyLibrary.so.1.2.3 를 만들어 타겟 시스템에 넣을 경우 타켓 시스템에는 아래와 같이 soft link file을 만들어 soname을 가진 파일을 만들어야 한다.

ln –s libMyLibrary.so.1.2.3 libMyLibrary.so.1
or
mv libMyLibrary.so.1.2.3 libMyLibrary.so.1


또한 해당 라이브러리를 사용하여 프로그램을 만드는 모든 개발자는 자신의 빌드 환경에 아래와 같이 공유 라이브러리가 링커 이름을 가지도록 설정하여야 한다. (즉 .so.1 파일은 호스트(빌드)시스템에서는 필요 없다)

ln –s libMyLibrary.so.1.2.3 libMyLibrary.so
or
mv libMyLibrary.so.1.2.3 libMyLibrary.so

특정 라이브러리의 soname을 확인하기 위해서는 아래와 같은 명령을 사용할 수 있다.

objdump -p libMyLibrary.so.1.2.3 | grep SONAME

더 자세한 내용은...
http://wiki.kldp.org/wiki.php/DocbookSgml/Program-Library-HOWTO#DL-LIBRARIES

댓글 없음: