Kaynakları kaynaktan derlemeyi öğrenme (Unix / Linux / OSX'te)


47

Yazılımları paketlerden (MacPorts / apt-get) mümkün olan yerlerde kurarken, kendimi sık sık paketleri kaynaktan derlemeye ihtiyaç duyuyorum. ./configure && make && sudo make installgenellikle yeterlidir, ancak bazen çalışmaz - ve çalışmadığında sık sık takılıyorum. Bu neredeyse her zaman bir şekilde diğer kütüphane bağımlılıkları ile ilgilidir.

Aşağıdakileri öğrenmek istiyorum:

  • Hangi argümanlara geçeceğimi nasıl bulurum ./configure?
  • Paylaşılan kütüphaneler OS X / Linux altında nasıl çalışır - dosya sisteminde yaşadıkları, ./configure && makeonları nasıl buldukları, birbirleriyle bağlantı kurduklarında ne oldukları
  • Paylaşılan ve statik olarak bağlantılı bir kitaplık arasındaki gerçek farklar nelerdir? Neden her şeyi statik olarak bağlayamıyorum (bugünlerde RAM ve disk alanı ucuz) ve bu nedenle garip kütüphane sürüm çakışmalarından kaçınıyorum.
  • Hangi kitaplıkları yüklediğimi ve hangi sürümleri nasıl bulabilirim?
  • Normal sistemimi bozmadan bir kütüphanenin birden fazla sürümünü nasıl kurabilirim?
  • Ben ise am aksi paketleri kullanılarak yönetilen bir sistem üzerinde kaynağından şeyler yüklemeden, bunu yaparken en temiz yolu nedir?
  • Bir şeyi kaynağından doğru bir şekilde derlemeyi başardığımı varsayarsak, diğer insanların aynı çemberin içinden atlamak zorunda kalmayacak şekilde nasıl paketleyebilirim? Özellikle OS X’de ....
  • Bu işte başarılı olmak için ustalaşmam gereken komut satırı araçları nelerdir? Otool, pkg-config vb. Gibi şeyler

Buraya biraz zaman ve çaba harcamak istiyorum - yukarıdaki sorulara doğrudan cevap vermek istemiyorum, daha çok okuyabileceğim kitaplar / öğreticiler / Sıkça Sorulan Sorular hakkında tavsiyeler almak istiyorum. gerçekte neler olup bittiğini anlamam ve bu yüzden sorunları kendi başıma çözmem gerekiyor.

Yanıtlar:


40

Her şeyi doğrudan yanıtladığım için özür dilerim, ancak yararlı öğreticiler, sık sorulan sorular, vb.

1. ./configure öğesine hangi argümanları ileteceğimi nasıl bulurum?

Gerçekten pratik yap. Otomatik araçlar tutarlı olduğu için yeterince kolaydır. Fakat cmake veya custom scriptler kullanan birçok şey var. Genel olarak, yapılandırmak için herhangi bir şey iletmek zorunda kalmamalısınız, sisteminizin foo-tool yapıp yapamayacağını anlamalıdır.

Yapılandırma ve GNU araçları, bağımlılıklar için /, / usr ve / usr / local ifadelerini kullanır. Başka bir yere yüklerseniz (bağımlılık MacPorts veya Fink tarafından kurulursa işleri acı verici yapar), GNU araçlarının bu bağımlılıkları bulmasına yardımcı olmak için kabuğun ortamını yapılandırmak veya değiştirmek için bir bayrak iletmeniz gerekir.

2. Paylaşılan kütüphaneler OS X / Linux altında nasıl çalışırlar - dosya sisteminde yaşadıkları yer, ./configure && onları nasıl bulur, bağlandıklarında ne olur?

Linux'ta, dinamik bağlayıcının bulabileceği bir yola kurulmaları gerekir, bu LD_LIBRARY_PATHortam değişkeni ve /etc/ld.conf içeriği ile tanımlanır . Mac'te, hemen hemen her zaman çoğu açık kaynaklı yazılım için aynıdır (bir Xcode Projesi olmadığı sürece). Env değişkeni hariç DYLD_LIBRARY_PATH.

Bağlayıcının kitaplıkları aradığı varsayılan bir yol vardır. Bu / lib: / usr / lib: / usr / yerel / lib

Bunu, CPATH değişkenini veya CFLAGS veya herhangi bir sayıda başka ortam değişkenini gerçekten (uygun şekilde karmaşık) kullanarak tamamlayabilirsiniz. CFLAGS'a şöyle bir öneriyorum:

CFLAGS ihracat = "$ CFLAGS -L / yeni / yol"

-L parametresi bağlantı yoluna ekler.

Modern şeyler pkg-config aracını kullanır. Yüklediğiniz Modern sayfalar ayrıca kitaplığı, nerede olduğunu ve nasıl bağlanacağını açıklayan bir .pc dosyası yükler. Bu hayatı kolaylaştırır. Ancak OS X 10.5 ile gelmiyor, bu yüzden onu da yüklemeniz gerekecek. Ayrıca pek çok temel görev desteklemiyor.

Bağlama eylemi sadece "çalışma zamanında bu işlevi çöz" dir, gerçekten büyük bir string tablodur.

3. Paylaşılan ve statik olarak birbirine bağlı bir kütüphane arasındaki gerçek farklar nelerdir? Neden her şeyi statik olarak bağlayamıyorum (bugünlerde RAM ve disk alanı ucuz) ve bu nedenle garip kütüphane sürüm çakışmalarından kaçınıyorum.

Statik bir kütüphane dosyasına bağlandığınızda, kod uygulamanızın bir parçası haline gelir. Bu kütüphane için dev bir .c dosyası olsaydı ve uygulamanıza derlediyseniz.

Dinamik kitaplıklar aynı koda sahiptir, ancak uygulama çalıştırıldığında, kod uygulama zamanında uygulamaya yüklenir (basitleştirilmiş açıklama).

Her şeyi statik olarak bağlayabilirsiniz, ancak, ne yazık ki herhangi bir yapı sistemi bunu kolaylaştırır. Yapı sistem dosyalarını manuel olarak düzenlemeniz gerekir (örneğin, Makefile.am veya CMakeLists.txt). Bununla birlikte, farklı kütüphanelerin sürümlerini gerektiren şeyleri düzenli olarak kurarsanız ve paralel olarak kurulum bağımlılıkları buluyorsanız, bu muhtemelen öğrenmeye değerdir.

İşin püf noktası bağlantı çizgisini -lfoo'dan -l / path / 'e / static / foo.a olarak değiştirmektir.

Muhtemelen bulabilir ve değiştirebilirsiniz. Daha sonra aracın ldd foo veya otool -L foo kullanarak .so veya dylib ile bağlantısı olmadığını kontrol edin.

Başka bir sorun, tüm kütüphanelerin statik kütüphaneleri derlememesidir. Bir çoğu var. Ancak daha sonra MacPorts veya Debian gönderilmemeye karar vermiş olabilir.

4. Hangi kütüphaneleri kurduğumu ve hangi versiyonları olduğunu nasıl öğrenebilirim?

Bu kütüphaneler için pkg-config dosyalarınız varsa, bu kolaydır:

pkg-config - list-all

Aksi takdirde, genellikle kolayca yapamazsınız. Dylib, kütüphanenin sürümüyle aynı olan bir soname (yani foo.0.1.dylib, soname 0.1'dir) içerebilir. Ancak bu gerekli değildir. Soname, bir ikili hesaplanabilirlik özelliğidir, kütüphanedeki işlevlerin biçimini değiştirirseniz, soname'nin büyük bölümünü çarpmanız gerekir. Yani örneğin alabilirsiniz. 2.0 kitaplığı için sürüm 14.0.5 soname. Bu yaygın olmasa da.

Bu tür bir şey yüzünden hayal kırıklığına uğradım ve Mac için bunun için bir çözüm geliştirdim ve bundan sonra konuşacağım.

5. Normal sistemimi bozmadan bir kütüphanenin birden fazla sürümünü nasıl kurabilirim?

Buna benim çözümüm burada: http://github.com/mxcl/homebrew/

Kaynaktan yüklemeyi seviyorum ve bunu kolaylaştıran bir araç istedim ancak bazı paket yönetimi ile. Yani Homebrew ile yapıyorum, örneğin. Kendimi kaynağından al, ancak özel bir önek yüklediğine emin ol:

/usr/local/Cellar/wget/1.1.4

Daha sonra hepsini / usr / local ile ilişkilendirmek için homebrew aracını kullanıyorum, bu yüzden hala / usr / local / bin / wget ve /usr/local/lib/libwget.dylib var.

Daha sonra farklı bir wget sürümüne ihtiyacım olursa paralel olarak yükleyebilir ve / usr / local tree ile bağlantılı sürümü değiştirebilirim.

6. Paketleri kullanarak paketleri başka kaynaklardan yönetilen bir sisteme yüklüyorsam, yapmanın en temiz yolu nedir?

Homebrew yolunun en temiz olduğuna inanıyorum, öyleyse kullanın veya eşdeğerini yapın. / Usr / local / pkgs / name / version'a yükleyin ve sembolik bağlantı kurun veya gerisini içeri sabitleyin.

/ Usr / local komutunu kullanın. Var olan her derleme aracı, bağımlılıkları ve başlıkları arar. Hayatın çok daha kolay olacak .

7. Bir şeyi kaynağından doğru derlemeyi başardığımı varsayarsak, diğer insanların aynı çemberin içinden atlamak zorunda kalmayacak şekilde nasıl paketleyebilirim? Özellikle OS X’de ....

Bağımlılığı yoksa, derleme dizinini düzenleyebilir ve daha sonra "make install" yapabilecek başka birine verebilirsiniz. Ancak bunu yalnızca OS X'in aynı sürümleri için güvenilir bir şekilde yapabilirsiniz. Linux'ta muhtemelen aynı Çekirdek sürümü ve libc küçük sürümüyle benzer Linux (örneğin Ubuntu) için çalışacaktır.

Unix'te ikili dosyaları dağıtmanın kolay olmasının nedeni ikili uyumluluktan kaynaklanmaktadır. GNU halkı ve diğerleri, ikili arayüzlerini sık sık değiştirir.

Temelde ikili dosyaları dağıtmayın. İşler muhtemelen çok garip şekillerde kırılacak.

Mac'te, en iyi seçenek bir macports paketi yapmaktır. Herkes macport kullanır. Linux'ta pek çok farklı yapı sistemi ve kombinasyonu var, garip bir yapılandırmada x aracını nasıl oluşturduğunuza dair bir blog yazısı yazmaktan daha iyi bir tavsiye olduğunu sanmıyorum.

Bir paket açıklaması yaparsanız (macports veya homebrew için) o zaman herkes bu paketi kurabilir ve bağımlılık sorunlarını da çözer. Bununla birlikte, bu genellikle kolay değildir ve ana macports ağacında macports tarifinizi almak da kolay değildir. Ayrıca macport'lar egzotik kurulum tiplerini desteklemiyor, tüm paketler için bir seçenek sunuyor.

Homebrew ile gelecekteki hedeflerimden biri, bir web sitesindeki bir linke tıklamayı mümkün kılmaktır (örn. Homebrew: // blah ve bu Ruby betiğini indirecek, bu paket için depsleri kuracak ve sonra uygulamayı oluşturacaksınız. Ama evet, Yapmamıştım, ama seçtiğim tasarım dikkate alındığında çok aldatıcı değil.

8. Bu işte başarılı olmak için ustalaşmam gereken komut satırı araçları nelerdir? Otool, pkg-config vb. Gibi şeyler

otool daha sonra gerçekten kullanışlıdır. Bu, dahili ikilinin neye bağlı olduğunu gösterir. Yapmanız gereken bir aracın bağımlılıklarını bulduğunuzda, işe yaramaz. Aynı şey, kullanmadan önce bağımlılığı daha önce kurduğunuz için pkg-config için de geçerlidir.

Takım zincirim, README ve INSTALL dosyalarını okumak ve configure --help yapmaktır. Aklı başında olup olmadığını kontrol etmek için derleme çıktısını izleyin. Yapı hatalarını çözümleyin. Belki gelecekte, serverfault'a sor :)


2
İlginçtir, Homebrew Portage'a (Gentoo Linux'un paket yöneticisi) çok benziyor. Güzel bir iş parçası gibi geliyor.
David Z

12

Bu çok büyük bir konudur, bu nedenle Linux'ta paylaşılan kütüphanelerle başlayalım (Linux'ta ELF ve OS X'te Mach-O), Ulrich Drepper, Linux'taki paylaşılan kütüphanelerin bazı tarihlerini kapsayan DSO'ları (dinamik paylaşılan nesneler) yazmak için iyi bir giriş yapmıştır. neden önemli olduklarını içeren

Ulrich ayrıca, statik bağlantının neden zararlı olarak değerlendirildiğini , buradaki önemli noktalardan birinin güvenlik güncellemeleri olduğunu da açıklıyor . Geniş kapsamlı statik olarak bağlanmış olan ortak bir kütüphanede (örneğin zlib) arabellek taşması dağıtımlar için büyük bir ek yüke neden olabilir - bu, zlib 1.1.3 ( Red Hat danışmanlığı ) ile ortaya çıkmıştır.

ELF

Bağlayıcı ld.so manuel sayfa

man ld.so 

Çalışma zamanı dinamik bağlantısına dahil olan temel yolları ve dosyaları açıklar. Modern Linux sistemlerinde /etc/ld.so.conf.d/ aracılığıyla eklenmiş ve genellikle /etc/ld.so.conf içinde yer alan bir glob aracılığıyla eklenmiş yollar göreceksiniz.

Ld.so yapılandırmanız aracılığıyla dinamik olarak nelerin mevcut olduğunu görmek istiyorsanız,

ldconfig -v -N -X

DSO'yu okumak, bu ilkelerin OS X'teki Mach-O'ya nasıl uygulandığını anlayabilmeniz için size iyi bir temel bilgi seviyesi sağlamalıdır.

Maço

OS X'te ikili format Mach-O'dur. Bağlayıcı için yerel sistem dokümantasyonu

man dyld

Mach biçimi belgeleri Apple edinilebilir

UNIX oluşturma araçları

Ortak configure, make, make installsüreç genellikle vardır GNU autotools tarafından sağlanmaktadır çevrimiçi kitap olduğunu kapakları yapılandırmak / yapı bölünmüş ve GNU toolchain tarihinin bazılarıdır. Autoconf , hedef derleme sistemindeki özellik kullanılabilirliğini belirlemek için testler kullanır, bunu yönlendirmek için M4 makro dilini kullanır . Automake temelde Makefiles için şablon oluşturuyor, şablon genellikle Makefile.am olarak adlandırılan ve autoconf çıktısının bir Makefile'a dönüştürüldüğü Makefile.am olarak adlandırılıyor.

GNU merhaba programı GNU toolchain anlamak için iyi bir örnek olarak görür - ve manuel Autotools belgeleri içerir.


10

Simon! Ben nasıl hissettiğini biliyorum; Ben de Linux öğrenmenin bu kısmı ile mücadele ettim. Kendi deneyimlerime dayanarak, hitap ettiğiniz bazı öğeler hakkında bir öğretici yazı yazdım (çoğunlukla kendim için bir referans!): Http://easyaspy.blogspot.com/2008/12/buildinginstalling-application-from.html . Python uygulamalarının ne kadar basit bir kurulum / kurulum yapılacağı hakkındaki notumu takdir edersiniz :)

Umarım bu yardımcı olur! Ve mutlu derleme.

Tim Jones


Ubuntu Linux'ta kaynaktan uygulama yükleme / yükleme

Ubuntu depoları harika uygulamalarla doluyken, bir zamanlar veya başka bir yerde, depolarda bulunmayan (veya bir Debian paketine sahip olmayan) "olması gereken" aracına rastlamak zorundasınız. depolarda daha yeni sürüm. Ne yaparsın? Peki, uygulamayı kaynaktan derlemelisin! Endişelenme, bu göründüğü kadar karmaşık değil. Sıra dışı bir amatör olmaktan deneyimlerime dayanan bazı ipuçları! (Bu örnek için Ubuntu kullanırken, genel kavramlar, Fedora ve hatta Windows'daki Cygwin platformları gibi çoğu Unix / Linux dağıtımına uygulanabilir olmalıdır.)

Temel uygulama süreci (derleme) çoğu kaynaktan bu uygulama takip eder: configure -> compile -> install. Bunları yapmak için tipik Unix / Linux komutları: config-> make-> make install. Bazı durumlarda, bunların hepsinin tek bir komutta birleştirilebileceğini gösteren web sayfalarını bile bulabilirsiniz:

$ config && make && make install

Elbette bu komut, bu adımların hiçbirinde sorun olmadığını varsayar. Eğlencenin geldiği yer burası!

Başlamak

Sisteminizde önce kaynağından bir uygulama derlenmiş değil, muhtemelen gibi bazı genel geliştirme araçları ile kurmak gerekir gccderleyici paketi, bazı genel başlık dosyaları (çoktan yazıldı kod olarak düşünmek yüklediğiniz program tarafından kullanılan bir başkası tarafından) ve make aracı. Neyse ki, Ubuntu'da build-essentialbunu yükleyecek bir metapaket var . Yüklemek için (veya zaten sahip olduğundan emin olun!) Terminalde şu komutu çalıştırın:

$ sudo apt-get install build-essential

Artık temel kuruma sahip olduğunuza, uygulama kaynak dosyalarını indirin ve bunları "giriş" dizininiz gibi okuma / yazma izninizin olduğu bir dizine kaydedin. Tipik olarak, bunlar ya .tar.gzda dosya uzantısına sahip bir arşiv dosyasında olacaktır .tar.bz2. .tarBasitçe bir göreli dizin yapısını korur dosyaların gruplama bir "kaset arşivi", anlamına gelir. .gzPopüler bir Unix / Linux sıkıştırma biçimidir gzip (GNU zip), kısaltmasıdır. Benzer şekilde, .bz2gzip'ten daha yüksek sıkıştırma (daha küçük sıkıştırılmış dosya boyutu) sağlayan daha yeni bir sıkıştırma formatı olan bzip2'nin standları.

Kaynak dosyayı indirdikten sonra, bir terminal penceresi açın (Ubuntu menüsünden System Terminal) ve dosyanızı kaydettiğiniz dizine geçin. ( ~/downloadBu örnekte kullanacağım . İşte, '~' "home" dizininize bir kısayol.) Dosyaları indirilen arşiv dosyasından çıkarmak için tar komutunu kullanın:

Dosyanız bir gzip arşivi ise (örneğin, biterse .tar.gz), aşağıdaki komutu kullanın:

            $ tar -zxvf filename.tar.gz

Dosyanız bir bzip2 arşivi ise (örneğin, biterse .tar.bz2), aşağıdaki komutu kullanın:

            $ tar -jxvf filename.tar.gz

İpucu: Arşiv çıkarmak için tüm komut satırı anahtarlarını hatırlamak istemiyorsanız, bu yardımcı programlardan birini (veya her ikisini) almanızı öneririz: dtrx (en sevdiğim!) Veya deco (daha popüler). Bu yardımcı programlardan herhangi biriyle, yardımcı programın adını (dtrx veya deco) ve dosya adını girersiniz, geri kalan her şeyi yapar. Bunların her ikisi de, karşılaşmanız muhtemel olan tüm arşiv formatlarının çoğunun nasıl kullanılacağını "bilir".

Kaynağından oluştururken, karşılaşmanız muhtemel olan iki yaygın hata türü vardır:

  1. Kurulumunuza özgü bir makefile oluşturmak için konfigürasyon betiğini (genellikle config veya configure olarak adlandırılır) çalıştırdığınızda yapılandırma hataları oluşur.
  2. Make komutunu çalıştırdığınızda (makefile oluşturulduktan sonra) derleyici hataları oluşur ve derleyici ihtiyacı olan bazı kodları bulamaz.

Bunların her birine bakacağız ve nasıl çözüleceğini tartışacağız.

Yapılandırma ve Yapılandırma Hataları

Kaynak kod arşiv dosyasını çıkardıktan sonra, terminalde, çıkarılan dosyaları içeren dizine geçmelisiniz. Genelde, bu dizin adı, dosyanın adıyla aynı olur ( .tar.gzveya .tar.bz2uzantısı olmadan ). Ancak, bazen dizin adı herhangi bir sürüm bilgisi olmadan uygulamanın adıdır.

Kaynak dizinde bir READMEdosyayı ve / veya dosyayı arayın INSTALL(veya benzer adlara sahip bir şey). Bu dosyalar tipik olarak, bağımlılıklar hakkında bilgiler de dahil olmak üzere uygulamanın nasıl derleneceği / derleneceği ve yükleneceği hakkında faydalı bilgiler içerir. "Bağımlılıklar", başarılı bir şekilde derlenmesi gereken diğer bileşenler veya kütüphaneler için süslü bir addır.

Okumak bıraktıktan sonra READMEve / veya INSTALLbir yürütülebilir için göz (umarım uygulama için tüm ilgili çevrimiçi belgelerine bakıp,) dosyası adlı dosya (dosya üzerinde "x" izni setine sahiptir) configveya configure. Bazen dosyanın .sh(örneğin, config.sh) gibi bir uzantısı olabilir . Bu genellikle derlemek için bir "aklı başında" ortamınız olduğunu doğrulamak için diğer bazı yardımcı programları çalıştıran bir kabuk betiğidir. Başka bir deyişle, ihtiyacınız olan her şeyin kurulu olduğundan emin olmak için kontrol edecektir.

İpucu: Bu bir yapılandırma dosyası yerine Python tabanlı bir uygulama ise, adlı bir dosya bulmalısınız setup.py. Python uygulamaları genellikle kurulumu çok basittir. Bu uygulamayı kurmak için root olarak (örneğin, Ubuntu altındaki aşağıdaki komutun önüne sudo koyun) bu komutu çalıştırın:

    $ python setup.py install

Yapmanız gereken tek şey bu olmalı. Bu eğitimin geri kalanını atlayabilir ve uygulamanızı kullanmaya ve keyfini çıkarmaya doğrudan devam edebilirsiniz.

Yapılandırma komut dosyasını terminalde çalıştırın. Genelde, yapılandırma komut dosyanızı normal kullanıcı hesabınızla çalıştırabilirsiniz (ve gerekir!).

$ ./config

Komut size ne yaptığı hakkında bir fikir vermek için bazı mesajlar gösterecektir. Genellikle, komut dosyası başarılı veya başarısız olup olmadığını ve başarısız olursa, hatanın nedeni hakkında bazı bilgiler verir. Herhangi bir hata mesajı almazsanız, genellikle her şeyin yolunda gittiğini varsayabilirsiniz.

Bir yapılandırma betiğine benzeyen bir komut dosyası bulamazsanız, bu genellikle uygulamanın çok basit olduğu ve platformdan bağımsız olduğu anlamına gelir. Bu, sağlanan derleme adımına atlayabileceğiniz anlamına gelir, çünkü sağlanan Makefileherhangi bir sistemde çalışmalıdır.

Bir örnek

Bu derste, başvurunuzu oluştururken karşılaşabileceğiniz hata türlerine örnek olarak Newsbeuter adlı metin tabanlı RSS okuyucuyu kullanacağım. Newsbeuter için, yapılandırma betiğinin adı config.sh. Sistemimde çalıştırdığımda config.shaşağıdaki hatalar meydana geliyor:

tester@sitlabcpu22:~/download/newsbeuter-1.3$ ./config.sh
Checking for package sqlite3... not found

You need package sqlite3 in order to compile this program.
Please make sure it is installed.

Biraz araştırma yaptıktan sonra, sqlite3uygulamanın kurulduğunu öğrendim . Ancak, kaynaktan inşa etmeye çalıştığım için, bu config.shaslında aradığı şey için geliştirme kütüphaneleri (başlıkları) sqlite3. Ubuntu'da çoğu paketin içinde biten bir ilişkili geliştirme karşı paketi vardır -dev. (Fedora gibi diğer platformlar genellikle -develgeliştirme paketleri için bir paket soneki kullanır .)

sqlite3Geliştirme paketi için uygun paketi bulmak için , apt-cacheyardımcı programı Ubuntu'da (ve benzer şekilde, yumFedora'daki yardımcı programı) kullanabiliriz:

tester@sitlabcpu22:~/download/newsbeuter-1.3$ sudo apt-cache search sqlite

Bu komut oldukça büyük bir sonuç listesi döndürür, bu nedenle hangisinin uygun paket olduğunu belirlemek için bir takım dedektiflik çalışmaları yapmalıyız. Bu durumda uygun paket olduğu ortaya çıkıyor libsqlite3-dev. Bazen aradığımız libpaketin aynı paket adı yerine öneki olacağına dikkat edin -dev. Bunun nedeni, bazen sadece birçok farklı uygulama tarafından kullanılabilecek paylaşılan bir kütüphane arıyoruz. Yüklemek için libsqlite3-dev, terminaldeki tipik apt-get install komutunu çalıştırın:

tester@sitlabcpu22:~/download/newsbeuter-1.3$ sudo apt-get install libsqlite3-dev

Şimdi, config.shbu bağımlılık problemini çözdüğümüzden ve daha fazla bağımlılık problemimiz olmadığından emin olmak için tekrar koşmalıyız. (Burada göstermeyeceğim halde, Newsbeuter durumunda, libcurl4-openssl-devpaketi de kurmak zorunda kaldım .) Ayrıca, bir geliştirme paketi (gibi libsqlite3-dev) yüklerseniz ve ilişkili uygulama paketi de (örneğin, sqlite3) değil önceden kuruluysa, çoğu sistem ilişkili uygulama paketini aynı anda otomatik olarak kurar.

Yapılandırma başarılı bir şekilde çalıştığında, sonuç bir veya daha fazla make dosyası yaratacağı şeklinde olacaktır. Bu dosyalar genellikle adlandırılır Makefile(Unix / Linux'ta dosya adı durumunun önemli olduğunu unutmayın!). Derleme paketi src, vb. Gibi alt dizinler içeriyorsa, bu alt dizinlerin her biri bir de içerecektir Makefile.

Yapı ve Derleme Hataları

Şimdi, uygulamayı derlemeye hazırız. Buna genellikle bina denir ve adı gerçek dünyadaki bir şeyi inşa etme sürecinden ödünç alınır. Tipik olarak çoklu kaynak kod dosyaları olan uygulamanın çeşitli "parçaları", toplam uygulamayı oluşturmak için bir araya getirilir. Make yardımcı programı, derleme işlemini yönetir ve işi gerçekten yapmak için derleyici ve bağlayıcı gibi diğer uygulamaları çağırır. Çoğu durumda, yapılandırmayı yaptığınız dizinden make (normal kullanıcı hesabınızla) yapmanız yeterlidir. (Qt kütüphanesiyle yazılmış uygulamaları derlemek gibi birkaç durumda, bunun yerine qmake gibi başka bir "sarmalayıcı" uygulaması çalıştırmanız gerekir. Yine, ayrıntılar için her zaman READMEve / veya INSTALLbelgeleri kontrol edin .)

Yukarıdaki yapılandırma komut dosyasında olduğu gibi, terminalde make (veya benzeri bir yardımcı program) çalıştırdığınızda, neyin yürütüldüğü ile ilgili herhangi bir uyarı ve hata ile ilgili bazı mesajlar görüntülenir. Genelde uygulamanın geliştiricileri için olduğu ve ihlal edilmekte olan bazı standart uygulamalar olduğunu söyledikleri için genellikle uyarıları yok sayabilirsiniz. Genellikle, bu uyarılar uygulama işlevini etkilemez. Öte yandan, derleyici hataları ile ilgilenilmesi gerekir. Newsbeuter ile koştuğum zaman, bir süre işler yolunda gitti, ama sonra bir hata yaptım:

tester@sitlabcpu22:~/download/newsbeuter-1.3$ make
...
c++ -ggdb -I/sw/include -I./include -I./stfl -I./filter -I. -I./xmlrss -Wall -Wextra -DLOCALEDIR=\"/usr/local/share/locale\" -o src/configparser.o -c src/configparser.cpp
c++ -ggdb -I/sw/include -I./include -I./stfl -I./filter -I. -I./xmlrss -Wall -Wextra -DLOCALEDIR=\"/usr/local/share/locale\" -o src/colormanager.o -c src/colormanager.cpp
In file included from ./include/pb_view.h:5,
from src/colormanager.cpp:4:
./include/stflpp.h:5:18: error: stfl.h: No such file or directory
In file included from ./include/pb_view.h:5,
from src/colormanager.cpp:4:
./include/stflpp.h:33: error: ISO C++ forbids declaration of \u2018stfl_form\u2019 with no type
./include/stflpp.h:33: error: expected \u2018;\u2019 before \u2018*\u2019 token
./include/stflpp.h:34: error: ISO C++ forbids declaration of \u2018stfl_ipool\u2019 with no type
./include/stflpp.h:34: error: expected \u2018;\u2019 before \u2018*\u2019 token
make: *** [src/colormanager.o] Error 1

Yapma işlemi, ilk hatayla karşılaşılır karşılaşmaz duracaktır. Derleyici hatalarının ele alınması bazen zor bir iş olabilir. Sorunla ilgili bazı ipuçlarının hatalarına bakmak zorundasınız. Tipik olarak, sorun, genellikle .hveya uzantısı olan bazı başlık dosyalarının .hppeksik olmasıdır. Yukarıdaki hatanın söz konusu olması durumunda, sorunun stfl.hüstbilgi dosyasının bulunamadığıdır (ya da olmalı!) . Bu örnekte gösterildiği gibi, hata mesajının ilk satırlarına bakmak ve sorunun nedenini bulmak için aşağıya inmek istersiniz.

Newsbeuter belgelerine baktıktan sonra (başlamadan önce yapmam gereken, ancak eğitimin bu bölümü çok anlamlı olmaz!), Bunun STFL adında bir 3. parti kütüphaneye ihtiyacı olduğunu buldum. Peki bu durumda ne yapacağız? Aslında, bu gerekli kütüphane için aynı işlemi tekrarlıyoruz: kitaplığı elde edin ve bunun için configure-build-install işlemini yürütün ve ardından istenen uygulamayı oluşturmaya devam edin. Örneğin, STFL durumunda, libncursesw5-devdüzgün bir şekilde yapılabilmesi için paketi kurmak zorunda kaldım . (Genellikle, başka bir gerekli uygulamayı yükledikten sonra orijinal uygulamamızdaki yapılandırma adımını yinelemek gerekli değildir, ancak hiçbir zaman da zarar vermez.)

STFL araç setini başarıyla kurduktan sonra Newsbeuter için make işlemi başarıyla gerçekleştirildi. Make işlemi tipik olarak bıraktığı yerden (hata noktasında) kalkar. Bu nedenle, başarılı bir şekilde derlenmiş herhangi bir dosya yeniden derlenmeyecektir. Her şeyi yeniden derlemek istiyorsanız, derlenmiş tüm nesneleri kaldırmak için hepsini temizle komutunu çalıştırabilir ve ardından yeniden çalıştırmayı çalıştırabilirsiniz.

yükleme

Derleme işlemi başarıyla tamamlandıktan sonra uygulamayı yüklemeye hazırsınız. Çoğu durumda, uygulamayı dosya sisteminin ortak alanlarına (örneğin, /usr/binveya /usr/share/bin, vb.) Yüklemek için , yüklemeyi root olarak çalıştırmanız gerekir. Kurulum gerçekten de tüm süreçteki en basit adımdır. Takmak için, terminal çalışmasına:

$ make install

Herhangi bir hata için bu işlemin çıktısını kontrol edin. Her şey başarılı olsaydı, terminaldeki komut ismini çalıştırabiliyor olmanız gerekiyordu. (Bir GUI uygulamasıysa, komut satırının sonuna & sonuna ekleyin veya uygulama çalışmayı bitirinceye kadar terminal oturumunu kullanamazsınız.)

Kaynaktan bir uygulama oluşturduğunuzda, genellikle Ubuntu'daki GUI menülerine bir simge veya kısayol eklemez. Bunu manuel olarak eklemeniz gerekecek.

Ve bu temelde, yinelemeli olsa da, Ubuntu'da bir kaynaktan bir uygulama oluşturma ve yükleme sürecidir. Bunu birkaç kez yaptıktan sonra, sizin için ikinci doğa olacak!


Tim, eğitimini okumak isterdim, ama gönderdiğin link çalışmıyor.
gareth_bowles

6

Peki, ./configure --help, GNU autotools tarafından oluşturulan configure dosyaları için size çok fazla bilgi verecektir. Çoğu, özellikleri etkinleştirmeksizin, --with / - ile gelir (bunlar, kütüphaneyi nerede bulacağını söylemek için "paylaşılan" gibi ekstra bir parametre alabilir).

Diğer önemli olanlar ise --prefix (varsayılan olarak / usr / local / çoğu zaman) ve nereye yükleneceğini söyler (eğer paketler oluşturuyorsanız bunu genellikle --prefix = / usr veya belki --prefix olarak istersiniz) = / opt / YourPackage).

Linux'ta, / lib, / usr / lib ve / usr / local / lib genellikle gcc'mi arar ve ldconfig'in varsayılan yapılandırmasına dahil edilir. İyi bir nedeniniz yoksa, kütüphanelerinizi istediğiniz yer burasıdır. Bununla birlikte /etc/ld.so.conf fazladan girişleri listeleyebilir.

"gcc -l" komutunu çalıştırmayı deneyerek ve hataları olup olmadığına bakarak bunları yapılandırın ve bulun. Aramaya ekstra yollar eklemek için CFLAGS parametrenize "-L" ekleyebilirsiniz.

Yüklü birden çok sürümünüz olabilir ve daha eski bir sürüme bağlı olan yazılım buna karşı bağlı kalır (Linux'ta bağlamayı bulmak için ldd'yi çalıştırın), ancak yeni derlemeler genellikle sisteminizdeki dinamik bir kitaplığın en son sürümünü hedefler.

Çoğu yazılım, özellikle libtool kullanıyorsa, dinamik libs'ler olduğunu varsayar;

ls -l kurulu kütüphaneleri bulmak için en iyi bahis.

Ve burası bilgisiz olduğum yer; paketlerle nasıl iyi oynanır: bilmiyorum. Mümkün olduğunda, sorunu önlemek için bir paketin içine şeyler sarmaya çalışıyorum.


4

"./Configure öğesine hangi argümanları ileteceğimi nasıl bulurum?"

genellikle: ./configure - help size orada ne istediğinizi söyler.

"Hangi kitaplıkları yüklediğimi ve hangi sürümleri nasıl yükleyebilirim?"

Bu sisteme bağlıdır. Bunun bir yolu, find /|grep libname|lessgenel olarak kütüphane dosyalarının dosya adındaki sürüme sahip olmalarıdır.

"Normal sistemimi bozmadan bir kütüphanenin birden fazla sürümünü nasıl kurabilirim?"

Yine, sisteme ve kütüphaneye bağlıdır. sudo make altinstallsizin için sürümlü bir ad oluşturacak. Kütüphane dosyaları genellikle kendilerini sürümleri. Ancak aklınızda bulundurun; sürümleri genellikle "normalize" bir isim için sembolik bağlantılar oluşturduğundan, bu işleri bozabilir.

"Paketten paketleri kullanarak yönetilen bir sisteme bir şey yüklüyorsam, bunu yapmanın en temiz yolu nedir?"

.Pconfix parametrelerini ./configure içinde kullanmak ve bir yere koymak /opt, izlenmesi iyi bir uygulamadır.

Feragatname: Hiçbir şekilde uzman değilim, ancak cmd hattından 5 yıldan beri linux kullanıyorum (gevşek yazılım, CentOS, redhat, ubuntu, diğerlerini yanlış ve OS X).


4

Sorunuzun bir kısmını cevaplamak için geçen gün hangi kütüphaneleri kurduğunuzu ve sürümleri görmenin iyi bir yolunu buldum (Bu Linux Debian'da, bu yüzden diğer sürümlerle de çalışmalı).

dpkg --list

Böyle bir çıktının alındığı uzun bir liste olmalı.

ii  libssl0.9.8    0.9.8c-4etch5  SSL shared libraries
ii  libssp0        4.1.1-21       GCC stack smashing protection library
ii  libstdc++5     3.3.6-15       The GNU Standard C++ Library v3
ii  libstdc++5-3.3 3.3.6-15       The GNU Standard C++ Library v3 (development
ii  libstdc++6     4.1.1-21       The GNU Standard C++ Library v3

4

Simon,

1.) ./configure --help iyi miktarda bilgi sağlar. Kontrol etmenizi öneririm. Genellikle uygun olduğunda statik / dinamik olarak bağlanmış kitaplıkları derleme seçenekleri vardır.

2.) Kütüphaneciler dinamik linker yolunda yaşarlar. Bu genellikle /etc/ld.so.conf dosyasında ayarlanır. Bağlayıcı, bulunan ilk ile eşleşen PATH ortam değişkeni gibi, uygun kitaplıkları arar.

3.) Bu genellikle bir kütüphane sürümü değiştiğinde her şeyi yeniden derlemeniz gerektiği için sorunlara yol açar. Bazı araştırmalar yaparsanız, muhtemelen statik olarak bağlamanın kötü bir fikir olmasının nedenleri hakkında bilgi bulabilirsiniz. O kadar uzun zamandır yapmadım burada gerçekten ayrıntılı olarak çalışamıyorum.

4.) Bu biraz zor. Kesinlikle emin olmak için kütüphane yolunu kontrol etmeniz gerekir. Kütüphanelerde genellikle kurulu sürümün sembolik bir bağlantısı vardır.

