From 906abf910c838f47e98a4bb6b97a3ff19dfd5238 Mon Sep 17 00:00:00 2001 From: Po Han Chen Date: Thu, 26 Mar 2026 14:53:31 +0800 Subject: [PATCH] handbook/zh-tw: rewrite linuxemu chapter translation Update to match current English version. Adds Rocky Linux, Debian/Ubuntu debootstrap sections. Removes outdated CentOS 6 references and manual kldload instructions. --- .../zh-tw/books/handbook/linuxemu/_index.adoc | 430 ++++++++++++++---- 1 file changed, 336 insertions(+), 94 deletions(-) diff --git a/documentation/content/zh-tw/books/handbook/linuxemu/_index.adoc b/documentation/content/zh-tw/books/handbook/linuxemu/_index.adoc index 5761e24d375d..70775cb40566 100644 --- a/documentation/content/zh-tw/books/handbook/linuxemu/_index.adoc +++ b/documentation/content/zh-tw/books/handbook/linuxemu/_index.adoc @@ -1,23 +1,25 @@ --- -title: 章 10. Linux® Binary 相容性 -part: 部 II. 一般作業 +title: Chapter 12. Linux Binary 相容性 +part: Part II. 常見工作 prev: books/handbook/printing -next: books/handbook/partiii +next: books/handbook/wine +description: FreeBSD 提供與 Linux 的 Binary 相容性,讓使用者不需修改 Binary 便能在 FreeBSD 系統上安裝與執行大多數 Linux Binary +tags: ["linux", "linuxulator", "emulation", "binary", "compatibility"] showBookMenu: true -weight: 13 +weight: 15 params: path: "/books/handbook/linuxemu/" --- [[linuxemu]] -= Linux(R) Binary 相容性 += Linux Binary 相容性 :doctype: book :toc: macro :toclevels: 1 :icons: font :sectnums: :sectnumlevels: 6 -:sectnumoffset: 10 +:sectnumoffset: 12 :partnums: :source-highlighter: rouge :experimental: @@ -50,91 +52,348 @@ endif::[] [[linuxemu-synopsis]] == 概述 -FreeBSD 提供 Linux(TM) Binary 的相容性,允許使用者在 FreeBSD 系統上不需要修改就可以安裝和執行大部份的 Linux(TM) Binary。 曾經有報告指出,在某些情況下,Linux(TM) Binary 在 FreeBSD 的表現比在 Linux(TM) 好。 +FreeBSD 提供**選用的** Linux(R) Binary 相容性,一般稱為 Linuxulator,讓使用者可以直接安裝並執行未經修改的 Linux Binary。 +此功能支援 x86(32 位元與 64 位元)以及 AArch64 架構。 +部分 Linux 專屬的作業系統功能尚未支援,主要集中在硬體相關或系統管理方面,例如 cgroups 或 namespaces。 -然而,部份特定在 Linux(TM) 作業系統上的功能在 FreeBSD 並沒有支援。例如,若 Linux(TM) Binary 過度的使用 i386(TM) 特定的呼叫,如啟動虛擬 8086 模式,會無法在 FreeBSD 執行。 +閱讀本章之前: -[NOTE] +* 需要瞭解如何安裝 crossref:ports[ports,第三方軟體]。 + +閱讀本章之後,您將瞭解: + +* 如何在 FreeBSD 系統上啟用 Linux Binary 相容性。 +* 如何安裝額外的 Linux 共用程式庫。 +* 如何在 FreeBSD 系統上安裝 Linux 應用程式。 +* FreeBSD 中 Linux 相容性的實作細節。 + +[[linuxemu-lbc-install]] +== 設定 Linux Binary 相容性 + +預設情況下,man:linux[4] Binary 相容性並未啟用。 + +若要在開機時啟用 Linux ABI,請執行以下指令: + +[.programlisting] +.... +# sysrc linux_enable="YES" +.... + +啟用後不需重新開機,執行以下指令即可立即啟動: + +[source,shell] +.... +# service linux start +.... + +靜態連結的 Linux Binary 到這一步就能運作了。 + +Linux 服務會載入必要的核心模組,並在 [.filename]#/compat/linux# 下掛載 Linux 應用程式所需的檔案系統。 +這些 Binary 的啟動方式與原生 FreeBSD Binary 相同,行為幾乎完全一致,也能以一般方式追蹤與除錯。 + +執行以下指令可以檢視 [.filename]#/compat/linux# 目前的內容: + +[source,shell] +.... +# ls -l /compat/linux/ +.... + +輸出應類似如下: + +[.programlisting] +.... +total 1 +dr-xr-xr-x 13 root wheel 512 Apr 11 19:12 dev +dr-xr-xr-x 1 root wheel 0 Apr 11 21:03 proc +dr-xr-xr-x 1 root wheel 0 Apr 11 21:03 sys +.... + +[[linux-userlands]] +== Linux Userland + +Linux 軟體要能運作,不只需要 ABI 層,還必須先安裝 Linux userland。 + +[TIP] ==== -FreeBSD 10.3 後支援 64 位元的 Linux(TM) Binary 相容性。 +如果您只是要執行 Port 套件集中已收錄的軟體,直接透過套件管理員安裝即可,man:pkg[8] 會自動配置所需的 Linux userland。 + +舉例來說,要安裝 Sublime Text 4 以及它相依的所有 Linux 程式庫,只要執行: + +[source,shell] +.... +# pkg install linux-sublime-text4 +.... ==== -讀完這章,您將了解: +[[linuxemu-rockylinux]] +=== 從 FreeBSD 套件安裝 Rocky Linux 基礎系統 -* 如何在 FreeBSD 系統啟用 Linux(TM) Binary 相容模式。 -* 如何安裝其他的 Linux(TM) 共用程式庫。 -* 如何在 FreeBSD 系統安裝 Linux(TM) 應用程式。 -* 在 FreeBSD 中 Linux(TM) 相容性的實作細節。 +執行以下指令安裝 Rocky Linux 9 userland: -在開始閱讀這章之前,您需要: +[source,shell] +.... +# pkg install linux_base-rl9 +.... -* 知道如何安裝 crossref:ports[ports,其他的第三方軟體]。 +package:emulators/linux_base-rl9[] 會將衍生自 Rocky Linux 9 的基礎系統安裝到 [.filename]#/compat/linux#。 -[[linuxemu-lbc-install]] -== 設定 Linux(TM) Binary 相容性 +安裝完成後,可以執行以下指令確認 Rocky Linux userland 已正確佈署: -Linux(TM) 程式庫預設並不會安裝,且並不會開啟 Linux(TM) Binary 相容性。 Linux(TM) 程式庫可以手動安裝或是從 FreeBSD Port 套件集安裝。 +[source,shell] +.... +# ls -l /compat/linux/ +.... + +輸出應類似如下: + +[.programlisting] +.... +total 36 +drwxr-xr-x 2 root wheel 512 Oct 9 17:28 afs +lrwxr-xr-x 1 root wheel 7 May 16 2022 bin -> usr/bin +drwxr-xr-x 3 root wheel 512 Oct 9 17:28 dev +drwxr-xr-x 24 root wheel 1536 Oct 9 17:28 etc +lrwxr-xr-x 1 root wheel 7 May 16 2022 lib -> usr/lib +lrwxr-xr-x 1 root wheel 9 May 16 2022 lib64 -> usr/lib64 +drwxr-xr-x 2 root wheel 512 Oct 9 17:28 opt +drwxr-xr-x 2 root wheel 512 Oct 9 17:28 proc +lrwxr-xr-x 1 root wheel 8 Oct 1 03:11 run -> /var/run +lrwxr-xr-x 1 root wheel 8 May 16 2022 sbin -> usr/sbin +drwxr-xr-x 2 root wheel 512 Oct 9 17:28 srv +drwxr-xr-x 2 root wheel 512 Oct 9 17:28 sys +drwxr-xr-x 8 root wheel 512 Oct 9 17:28 usr +drwxr-xr-x 16 root wheel 512 Oct 9 17:28 var +.... + +[[linuxemu-centos]] +=== 從 FreeBSD 套件安裝 CentOS 基礎系統 + +[WARNING] +==== +package:emulators/linux_base-c7[] 已隨上游專案一同被標記為棄用。 +這代表 package:emulators/linux_base-c7[] 將不再收到安全性更新。 +除非需要 32 位元相容性,否則建議改用 crossref:linuxemu[linuxemu-rockylinux, Rocky Linux 基礎系統]。 +==== + +執行以下指令安裝 CentOS userland: + +[source,shell] +.... +# pkg install linux_base-c7 +.... + +package:emulators/linux_base-c7[] 會將衍生自 CentOS 7 的基礎系統安裝到 [.filename]#/compat/linux#。 + +安裝完成後,可以執行以下指令確認 CentOS userland 已正確佈署: + +[source,shell] +.... +# ls -l /compat/linux/ +.... + +輸出應類似如下: -在嘗試編譯 Port 前,要載入 Linux(TM) 核心模組,否則編譯會失敗: +[.programlisting] +.... +total 30 +lrwxr-xr-x 1 root wheel 7 Apr 11 2018 bin -> usr/bin +drwxr-xr-x 13 root wheel 512 Apr 11 21:10 dev +drwxr-xr-x 25 root wheel 64 Apr 11 21:10 etc +lrwxr-xr-x 1 root wheel 7 Apr 11 2018 lib -> usr/lib +lrwxr-xr-x 1 root wheel 9 Apr 11 2018 lib64 -> usr/lib64 +drwxr-xr-x 2 root wheel 2 Apr 11 21:10 opt +dr-xr-xr-x 1 root wheel 0 Apr 11 21:25 proc +lrwxr-xr-x 1 root wheel 8 Feb 18 02:10 run -> /var/run +lrwxr-xr-x 1 root wheel 8 Apr 11 2018 sbin -> usr/sbin +drwxr-xr-x 2 root wheel 2 Apr 11 21:10 srv +dr-xr-xr-x 1 root wheel 0 Apr 11 21:25 sys +drwxr-xr-x 8 root wheel 9 Apr 11 21:10 usr +drwxr-xr-x 16 root wheel 17 Apr 11 21:10 var +.... + +[[linuxemu-debootstrap]] +=== 使用 debootstrap 安裝 Debian / Ubuntu 基礎系統 + +另一種提供 Linux 共用程式庫的方式是使用 package:sysutils/debootstrap[]。 +好處是能取得完整的 Debian 或 Ubuntu 發行版。 + +執行以下指令安裝 debootstrap: + +[source,shell] +.... +# pkg install debootstrap +.... + +man:debootstrap[8] 需要啟用 man:linux[4] ABI。 +啟用後,執行以下指令將 Ubuntu 或 Debian 安裝到 [.filename]#/compat/ubuntu#: [source,shell] .... -# kldload linux +# debootstrap jammy /compat/ubuntu +.... + +[NOTE] +==== +雖然技術上可以安裝到 [.filename]#/compat/linux#,但不建議這樣做,以免與 CentOS 系列套件產生衝突。 +建議根據發行版或版本名稱來命名目錄,例如 [.filename]#/compat/ubuntu#。 +==== + +輸出應類似如下: + +[.programlisting] +.... +I: Retrieving InRelease +I: Checking Release signature +I: Valid Release signature (key id F6ECB3762474EDA9D21B7022871920D1991BC93C) +I: Retrieving Packages +I: Validating Packages +I: Resolving dependencies of required packages... +I: Resolving dependencies of base packages... +I: Checking component main on http://archive.ubuntu.com/ubuntu... +[...] +I: Configuring console-setup... +I: Configuring kbd... +I: Configuring ubuntu-minimal... +I: Configuring libc-bin... +I: Configuring ca-certificates... +I: Base system installed successfully. +.... + +接著在 [.filename]#/etc/fstab# 中設定掛載點。 + +[TIP] +==== +如果希望共用家目錄的內容,並且能執行 X11 應用程式,應使用 man:nullfs[5] 將 [.filename]#/home# 和 [.filename]#/tmp# 以 loopback 方式掛載到 Linux 相容區域。 + +以下範例可加入 [.filename]#/etc/fstab#: + +[.programlisting] +.... +# Device Mountpoint FStype Options Dump Pass# +devfs /compat/ubuntu/dev devfs rw,late 0 0 +tmpfs /compat/ubuntu/dev/shm tmpfs rw,late,size=1g,mode=1777 0 0 +fdescfs /compat/ubuntu/dev/fd fdescfs rw,late,linrdlnk 0 0 +linprocfs /compat/ubuntu/proc linprocfs rw,late 0 0 +linsysfs /compat/ubuntu/sys linsysfs rw,late 0 0 +/tmp /compat/ubuntu/tmp nullfs rw,late 0 0 +/home /compat/ubuntu/home nullfs rw,late 0 0 .... -對 64-位元的相容性: +然後執行 man:mount[8]: [source,shell] .... -# kldload linux64 +# mount -al .... +==== -確認模組已載入: +若要透過 man:chroot[8] 進入系統,執行以下指令: [source,shell] .... -% kldstat - Id Refs Address Size Name - 1 2 0xc0100000 16bdb8 kernel - 7 1 0xc24db000 d000 linux.ko +# chroot /compat/ubuntu /bin/bash .... -在 FreeBSD 安裝基本的 Linux(TM) 程式庫和 Binary 最簡單的方式是安裝 package:emulators/linux_base-c6[] 套件或是 Port 。要安裝 Port: +接著可以執行 man:uname[1] 確認 Linux 環境: [source,shell] .... -# pkg install emulators/linux_base-c6 +# uname -s -r -m .... -要在開機時開啟 Linux(TM) 相容性,可以加入這行到 [.filename]#/etc/rc.conf#: +輸出應類似如下: [.programlisting] .... -linux_enable="YES" +Linux 5.15.0 x86_64 .... -在 64-位元的機器上,[.filename]#/etc/rc.d/abi# 會自動載入用來做 64-位元模擬的模組。 +進入 chroot 後,系統的行為就如同一般的 Ubuntu 安裝。 +雖然 systemd 無法運作,但 man:service[8] 指令可以正常使用。 -Since the Linux(TM) binary compatibility layer has gained support for running both 32- and 64-bit Linux(TM) binaries (on 64-bit x86 hosts), it is no longer possible to link the emulation functionality statically into a custom kernel. +[TIP] +==== +若要補上預設缺少的套件庫,請編輯 [.filename]#/compat/ubuntu/etc/apt/sources.list#。 + +amd64 可使用以下範例: + +[.programlisting] +.... +deb http://archive.ubuntu.com/ubuntu jammy main universe restricted multiverse +deb http://security.ubuntu.com/ubuntu/ jammy-security universe multiverse restricted main +deb http://archive.ubuntu.com/ubuntu jammy-backports universe multiverse restricted main +deb http://archive.ubuntu.com/ubuntu jammy-updates universe multiverse restricted main +.... + +arm64 則可使用: + +[.programlisting] +.... +deb http://ports.ubuntu.com/ubuntu-ports bionic main universe restricted multiverse +.... +==== + +[[linuxemu-advanced]] +== 進階主題 + +所有與 Linux 相關的 man:sysctl[8] 設定值都可以在 man:linux[4] 中找到。 + +部分應用程式需要掛載特定的檔案系統。 + +這通常由 [.filename]#/etc/rc.d/linux# 腳本處理,但也可以在開機時停用: + +[.programlisting] +.... +sysrc linux_mounts_enable="NO" +.... + +rc 腳本掛載的檔案系統無法在 chroot 或 jail 內的 Linux 程序中使用;如有需要,請在 [.filename]#/etc/fstab# 中設定: + +[.programlisting] +.... +devfs /compat/linux/dev devfs rw,late 0 0 +tmpfs /compat/linux/dev/shm tmpfs rw,late,size=1g,mode=1777 0 0 +fdescfs /compat/linux/dev/fd fdescfs rw,late,linrdlnk 0 0 +linprocfs /compat/linux/proc linprocfs rw,late 0 0 +linsysfs /compat/linux/sys linsysfs rw,late 0 0 +.... + +由於 Linux Binary 相容層已支援同時執行 32 位元與 64 位元的 Linux Binary,因此無法再將模擬功能靜態連結到自訂核心中。 [[linuxemu-libs-manually]] -=== 手動安裝其他程式庫 +=== 手動安裝額外的程式庫 + +[NOTE] +==== +若基礎系統是以 man:debootstrap[8] 建立的子目錄,請參照前述說明操作。 +==== + +如果某個 Linux 應用程式在設定好 Linux Binary 相容性後仍抱怨缺少共用程式庫,請確認該 Linux Binary 需要哪些共用程式庫,再手動安裝。 -若有 Linux(TM) 應用程式在設定 Linux(TM) Binary 相容性後出現缺少共用程式庫的情況,確認這個 Linux(TM) Binary 需要哪個共用程式庫並手動安裝。 +在相同 CPU 架構的 Linux 系統上,可以用 `ldd` 查出應用程式需要的共用程式庫。 -在 Linux(TM) 系統,可使用 `ldd` 來找出應用程式需要哪個共用程式庫。 例如,檢查 `linuxdoom` 需要哪個共用程式庫,在有安裝 Doom 的 Linux(TM) 系統執行這個指令: +舉例來說,若要檢查 `linuxdoom` 需要哪些共用程式庫,請在已安裝 Doom 的 Linux 系統上執行: [source,shell] .... % ldd linuxdoom +.... + +輸出應類似如下: + +[.programlisting] +.... libXt.so.3 (DLL Jump 3.1) => /usr/X11/lib/libXt.so.3.1.0 libX11.so.3 (DLL Jump 3.1) => /usr/X11/lib/libX11.so.3.1.0 libc.so.4 (DLL Jump 4.5pl26) => /lib/libc.so.4.6.29 .... -然後,複製所有 Linux(TM) 系統輸出結果中最後一欄的檔案到 FreeBSD 系統的 [.filename]#/compat/linux#。 複製完後,建立符號連結 (Symbolic link) 至輸出結果第一欄的名稱。以這個例子會在 FreeBSD 系統產生以下檔案: +接著將輸出最後一欄列出的所有檔案從 Linux 系統複製到 FreeBSD 系統的 [.filename]#/compat/linux# 下。 +複製完成後,建立指向第一欄名稱的符號連結。 -[source,shell] +以這個範例來說,FreeBSD 系統上會產生以下檔案: + +[.programlisting] .... /compat/linux/usr/X11/lib/libXt.so.3.1.0 /compat/linux/usr/X11/lib/libXt.so.3 -> libXt.so.3.1.0 @@ -144,56 +403,67 @@ libc.so.4 (DLL Jump 4.5pl26) => /lib/libc.so.4.6.29 /compat/linux/lib/libc.so.4 -> libc.so.4.6.29 .... -若 Linux(TM) 共用程式庫已經存在,並符合 `ldd` 輸出結果第一欄的主要修訂版號,則不需要複製該行最後一欄的檔案,使用既有的程式庫應可運作。若有較新的版本建議仍要複製共用程式庫,只要符號連結指向新版的程式庫,舊版便可移除。 +如果系統中已經有主版號相符的 Linux 共用程式庫(對應 `ldd` 輸出的第一欄),就不需要再複製最後一欄的檔案,既有的程式庫應該就能使用。 +不過如果有較新的版本,仍建議複製過來。 +舊的版本可以移除,只要確認符號連結指向新版即可。 -例如,以下程式庫已存在 FreeBSD 系統: +例如,FreeBSD 系統上已有以下程式庫: -[source,shell] +[.programlisting] .... /compat/linux/lib/libc.so.4.6.27 /compat/linux/lib/libc.so.4 -> libc.so.4.6.27 .... -且 `ldd` 顯示 Binary 需要使用較新的版本: +而 `ldd` 顯示某個 Binary 需要更新的版本: -[source,shell] +[.programlisting] .... libc.so.4 (DLL Jump 4.5pl26) -> libc.so.4.6.29 .... -雖然既有的程式庫只有在最後一碼過時一或兩個版本,程式應該仍可使用稍微舊的版本執行,雖然如此,保險起見還替換既有的 [.filename]#libc.so# 為較新的版本: +既有的程式庫只在最後一碼差了一兩個版本,理論上程式仍能正常執行。 +不過保險起見,還是建議替換掉既有的 [.filename]#libc.so#: -[source,shell] +[.programlisting] .... /compat/linux/lib/libc.so.4.6.29 /compat/linux/lib/libc.so.4 -> libc.so.4.6.29 .... -一般來說,只有在安裝 Linux(TM) 程式到 FreeBSD 完的前幾次會需要查看 Linux(TM) Binary 相依的共用程式庫。之後系統便有足夠的 Linux(TM) 共用程式庫能夠執行新安裝的 Linux(TM) Binary,便不再需要額外的動作。 +通常只有在 FreeBSD 上頭幾次安裝 Linux 程式時,才需要費心查找 Linux Binary 所相依的共用程式庫。 +累積一段時間後,系統裡的 Linux 共用程式庫就足夠齊全,新安裝的 Linux Binary 不需額外處理便能直接執行。 + +=== 為 Linux ELF Binary 加上標記 -=== 安裝 Linux(TM)ELF Binary +FreeBSD 核心用幾種方法判斷要執行的 Binary 是否為 Linux Binary:檢查 ELF 檔頭中的品牌標記、尋找已知的 ELF 直譯器路徑、檢查 ELF 註記;最後,預設情況下未標記的 ELF 執行檔會被當作 Linux Binary 處理。 -ELF Binary 有時候需要額外的步驟。當執行無商標 (Unbranded) 的 ELF Binary,會產生錯誤訊息: +如果以上方法全部失敗,嘗試執行該 Binary 可能會出現錯誤訊息: [source,shell] .... % ./my-linux-elf-binary +.... + +輸出應類似如下: + +[.programlisting] +.... ELF binary type not known Abort .... -要協助 FreeBSD 核心區別是 FreeBSD ELF Binary 還是 Linux(TM) Binary,可使用 man:brandelf[1]: +要協助 FreeBSD 核心區分 FreeBSD ELF Binary 與 Linux Binary,可以使用 man:brandelf[1]: [source,shell] .... % brandelf -t Linux my-linux-elf-binary .... -由於 GNU 工具鏈會自動放置適當的商標資訊到 ELF Binary,通常不需要這個步驟。 +=== 安裝以 Linux RPM 為基礎的應用程式 -=== 安裝以 Linux(TM)RPM 為基礎的應用程式 - -要安裝 Linux(TM)RPM 為基礎的應用程式,需先安裝 package:archivers/rpm4[] 套件或 Port。安裝完成之後,`root` 可以使用這個指令安裝 [.filename]#.rpm#: +要安裝以 Linux RPM 為基礎的應用程式,請先安裝 package:archivers/rpm4[] 套件或 Port。 +安裝完成後,`root` 可以用以下指令安裝 [.filename]#.rpm#: [source,shell] .... @@ -201,19 +471,20 @@ Abort # rpm2cpio < /path/to/linux.archive.rpm | cpio -id .... -如果需要, `brandelf` 已安裝的 ELF Binary。注意,這將會無法乾淨地解除安裝。 +如有需要,請對安裝好的 ELF Binary 執行 `brandelf`。 +請注意,這樣做將無法乾淨地解除安裝。 === 設定主機名稱解析器 -如果 DNS 無法運作或出現這個錯誤: +如果 DNS 無法運作或出現以下錯誤: -[source,shell] +[.programlisting] .... resolv+: "bind" is an invalid keyword resolv+: "hosts" is an invalid keyword .... -將 [.filename]#/compat/linux/etc/host.conf# 設定如下: +請將 [.filename]#/compat/linux/etc/host.conf# 設定如下: [.programlisting] .... @@ -221,40 +492,11 @@ order hosts, bind multi on .... -這指定先搜尋 [.filename]#/etc/hosts#,其次為 DNS。 當 [.filename]#/compat/linux/etc/host.conf# 不存在, Linux(TM) 應用程式會使用 [.filename]#/etc/host.conf# 並會警告不相容的 FreeBSD 語法。如果名稱伺服器未設定使用 [.filename]#/etc/resolv.conf# 的話,則可移除 `bind`。 - -[[linuxemu-advanced]] -== 進階主題 - -This section describes how Linux(TM) binary compatibility works and is based on an email written to http://lists.FreeBSD.org/mailman/listinfo/freebsd-chat[FreeBSD chat mailing list] by Terry Lambert mailto:tlambert@primenet.com[tlambert@primenet.com] (Message ID: `<199906020108.SAA07001@usr09.primenet.com>`). - -FreeBSD has an abstraction called an "execution class loader". This is a wedge into the man:execve[2] system call. - -Historically, the UNIX(TM) loader examined the magic number (generally the first 4 or 8 bytes of the file) to see if it was a binary known to the system, and if so, invoked the binary loader. - -If it was not the binary type for the system, the man:execve[2] call returned a failure, and the shell attempted to start executing it as shell commands. The assumption was a default of "whatever the current shell is". - -Later, a hack was made for man:sh[1] to examine the first two characters, and if they were `:\n`, it invoked the man:csh[1] shell instead. - -FreeBSD has a list of loaders, instead of a single loader, with a fallback to the `#!` loader for running shell interpreters or shell scripts. - -For the Linux(TM)ABI support, FreeBSD sees the magic number as an ELF binary. The ELF loader looks for a specialized _brand_, which is a comment section in the ELF image, and which is not present on SVR4/Solaris(TM) ELF binaries. - -For Linux(TM) binaries to function, they must be _branded_ as type `Linux` using man:brandelf[1]: - -[source,shell] -.... -# brandelf -t Linux file -.... - -When the ELF loader sees the `Linux` brand, the loader replaces a pointer in the `proc` structure. All system calls are indexed through this pointer. In addition, the process is flagged for special handling of the trap vector for the signal trampoline code, and several other (minor) fix-ups that are handled by the Linux(TM) kernel module. - -The Linux(TM) system call vector contains, among other things, a list of `sysent[]` entries whose addresses reside in the kernel module. - -When a system call is called by the Linux(TM) binary, the trap code dereferences the system call function pointer off the `proc` structure, and gets the Linux(TM), not the FreeBSD, system call entry points. - -Linux(TM) mode dynamically _reroots_ lookups. This is, in effect, equivalent to `union` to file system mounts. First, an attempt is made to lookup the file in [.filename]#/compat/linux/original-path#. If that fails, the lookup is done in [.filename]#/original-path#. This makes sure that binaries that require other binaries can run. For example, the Linux(TM) toolchain can all run under Linux(TM)ABI support. It also means that the Linux(TM) binaries can load and execute FreeBSD binaries, if there are no corresponding Linux(TM) binaries present, and that a man:uname[1] command can be placed in the [.filename]#/compat/linux# directory tree to ensure that the Linux(TM) binaries cannot tell they are not running on Linux(TM). +這表示先搜尋 [.filename]#/etc/hosts#,再查詢 DNS。 +當 [.filename]#/compat/linux/etc/host.conf# 不存在時,Linux 應用程式會使用主系統的 [.filename]#/etc/host.conf#,但會抱怨該檔案在 FreeBSD 上不存在。 +如果未透過 [.filename]#/etc/resolv.conf# 設定名稱伺服器,請移除 `bind`。 -In effect, there is a Linux(TM) kernel in the FreeBSD kernel. The various underlying functions that implement all of the services provided by the kernel are identical to both the FreeBSD system call table entries, and the Linux(TM) system call table entries: file system operations, virtual memory operations, signal delivery, and System V IPC. The only difference is that FreeBSD binaries get the FreeBSD _glue_ functions, and Linux(TM) binaries get the Linux(TM)_glue_ functions. The FreeBSD _glue_ functions are statically linked into the kernel, and the Linux(TM)_glue_ functions can be statically linked, or they can be accessed via a kernel module. +[[linuxemu-misc]] +=== 其他事項 -Technically, this is not really emulation, it is an ABI implementation. It is sometimes called "Linux(TM) emulation" because the implementation was done at a time when there was no other word to describe what was going on. Saying that FreeBSD ran Linux(TM) binaries was not true, since the code was not compiled in. +更多關於 Linux(R) Binary 相容性運作原理的資訊,請參閱文章 link:{linux-emulation}[Linux emulation in FreeBSD]。