örneğin libssh2.so.1 -> libssh2.so.1.0.0

Genellikle insanlar kurdukları kütüphaneleri ve programları kendi debian paketlerini alarak ya da başka bir teknik kullanarak yönetir. Ben istifleme kullanarak yüklü yazılım (yönetmek http://www.gnu.org/software/stow/ çok basit ve sembolik bağlantıları kullanarak kütüphane yükler). Bir deb / rpm paketi kurmak / test etmek zorunda olmadığım için daha kolay buluyorum.

5.) Çok sayıda kütüphane sürümü normal olarak kütüphane dizinlerine kurulabilir. Yürütülebilir dosyalara bağlanan kütüphaneler, bağlandıkları sürümlere bağlı kalacaktır. Bir çalıştırılabilir dosyada ldd çalıştırmak, çalıştırılabilir dosyanın bağlandığı kütüphaneleri size söyleyecektir.

6.) Daha önce de bahsettiğim gibi, kendi debian paketlerinizi almak veya stow kullanmak muhtemelen en temiz çözümdür.

7.) Mac OSX için gerçekten konuşamam ama Linux için dağıtımın paketleme sistemi en iyi yoldur.

8.) Muhtemelen, ldd kullanarak ve bir şeyin hangi versiyona bağlı olduğunu veya bir çalıştırılabilir dosyaya bağlı hangi kütüphanenin bulunamayacağını bulmak suretiyle çok fazla hayal kırıklığı giderilecektir. pkg-config size yalnızca yardımcı olacak, ancak onu kullanan yazılım için yardımcı olacaktır. Bugünlerde popüler olmasına rağmen, varsayılan autotools build sisteminin bir parçası değildir.


4

Statik kütüphaneler iyi bir fikir değildir - kütüphaneyi yükseltmeniz gerekiyorsa (örneğin bir güvenlik problemini çözmek için), her şeyi kütüphaneye bağımlı bir şekilde yeniden derlemeniz gerekir.

Sistemimi bozma potansiyeli olan "make install" fikrinden hoşlanmıyorum, ancak diğerlerinin söylediği gibi, /prefix komutunu başka bir yere kurmak yerine --prefix komutunu kullanmak yerine / usr / local dizinine yüklemek daha az acı verici. Bu yüzden, normal (ayrıcalıklı olmayan) kullanıcıma / usr / local'i boğdum. Bu şekilde "install install", önemli sistem dosyalarıyla uğraşmama garantilidir. (Bu kesinlikle çok kullanıcılı sistemlerde çalışmaz. Sanal sunucular için de mükemmeldir.)


4

Açıkça, sorular listenizde olmasa da, önsözünüzde bahsettiniz:

./configure && make && sudo make install genellikle yeterlidir, ancak bazen çalışmaz - ve çalışmadığında sık sık takılıyorum.

Debian veya Ubuntu'da takılıp kaldığımda, otomatik olarak, konfigüre edilemeyen dosyaları içeren paketleri içeren paketleri kuracak olan otomatik apt kullanacağım.

Görmek:

Kullanışlı bulabileceğiniz başka bir araç CheckInstall, make installkurulu paketler listenize yüklü uygulamaları ekler : https://help.ubuntu.com/community/CheckInstall


3

OS X için:

  • ./Configure öğesine hangi argümanları ileteceğimi nasıl bulurum?

./configure - yardım

  • Paylaşılan ve statik olarak bağlantılı bir kitaplık arasındaki gerçek farklar nelerdir? Neden her şeyi statik olarak bağlayamıyorum (bugünlerde RAM ve disk alanı ucuz) ve bu nedenle garip kütüphane sürüm çakışmalarından kaçınıyorum.

Paylaşılan kütüphaneleri kullanmak, onu kullanan her şeyi yeniden derlemeden kütüphaneyi yükseltmenize olanak sağlar.

  • Paylaşılan kütüphaneler OS X / Linux altında nasıl çalışırlar - dosya sisteminde yaşadıkları yer, nasıl.

Sistem kütüphaneleri / usr / lib içinde bulunur.

Derlediğiniz kitaplıklar / usr / local / lib dizininde (/ usr / local, / /.

Ortam değişkenleri DYLD_FALLBACK_LIBRARY_PATH ve LD_LIBRARY_PATH, hangi klasörlerin aranacağını belirtmenize izin verir, böylece / usr / local / lib listenin başında bulunmalıdır.

  • Normal sistemimi bozmadan bir kütüphanenin birden fazla sürümünü nasıl kurabilirim?

/ Usr / local dizinine her şeyi yükleyin - yukarıdaki ortam değişkenleriyle, / usr / local / lib içindeki sürüm, ortamınızdaki / usr / lib sürümüne göre önceliklidir.

  • Paketleri başka bir şekilde paketlerle yönetilen bir sisteme kaynaktan yüklüyorsam, bunu yapmanın en temiz yolu nedir?

/ Usr / local dizinine kurun. Ubuntu'da bir deb paketi oluşturmak için önce checkinstall'ı kullanmaya çalışıyorum.

  • Bir şeyi kaynağından doğru bir şekilde derlemeyi başardığımı varsayarsak, diğer insanların aynı çemberin içinden atlamak zorunda kalmayacak şekilde nasıl paketleyebilirim? Özellikle OS X’de ....

Derleme adımlarını bir blog yazısında belgeleyin diyorum.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.