--- title: FHS 檔案系統階層標準 --- [TOC] <style> .bg1 { padding: 0 5px; white-space: pre-line; border-radius: 2px; background-color: black; color: white; } .bg2 { padding: 0 5px; white-space: pre-line; border-radius: 2px; background-color: black; color: skyblue; } </style> <!-- 目標:讓學生了解linux的檔案目錄結構(FHS)與基礎指令 *要讓學生知道哪個檔案會在哪個目錄中 (表格練習) ex.開機檔案在? /boot 方法:先教學生基礎bash指令->先學怎麼用(30 min?),再講解FHS->再學其結構(60 min?)(先應用再理論) 群組是為了將多個使用者集合在一起,便於管理權限和資源。每個使用者可以屬於一個或多個群組,這些群組為使用者分配相同的資源和權限。 而 Linux 的檔案系統使用三種權限來控制誰可以對檔案和目錄進行操作: * 擁有者(Owner):檔案的創建者,一般是使用者。 * 群組(Group):與檔案相關聯的群組,群組成員可以根據設定對檔案進行操作。 * 其他人(Others):不屬於擁有者或群組的其他使用者。 --> # FHS 上課檔案 ## Linux 簡介 #### 歷史 * 早期的作業系統是要錢的(UNIX),使用時需要支付昂貴的許可費 > 歷史背景是當時都是 mainframe 而沒啥「個人電腦」,後來個人電腦(PC, Personal Computer )才出來 * The first open source in the world is Unix level 6. * 後續出現 MINIX,由計算機科學家 Andrew S. Tanenbaum 為了**教學目的**而開發的一個簡化版的 UNIX。 * 計算機科學家 Linus Torvalds ,他受到了 MINIX 的啟發,想要開發一個可以在個人電腦上執行的 OS ,決定編寫一個新的 OS ,這就是 Linux 核心(Linux kernel)的誕生。 #### 特點 * **萬物皆檔案**:在 Linux 中,硬碟、鍵盤、滑鼠等會被表示為檔案,執行的 Process 也會被表示為檔案,甚至是我們下的一些指令也是以檔案型態存在在電腦中。 * **檔案系統的資料結構**:Linux 使用 inode(index node)來定位各種檔案在磁區的位置,像是檔案、目錄、裝置檔案、socket 等都會有數個 inode。 > 透過 inode 在磁碟空間的茫茫大海中找到檔案位置 每個 inode 除了會儲存了檔案的屬性和磁區位置外,也會包含了其他資料如:最後修改時間、檔案擁有者(owner)等權限相關資料,**但不包括檔案名稱與檔案內容本身**。 * **多使用者作業系統**,可能很少會看到有人使用 Linux 當作個人電腦的主系統,但 Linux 最強大的地方是適合多個使用者在同一系統上工作。 ![image](https://hackmd.io/_uploads/SyVApSMAR.png) 每個使用者都擁有各自的帳戶、檔案和設定,並且每個人都有獨立的工作環境,大家在同一系統工作時幾乎不會互相影響。 > 截至2024九月,目前桌機與筆電大部分都是 Windows,佔71.47%,位居第二則是 macOS,有 15.45%,Linux 的使用者佔 6.28%,但別忘了 Android 使用的也是 Linux 核心,如果加上 Android 那可觀的市占率,Linux 就是市佔最大的 OS ㄛ ouo 世界上前500個最快的電腦全都是用 Linux kernal ## 前情指令 | 指令|簡介| |-|-| |cd|<font color="red">c</font>hange <font color="red">d</font>irectory 切換路徑| |ls|<font color="red">l</font>i<font color="red">s</font>t 將當前目錄底下的檔案列出來<br>| |sudo|<font color="red">S</font>uper <font color="red">U</font>ser <font color="red">D</font>O sudo 通常會被加在某一個指令的前面,以電腦管理員身份執行該指令。| |^c |Ctrl c,中斷進行中的程式| |^z |Ctrl z,暫停但不中斷| |^l|清除之前的畫面| ## FHS 檔案系統階層標準 * 全名:Filesystem Hierarchy Standard * 為什麼要用 FHS? 因為用 Linux 來開發產品公司與個人太多,因此訂定一個檔案系統階層標準來規範檔案的目錄位置。 FHS 旨在定義一個**標準的檔案系統層次結構**,使各種 Linux 發行版本的檔案和目錄位置保持一致。這樣,應用程式開發員和系統管理員不必擔心每個版本有不同的檔案位置,讓 Linux 有高移植性。 > 如果妳曾經使用過 Windows 系統的話,會發現妳的檔案總管內有好多的裝置,包括 C 槽、 D 槽、光碟機、 可攜式硬碟機、USB 裝置....一大堆東西。那麼 Linux 有沒有這些東西呢?答案是....沒有這些『代號』了 Linux 已經沒有所謂的裝置名稱了,所以當然也沒有 C, D... 槽。那麼我們的檔案要如何放置? 其實 Linux (或 Unix-Like,類 Unix 系統) 使用的是**單一根目錄理念**、目錄樹。最頂層的目錄為根目錄 (/),所有的目錄都在這個根目錄之下。這樣一來無論系統中有多少磁碟或分區,它們都被掛載到一個統一的目錄結構中。這個目錄樹也是整個檔案的基礎!如果你以檔案總管的想法來思考的話,如同下圖所示: ![image](https://imgur-backup.hackmd.io/hS53GKi.png) ![image](https://hackmd.io/_uploads/r10fTjaTR.png) > 在 Windows 中,每分出一個磁區就需要一個磁碟機代號(如 C:、D:),雖然直觀但不夠靈活,隨著設備的更新(如插入 USB、安裝新的硬碟),這些磁碟機代號的改變,會導致應用程式或使用者無法找到想要的檔案。 <br> <p class="text-center" style="font-size:30px; font-weight:700;">"Linux 中萬物皆檔案 Everything is a file"</p> ## 如何理解Linux中萬物皆檔案? 1. Device:在 Linux 中,設備(如硬碟、鍵盤、滑鼠等)會被表示為檔案,透過檔案系統中的 **設備檔案** `/dev/sda`來存取和操作裝置。 2. Process:每個執行的行程都被表示為檔案,可以在`/proc`目錄下找到相應的檔案,如`/proc/{PID}/status`和`/proc/{PID}/cmdline`。 3. 網路檔案:網路連線、套接字和網路介面等也被表示為檔案。例如,套接字檔案可以在`/proc/net`目錄下找到。 4. 檔案和目錄:檔案和目錄是最常見的概念,它們被用於儲存資料、設定資訊和程式碼等。在 Linux 中,檔案和目錄也被抽象化為檔案的形式,並透過檔案系統進行管理和存取。 ## Linux 檔案權限 > **多使用者作業系統**,可能很少會看到有人使用 Linux 當作個人電腦的主系統,但 Linux 最強大的地方是適合多個使用者在同一系統上工作。 ![image](https://hackmd.io/_uploads/HyQkRrfRR.png) 每個使用者都擁有各自的帳戶、檔案和設定,並且每個人都有獨立的工作環境,大家在同一系統工作時幾乎不會互相影響。 Linux 是多人多工的系統,因此可能常常會有多人同時使用這部主機來進行工作的情況, 為了考慮每個人的隱私權以及每個人喜好的工作環境,因此有了使用者與群組的概念。 - 檔案擁有者(Owner) 當一個使用者創建一個檔案時,該使用者自動成為檔案的擁有者。擁有者通常有對該檔案的讀取、寫入和執行權限,可以修改檔案的內容或刪除檔案。 - 群組(Group) 每個檔案都會分配給一個群組,該群組內的使用者將共享這個檔案的權限。 - 其他人(Others) 其他人是系統中除了檔案的擁有者和群組成員以外的所有使用者。對於其他人,檔案的擁有者可以選擇是否授予讀取、寫入或執行權限。 ###### ⮕ 就像是 GOOGLE 共編的概念 ## Linux 檔案屬性 #### ls 將目前目錄底下的檔案列出來 ->想看到更多詳細資訊,用`ls -l`顯示詳細資訊 ![image](https://hackmd.io/_uploads/Hykc_8S60.png) |顏色|代表意義| |-|-| |<font color="blue">藍色檔</font>|目錄| |<span class="bg1">白色檔</span>|一般性檔,如文字檔,設定檔,源碼檔等| |<span class="bg2">淺藍色檔</span>|連結檔、捷徑,主要是使用ln命令建立的檔| |<font color="green">綠色檔</font>|可執行檔,可執行檔程式| |<font color="red">紅色檔</font>|壓縮檔或包檔| #### 其中含義 ![image](https://hackmd.io/_uploads/BJVYGEa6C.png) 1. `白色` **檔案類型與權限(Mode)**:第一個字元表示檔案的類型: * -:一般檔案(regular file) * d:目錄(directory) * l:符號連結(symbolic link) * b:區塊設備檔案(block device file) * c:字元設備檔案(character device file) 2. `紅色` 隨後的 9 個字元分為 3 組,分別表示檔案擁有者、群組、其他使用者的讀取、寫入與執行權限: * r:讀取權限(read) * w:寫入權限(write) * x:執行權限(execute) 3. `橘色`**連結數量(Links)**:有多少 hardlink 指到此檔案。`在下面 "ln" 補充(後面會詳細說明)` 5. `黃色`**擁有者(Owner)**: 檔案的擁有者名稱。 6. `綠色`**群組(Group)**: 檔案所屬的群組名稱。 7. `藍色`**檔案大小(Size)**: 檔案的大小,以位元組(bytes)為單位。 8. `粉色`**最後修改時間(Timestamp)**: 檔案最後修改的日期和時間。格式為月、日和時間。如果修改時間超過一年,會顯示年份而非時間。 9. `紫色`**檔案名稱(Name)**: 檔案或目錄的名稱。如果是符號連結,會顯示連結到的目標。 ## `/` - `/` :root 為根目錄,是<font color="red">整個系統最重要</font>的目錄,所有的目錄都是由根目錄衍生出來的,同時根目錄也與開機/還原/系統修復等動作有關。 ![image](https://hackmd.io/_uploads/HJiWpsppR.png) *** ### `/bin` Binary * 存放基本的二進制可執行檔案,例如常用的命令(如 `ls`、`cp`複製、`mv`剪貼、`cat`印出檔案內容),而這些命令在一般使用者模式 * `/bin `目錄的可執行檔案可以被當作命令使用,是因為它們位於環境變數 PATH 指定的路徑中。 * 查看當前系統的 PATH 變數`echo $PATH` :::success **二進制可執行檔案** 是已經被編譯成機器碼的檔案,能夠被系統直接執行。 像 Python 的 .py 等,這些以人類可讀的文本格式書寫的程式,執行時需要編譯器(compiler)將其解釋成機器碼才能執行。 使用 file 命令可以判斷某個檔案是否為二進制可執行檔案: ```bash= file /bin/ls /bin/ls: ELF 64-bit LSB executable, x86-64, version 1 (SYSV), dynamically linked ... ``` - 牛刀小試 執行`cat /bin/ls`會出現什麼?為什麼格式會長那樣? ::: spoiler ![image](https://hackmd.io/_uploads/S1xtiKWAA.png) 該命令將列印二進位檔案/bin/ls的內容,這會導致亂碼。 如果你想減少「亂碼」輸出,你可以使用十六進位轉儲器:`od -ax /bin/ls | more` ::: ### `/sbin` Super user Binaries * 開機過程中所需要的檔案。 * 開機、修復、還原系統所需要的指令。 * 系統管理員會用到的指令,例如 ifconfig、shutdown 等。 `sudo` 其實是「<font color="red">S</font>uper <font color="red">U</font>ser <font color="red">DO</font>」的縮寫。 如果被加在某一個指令的前面,代表這個指令是透過 Super User 所執行的。 > Linux有非常多指令是用來設定系統環境的 > * 某些伺服器軟體程式,一般則放置到/usr/sbin/當中。 > * 本機自行安裝的軟體所產生的系統執行檔(system binary), 則放置到/usr/local/sbin/當中。 ::: danger #### josh 學長支援網路工具 -> 之後補充 ::: ### `/boot` bootstrap * 放置開機會使用到的檔案,包括 Linux 核心檔案以及開機選單與開機所需設定檔。 - 例如 : `initrd.img` - Initial ramdisk - 開機時會先在記憶體中載入一個暫時的根目錄系統 - 包含真正的 `/` - 掛載真正的 `/` 前的準備工作 - 非必要,但有 `initrd.img`,開機會快很多,因為不用重新編譯 kernel ### `/dev` device * 存放與設備(如硬碟、USB、終端機等)對應的設備檔案。 - 放置各種硬體設備的檔案 - 因為在 Linux 中,萬物皆檔案,所以對這些硬體檔案做操作就是對硬體做操作 - 例如:滑鼠、鍵盤、記憶體 * 每個檔案都代表一個設備,例如 `/dev/sda1` 代表一個硬碟分區。 * `/dev/tty`:放置終端檔案。 * `/dev/null`:空裝置,也叫做「黑洞」,任何寫入到 `/dev/null` 的資料都會被丟棄,常用來消除不需要的輸出。 * `echo "test" > /dev/null` :::success **牛刀小試** 試試看 `cat /dev/sda`(代表第一個硬碟) ::: ### `/etc` * 系統主要的設定檔,例如網路設定、啟動腳本、服務設定(如 /etc/passwd 保存使用者資訊)。 * 各檔案屬性是可以讓一般使用者查閱的, 但只有 root 有權力修改。 - `/etc/passwd`:user 的帳號密碼檔 - 不用 `sudo` 就可以查看 - ![image](https://hackmd.io/_uploads/HkpP0NbRR.png) - ![image](https://hackmd.io/_uploads/B1XNlH-0C.png) ->第一行 - **帳號名稱**:帳號名稱(例如 root, user)。 - **密碼佔位符**:通常是字母 x,代表密碼儲存在其他地方(例如 /etc/shadow 檔案),並不是明文儲存在這裡。 - 也可以放在`/etc/passwd`,但非常不安全。因`/etc/passwd`是所有使用者和程式都可以讀取的。 - **使用者ID(UID)**:使用者的數字ID(例如 0 是 root 使用者的UID,普通使用者則有自己的 ID 號碼)。 - **群組ID(GID)**:使用者所屬群組的 ID。 - **使用者描述**:使用者的描述資訊,有時是空的。 - **主目錄**:表示該使用者的主目錄位置(例如 /root 或 /home/user)。 - **登入shell**:表示該使用者使用的預設 shell(例如 /bin/bash 或 /usr/sbin/nologin)。 - 小lab:創兩個帳號,把 uid 更改後再回到家目錄看會到哪個帳號 - `/etc/shadow`:真正存 user 密碼的地方 - 需要使用 `sudo` 才能查看 - `shadow` 的密碼是加密過的 - ![image](https://hackmd.io/_uploads/ryZMCVZCA.png) 1. **使用者名**:每行的第一部分是使用者名(例如 root、sudo)。 2. **加密的密碼**:第二部分顯示加密後的密碼,如果內容不符合加密的輸出格式(例如包含 * 或 ! 等特殊字元),則此使用者就無法登入。 3. **上次密碼變更日期**:第三部分是自1970年1月1日( Unix 紀元時間)以來,上次變更密碼的天數。 4. **最短密碼使用期限**:第四部分表示從密碼變更日起,密碼至少要使用多少天才能再次修改(通常是 0 表示不限制)。 5. **最長密碼使用期限**:第五部分是密碼的最長有效天數,超過此天數後需要更改密碼(例如 99999 表示不強制過期)。 6. **警告期限**:第六部分是密碼即將過期時,提前幾天開始警告。 7. **帳號非活躍天數**:第七部分表示帳號密碼過期後多少天內帳號被標記為不活躍。 8. **帳號過期日期**:第八部分是帳號失效的日期。 9. **保留字段**:第九部分目前通常是保留不使用的。 - [講義 `/etc/passwd`、`/etc/shadow`](https://hackmd.io/LPP9vQ-2TqOvbxpyMjKM3Q) :::info **既然有 `/etc/passwd` 了,為什麼還要有 `/etc/shadow`?** 很久以前,`/etc/passwd` 裡面是有存使用者密碼,但那時的加密技術不成熟,而且有很多人把密碼設的很簡單,所以 `/etc/passwd` 的密碼移到 `/etc/shadow` 中並加密。 現在 `/etc/passwd` 的作用主要在察看使用者的資訊,只有 root 才可以看 `/etc/shadow` 。 ::: ### `/lib` Library * 在開機時會用到的函式庫。 * `/bin`或`/sbin`底下的指令會呼叫的函式庫。 * ![image](https://hackmd.io/_uploads/SJATnFZR0.png) :::info **什麼是 library 函式庫?** - library 是用在開發軟體的子程式集合 - 生活化的例子:食譜書 - 食譜中的目錄 :point_right: library - 包含各個食譜 :point_right: 常用的 Function - 在食譜目錄中選擇麻婆豆腐來料理 :point_right: 在 library 中選擇想要呼叫的 Function ::: ### `/lib<qual>` * 存放與 /lib 不同的格式的二進位函式庫。 * 如支援 64 位元的 /lib64 函式庫。 ### `/media` * 放置可移除的裝置,例如隨身碟、光碟、DVD。 * 電腦會自動掛載到這裡 * 小精靈(桌面環境中的程式)會幫你偵測設備 * `udisks2` 主要負責管理磁碟和儲存設備的掛載和卸載 :::danger #### 簡學長支援掛載實作 ```shell (base) bs10081@Reg-labLinux:~$ ls /media/bs10081/Flash-32G/ output.pdf ``` lsblk ->放到指令 sdc 8:32 1 28.8G 0 disk ├─sdc1 8:33 1 200M 0 part └─sdc2 8:34 1 28.6G 0 part /media/bs10081/Flash-32G ::: ### `/mnt` * (手動)暫時掛載某些額外的裝置。 :::info `/media`與`/mnt` | 目錄 | 目錄內容 | | -------- | -------- | | `/dev` | 放置硬體設備的**檔案**| | `/mnt` | **手動掛載**的可移除裝置| | `/media` | 放置**自動掛載**的可移除裝置| :::success 使用 `mount` 命令手動掛載可移除裝置 以下是使用 `mount` 指令手動掛載可移除裝置的步驟: ```bash= #假設裝置名稱是 /dev/sdb1,並且你希望將它掛載到 /mnt/usb 目錄 sudo mount /dev/sdb1 /mnt/usb #掛載完成後,你可以檢查掛載是否成功,並查看掛載的檔案系統: df -h #這個命令會列出所有已掛載的檔案系統,並顯示它們的掛載點和可用空間。 #你應該能在列表中看到 /mnt/usb 及其對應的裝置 /dev/sdb1。 #卸載裝置 sudo umount /mnt/usb # 以唯讀模式掛載 sudo mount -o ro /dev/sdb1 /mnt/usb ``` 注意:命令是 `umount` 而非 `unmount`,不要拼錯。 ::: ### `/opt` optional * 第三方軟體放置的目錄 * 自行安裝額外的軟體 * 像是 Google Chrome、VirtualBox、telegram - 怕某個檔案汙染系統的話,可以把雜七雜八的東西放在這裡 * 以前習慣放在`/usr/local` ### `/run` - 存放系統運行時需要的臨時數據 - 各種服務會需要的暫存檔案 - 例如: `.pid` - 內容只有一行,紀錄目前的 process 的 id 是多少 (pid) - 防止同個 service 同時啟動多個副本 - 會導致這些副本互相搶資源 - 啟動服務前會先檢查有沒有 `.pid` - 有,就停止啟動服務 - 沒有,就啟動服務,然後把此服務的 pid 存進 `<service>.pid` - 其它同一個 service 的多餘 process 則自動退出 - 當關閉服務時,`<service>.pid` 也會跟著被刪除 (kill) ### `/srv` service - 放置一些網路服務啟動後,這些服務所需要取用的資料目錄 - 通常有對 Unix 跨平台的服務才會被掛載在這邊 - 例如 : FTP (檔案傳輸協定) - 用在網路上 client 和 server 之間進行檔案傳輸的應用層協定 - 預設的 FTP server folder 是在 `/srv/ftp` 欲分享的檔案可以放在這邊 ### `/tmp` - 讓一般使用者或者是正在執行的程式暫時放檔案的地方 - 可依照自己的設定來定期清除`/tmp`內的東西 - ![image](https://hackmd.io/_uploads/BJD5m9-R0.png) - 所有使用者與群組的權限**可讀可寫可執行** - 因為 `/tmp` 是讓所有使用者暫存檔案的地方,所以要**可讀可寫** - 有些程式會將安裝檔暫存在此,所以要**可執行** - 未經授權的使用者可以寫入惡意程式 - 可能變成病毒的溫床 - 不過可以把特定檔案另外掛載,設定成 ==`noexec`== - 無法被執行 - 可以避免惡意程式被執行的可能 ### `/home` ![image](https://hackmd.io/_uploads/H1Ug9ZJCR.png) * 每個使用者都有各自的 home 目錄 * 存放所有使用者的個人檔案和設定檔。 * 每個使用者在 /home 目錄下都有自己的子目錄,這個目錄的名稱通常與使用者名稱相同。 * 使用者名稱為 joanna,那麼該使用者的主目錄路徑就是`/home/joanna`。 * 家目錄的兩種代號: * ~:代表目前這個使用者的家目錄 * ~XXX :則代表是 XXX 的家目錄 ### `/root` - 系統管理員 (root) 的家目錄 - 一般使用者的家目錄都在 `/home` - `root` 基本上是 Linux 系統中的神 :::success `sudo -i` 是用來切換到 root 使用者的命令,並進入該使用者的登錄環境。 ::: ### `/lost+found` * 當檔案系統發生錯誤時, 將一些遺失的片段放置到這個目錄下。 * 使用標準的 ext2/ext3/ext4 檔案系統格式才會產生 :::success * 用 fsck 程式來檢查檔案系統是否發生**錯誤** * 跳電 -> 檔案系統格式出問題(bit 跑掉) ::: ### `/proc` process * 本身是一個『虛擬檔案系統(virtual filesystem)』。 * 存放系統核心、行程資訊(process)、周邊裝置的狀態及網路狀態等。 * 目錄下的資料都存在記憶體中, 所以本身不佔任何硬碟空間。 ### `/sys` system * 也是一個虛擬的檔案系統。 * 不佔任何硬碟空間。 * 記錄核心與系統硬體資訊較相關的資訊。 * 如已載入的核心模組與核心偵測到的硬體裝置資訊等。 ## `/usr` 與他的子目錄 - Unix Software Resource,以前是指 user - 「非系統基本必須的」東西 - Unix 作業系統軟體資源所放置的目錄 User Shareable Read-only 或 Unix System Resources 或 Unix Software Resources 的縮寫 ### 需要存在的目錄 - `/usr/bin` - 放使用者非必備的二進位檔案 - 使用者安裝的程式的指令會在這裡 - `/usr/sbin` - 非系統平時運作所需要的指令 - 通常給超級使用者使用 - `/usr/lib` - 不是系統基本的,而是往上安裝的函式庫都放到 `/usr/lib` - 例如 - `python`:python 的函式庫 - `gcc`:C 的編譯器 :::info 根目錄底下也有`bin`, `sbin`, `lib`? - ![image](https://hackmd.io/_uploads/SkkDtoA6C.png) > 根目錄`/`下的`bin`, `sbin`, `lib`與`/usr/`底下的`bin`, `sbin`, `lib`內容是相同的ㄛ * 目錄底下的重複性高(意義差距不大),因此合併 ::: :::success #### softlink * 指向另一個檔案或目錄的指標。 * 類似於 Windows 中的快捷方式。 * 一個獨立的檔案,內容是他所指向的檔案或目錄的路徑。 * 如果原檔案被刪除或移動,軟連結將會無效,成為「死連結」(Broken Link)。 * 通過`ln -s source_file link_name`來建立軟連結。 #### hardlink * 指向檔案位置,而不是指向檔案名稱。 * 一個檔案可以有多個名稱(即多個硬連結),但它們實際上都指向相同的磁區。 * 硬連結指向檔案的實際數據區塊,因此即使原檔案被刪除,硬連結仍然可以存取該檔案的內容。 * 備份用 hardlink。 * 通過`ln source_file link_name`來建立軟連結。 |項目| 軟連結(Soft Link)| 硬連結(Hard Link)| |--|--|--| |位置 |可以跨檔案系統、磁碟分區 |必須在同一檔案系統內| |刪除原檔案的影響| 刪除原檔案會導致軟連結無效 |刪除原檔案不會影響硬連結| |指向目標| 指向檔案或目錄的路徑| 指向檔案的數據區塊| |是否可指向目錄| 可以指向目錄(ln -s)| 通常無法指向目錄(在部分系統中有限制)| |檔案計數(Links)| 不會增加檔案的硬連結數| 會增加檔案的硬連結數| * 檔案計數要用 ls -l 看 * 要查看有哪些硬連結指向同一個檔案,可以使用 find 命令: ```bash find /path/to/search -samefile filename #這會列出所有指向與 filename 相同檔案數據的連結。 ``` :::info - hardlink 指向一個**檔案本身** - 史萊姆 -> 一直分裂 - 只是多了一個暱稱,稱呼同一個東西 - softlink 指向**任何東西** -> 他不一定要存在 - 分身 -> 本體沒了就沒了 - 指向一個位置,像是一個指標或是路牌 > [name=蓬萊 人偶] [name=BT] ::: - `/usr/local` - 存放系統管理員在本機自行安裝自己下載的軟體 - 將自行安裝的軟體與作業系統的預設軟體區分開來 - 這個子目錄底下也有 `/bin`、`/lib`、`/etc`... 的次目錄 - 當系統進行升級或安裝新發行版時,可以將自行安裝或編譯的軟體放置在這邊 - 避免覆蓋系統預設軟體 - 無須重新安裝全部程式 - 若有相同名稱執行檔,可能會發生系統衝突、混淆(依 $PATH 順序決定) - `/usr/share` - 主要放置唯讀架構的檔案 - 幾乎都是文字檔案 - 例如:`man`,線上說明檔案,可以教你指令怎麼用 ## `/var` 與他的子目錄 - 主要針對**常態性變動**的檔案 - 系統運作後才會漸漸佔用硬碟容量的目錄 - 快取 (cache)、紀錄檔 (log file) 以及某些軟體運作所產生的檔案 - 適合存放需要頻繁改寫的檔案 - 例如:系統記錄檔、資料庫裡的檔案 ### 需要存在的目錄 - `/var/cache` - 應用程式本身運作過程中會產生的一些暫存檔 - 例如:`apt install` 下來的 package - `/var/lib` - 放置程式本身執行的過程中,需要使用到的資料檔案 - 例如:mySQL 的 data base 跟 table 通常都會存在 `/var/lib` - `/var/lock` - 某些裝置或者是檔案資源一次只能被一個應用程式所使用 - 同時被兩個程式使用該裝置時,可能產生一些錯誤的狀況 - 所以要將該裝置上鎖 (lock) - `/var/log` - 紀錄檔放置的目錄 - `/var/log/auth.log` - 記錄所有與認證和安全相關的事件,例如登錄嘗試、sudo 使用、SSH 登錄等 - ![image](https://hackmd.io/_uploads/BJU6-qGCC.png) - `/var/log/faillog` - 記錄失敗的登入嘗試,特別是與密碼錯誤相關的事件。 - `/var/log/btmp` - 紀錄登入失敗的資訊 - `/var/log/wtmp` - 記錄所有的登錄與登出活動 - `/var/log/boot.log`、 `/var/log/bootstrap.log` - 開機相關的紀錄檔 - `/var/mail` - 放置個人電子郵件信箱的目錄 - `/var/spool` - 這個目錄通常放置一些佇列資料 - 佇列資料 : 排隊等待其他程式使用的資料 - 這些資料被使用後通常都會被刪除 - 例如:印東西<!-- `mail` : 有人寄信過來的時候,信會放在此 --> - 也有 mail - ![image](https://hackmd.io/_uploads/ryRWRFG0C.png) *** ## Linux常用的指令 ### 查閱系統指令、工具和功能的說明檔案的工具 | 指令|簡介| |-|-| |man|Manual,用來查閱系統中每個命令或程式的手冊| |info|命令提供了比 `man` 更詳細、更結構化的檔案說明| |whatis|更簡潔的指令說明,它只會返回一行簡短描述| |type|查詢某個指令的型態| |file|確定檔案型態| |uname|顯示有關 Linux 系統基本資訊| ```bash= man ls # 查看 ls 命令的手冊頁 <--ls 命令的手冊頁(下略)--> info ls # 查看 ls 命令的 info 文檔 <--ls 命令的 info 文檔(下略)--> whatis ls # 返回一行描述 ls 命令的功能 ls (1) - list directory contents LS (6) - display animations aimed to correct users who accident... type ls # 查詢 ls 命令的型態 ls is alias to 'ls --color=auto' file /bin/ls # 確定 /bin/ls 的檔案型態 /bin/ls: ELF 64-bit LSB pie executable, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, BuildID[sha1]=36b86f957a1be53733633d184c3a3354f3fc7b12, for GNU/Linux 3.2.0, stripped uname #顯示有關 Linux 系統基本資訊 Linux uname -a #顯示詳細系統資訊 Linux leafish 5.15.153.1-microsoft-standard-WSL2 #1 SMP Fri Mar 29 23:14:13 UTC 2024 x86_64 x86_64 x86_64 GNU/Linux ``` ### 常用的網路相關工具 | 指令|簡介| |-|-| |netstat|查看系統的網路連接和統計數據| |ss|現代化的 socket 統計工具,替代 `netstat`,顯示網路連接、監聽port等| |dig|DNS 查詢工具,用於獲取域名的 DNS 資訊| |ping|測試網路連通性,檢測主機是否可達並計算延遲時間| ```bash= netstat -an # 顯示所有連接並以數字格式顯示 netstat -r # 顯示路由表 ss -tuln # 顯示所有 TCP、UDP 監聽端口,以數字格式顯示 ss -p # 顯示與連接相關的進程 dig example.com # 查詢 example.com 的 A 記錄(IPv4 地址) dig google.com MX # 查詢 google.com 的 MX 記錄(郵件交換器) dig @8.8.8.8 example.com # 使用 Google 的 DNS 伺服器(8.8.8.8)查詢 ping example.com # 向 example.com 發送 ICMP 數據包,測試連通性 ping -c 4 google.com # 向 google.com 發送 4 個 ICMP 數據包 ``` ### 操作檔案相關的指令 | 指令|簡介| |-|-| |pwd|<font color="red">p</font>rint <font color="red">w</font>orking <font color="red">d</font>irectory 顯示當前目錄位置| |ls|<font color="red">l</font>i<font color="red">s</font>t 將當前目錄底下的檔案列出來<br>| |cd|<font color="red">c</font>hange <font color="red">d</font>irectory 切換路徑| |mkdir|<font color="red">m</font>a<font color="red">k</font>e <font color="red">dir</font>ectory:建立資料夾| |touch|新增檔案:touch 檔名.副檔名| |cat|~~貓~~ 正確解釋:con<font color="red">cat</font>enate, 但我比較喜歡:call at terminal的說法| |head|用來顯示檔案的**前面幾行**,預設顯示 10 行| |tail|用來顯示檔案的**最後幾行**,預設顯示 10 行| |more|用來**分頁顯示**檔案內容的命令,適用於顯示較大的檔案| |less|類似 more,但可以上下滾動並支援搜索功能,更靈活| |cp|<font color="red">c</font>o<font color="red">p</font>y :要被複製的檔案路徑 複製檔的檔案路徑| |rm|<font color="red">r</font>e<font color="red">m</font>ove| |rmdir|<font color="red">r</font>e<font color="red">m</font>ove <font color="red">dir</font>ectory ([與 `rm -r ` 差異](https://teamtreehouse.com/community/rm-r-vs-rmdir))| |mv|<font color="red">m</font>o<font color="red">v</font>e| ### pwd 顯示當前目錄位置 <font color="red">p</font>rint <font color="red">w</font>orking <font color="red">d</font>irectory <br>![image](https://hackmd.io/_uploads/SyLtNXppA.png) *** ### ls 將當前目錄底下的檔案列出來 <font color="red">l</font>i<font color="red">s</font>t ![image](https://hackmd.io/_uploads/B15fr7apC.png) 開頭為`.`的為隱藏檔案,使用`ls -a`即可看到![image](https://hackmd.io/_uploads/B165Lmap0.png) ->想看到更多詳細資訊,用`ls -l`顯示詳細資訊![image](https://hackmd.io/_uploads/ryr_PQTaA.png) ->組合技`ls -la`,顯示詳細資訊+隱藏檔案![image](https://hackmd.io/_uploads/BydG_7TTA.png) **其中含義** ![image](https://hackmd.io/_uploads/BJVYGEa6C.png) 1. `白色` **檔案類型與權限(Mode)**:第一個字元表示檔案的類型: * -:一般檔案(regular file) * d:目錄(directory) * l:符號連結(symbolic link) * b:區塊設備檔案(block device file) * c:字元設備檔案(character device file) 2. `紅色` 隨後的 9 個字元分為 3 組,分別表示檔案擁有者、群組、其他使用者的讀取、寫入與執行權限: * r:讀取權限(read) * w:寫入權限(write) * x:執行權限(execute) 3. `橘色`**連結數量(Links)**: 顯示這個檔案或目錄的連結數量。 4. `黃色`**擁有者(Owner)**: 檔案的擁有者名稱。 5. `綠色`**群組(Group)**: 檔案所屬的群組名稱。 6. `藍色`**檔案大小(Size)**: 檔案的大小,以位元組(bytes)為單位。 7. `粉色`**最後修改時間(Timestamp)**: 檔案最後修改的日期和時間。格式為月、日和時間。如果修改時間超過一年,會顯示年份而非時間。 8. `紫色`**檔案名稱(Name)**: 檔案或目錄的名稱。如果是符號連結,會顯示連結到的目標。 :::info #### 檔案時間參數 * mtime(modification time) * 當該檔案的『內容資料』變更時,就會更新。 * ctime(status time) * 當該檔案的『狀態 (status)』改變時,就會更新這個時間 * 像**權限**與**屬性**被更改了,都會更新這個時間。 * atime(access time) * 當『該檔案的內容被取用』時,就會更新這個讀取時間 (access)。 * 像使用 cat 去讀取,就會更新該檔案的 atime 。 ::: * `ls -r`: 以反向排序列出檔案 * `ls -R`: 列出目錄下所有檔案,包含目錄下的資料夾內的所有檔案 * `ls -t`: 依照檔案建立時間列出 * `ls -S`: 依照檔案大小排序 :::success #### 牛刀小試 試試`ls -rRts`? ::: *** ### chmod 更改檔案或目錄權限 chmod 命令用來更改檔案或目錄的權限(讀取、寫入、執行)。 權限模式: - `r`:讀取權限(4)。 - `w`:寫入權限(2)。 - `x`:執行權限(1)。 ```bash= chmod 755 filename # 將權限設為 rwxr-xr-x(所有者可讀寫執行,群組和其他人可讀執行) # 每個權限使用一個數字來表示,三位數分別代表所有者、群組、其他人的權限,權限位可以疊加。 chmod u+w filename # 給檔案擁有者增加寫入權限 ``` 權限分為所有者(user)、群組(group)、其他人(others)三類。 :::info 如果你執行 ```bash= ls -ld /tmp ``` 你應該能看到類似這樣的輸出: ![image](https://hackmd.io/_uploads/BJD5m9-R0.png) 注意最右邊的有個 t,這叫做 sticky bit,一種特殊的 bit,它的主要作用是限制檔案的刪除權限。 **Sticky Bit 的作用** 當 sticky bit 被設定在一個目錄上時,該目錄內的檔案和子目錄只能由以下幾類使用者刪除或重命名: - 檔案的所有者。 - 目錄的所有者。 - root 超級使用者。 即使其他使用者擁有該目錄的**寫入(read)權限**,他們也不能**刪除或修改他人建立的檔案**。這在像 `/tmp` 這種目錄中特別有用,因為它可以防止使用者之間相互刪除檔案。 **這種權限被設定成 `1777`** ::: ### chgrp 改變所屬群組 要被改變的群組名稱必須要在`/etc/group`檔案內存在。 ```bash= chgrp mygroup filename # 將檔案的群組所有權改為 mygroup ``` ### chown(Change Owner) `chown` 命令用來更改檔案或目錄的所有者和/或群組。 ```bash= chown myowner filename # 將檔案的群組所有權改為 mygroup ``` ### adduser & useradd `adduser` 和 `useradd` 兩個都是用來新增使用者的命令,雖然功能相似,但還是有些不同。 - `adduser` 是功能比較多的命令,它會自動建立家目錄、設定密碼等。 - `useradd` 需要手動設定選項。它不會自動建立家目錄或設定密碼。 ```bash= sudo adduser newuser # 添加新使用者 newuser sudo useradd -m newuser # 創建新使用者並自動創建家目錄 # 通常會搭配 passwd 命令來設定新使用者的密碼: sudo passwd newuser ``` ### UID、GID 概念 - **UID(User Identifier)**:在 Linux/Unix 系統中,每個使用者都有一個唯一的使用者ID(UID)。這是系統用來識別每個使用者的方式。 - UID 0 通常是root(超級使用者)。 查看某個使用者的 UID: ```bash= id -u username # 查看使用者 username 的 UID ``` - **GID(Group Identifier)**:每個群組都有一個唯一的群組ID(GID)。檔案的群組所有權由其 GID 來決定。 查看某個使用者的 GID: ```bash= id -g username # 查看使用者 username 的 GID ``` 查看檔案的 UID 和 GID: ```bash= ls -l filename # 列出檔案的詳細信息,包括所有者 UID 和群組 GID ``` :::info - 小 LAB - `vim printUid.c` - ```c= #include <stdio.h> #include <unistd.h> int main() { printf("The uid is: %d\n", geteuid()); return 0; } ``` - `sudo apt install gcc` - `gcc printUid.c -o printUid` - `./printUid` - `sudo chown root printUid` - `sudo chmod 4755 printUid` - `./printUid` ::: *** :::spoiler cd 切換路徑 ### cd 切換路徑 <font color="red">c</font>hange <font color="red">d</font>irectory ![image](https://hackmd.io/_uploads/ByZ9d7paA.png) * `cd ..`:可以回到上一個目錄 * `cd .`:當前目錄 * `cd -`:前一個工作目錄 * `cd ~`: 當前 user 的家目錄, 直接下 cd 也可以回家目錄 *** ::: ### mkdir 建立資料夾 <font color="red">m</font>a<font color="red">k</font>e <font color="red">dir</font>ectory ![image](https://hackmd.io/_uploads/rJRWiXTpA.png) *** ### touch 新增檔案 ![image](https://hackmd.io/_uploads/Skr9hE6pC.png) ::: info **文字編輯** #### nano 指令`nano <檔名>.txt`進入文字編輯,開始撰寫內容。 要離開的話,下方已經很好心的提示我們怎麼離開:^X Exit > 這邊的 ^ 是 ctrl 的意思,在 linux 環境裡面是很常見的縮寫方式。 ![image](https://hackmd.io/_uploads/By1FR46pC.png) 按下 ctrl + X 之後,nano 會提示是否要存檔,依據指示設定存檔格式之後,就可以看到剛剛建立的檔案了。 --- #### vim 指令`vim <檔名>.txt`,進入vim。 vi 共分為三種模式,分別是『一般指令模式』、『編輯模式』與『指令列命令模式』。 - 一般指令模式 (command mode):一打開就直接進入(預設模式),可以刪除、複製、貼上檔案內的文字,無法編輯檔案內容。 - 編輯模式 (insert mode):在一般模式當中,輸入『i, I, o, O, a, A, r, R』後才會進入編輯模式,離開時按Esc即可回到一般指令模式。 - 指令列命令模式 (command-line mode):在一般模式當中,輸入『 : ,/, ? 』三個中的任何一個按鈕進入指令列命令模式,對檔案進行讀取、存檔、大量取代字元、離開 vi 、顯示行號等等的動作。 :::spoiler 三種模式關係圖 ![image](https://hackmd.io/_uploads/H1tnzIxCA.png) [圖鏈來源](https://linux.vbird.org/linux_basic/centos7/0310vi.php) ::: *** ### cat 印出檔案內容 con<font color="red">cat</font>enate ![image](https://hackmd.io/_uploads/SJcQ1HpaR.png) *** ### head 顯示檔案的前面幾行 head 命令用來顯示檔案的前面幾行。 預設情況下,head 顯示檔案的前 10 行,但可以使用選項來指定顯示的行數。 ```bash= head filename.txt # 顯示前 10 行 head -n 5 filename.txt # 顯示前 5 行 ``` *** ### tail 顯示檔案的最後幾行 tail 命令用來顯示檔案的最後幾行。 與 head 相似,預設顯示最後 10 行,並可透過選項調整顯示行數。此外,tail 還可以持續監控檔案末尾的變動,常用於日誌檔案的實時監控。 ```bash= tail filename.txt # 顯示最後 10 行 tail -n 20 filename.txt # 顯示最後 20 行 tail -f logfile.log # 實時監控檔案的變動(常用於監控日誌) ``` *** ### more 分頁顯示檔案內容 more 是一個用來分頁顯示檔案內容的命令,適用於顯示較大的檔案。 它會一次顯示一頁的內容,按空格鍵可以繼續往下看,但只能從上往下查看,不能返回。 ```bash= more filename.txt ``` - 按下 `空格鍵` 向下翻一頁。 - 按下 `Enter` 向下翻一行。 - 按下 `q` 退出。 *** ### less 上下滾動查看檔案內容 less 命令功能與 more 相似,但比 more 更加靈活。less 可以上下滾動查看檔案內容,並且不需要一次將整個檔案加載到內存中,因此在查看大檔案時非常有效率。 ```bash= less filename.txt ``` - 使用 `Page Up` 和 `Page Down` 進行翻頁。 - 使用 `q` 退出。 - 搜尋功能,按下 `/` 鍵後輸入搜尋字串,並按 `n` 查找下一個。 *** ### cp 複製檔案 <font color="red">c</font>o<font color="red">p</font>y :要被複製的檔案路徑 複製檔的檔案路徑 (source to destination) ![image](https://hackmd.io/_uploads/S1UQzH6pC.png) * `cp -r`:複製資料夾(r = recursive) * `cp -p`: 連同檔案的權限、擁有者、時間都複製 -> 常用於備份 *** ### mv 移動檔案(剪下貼上)/重新命名 <font color="red">m</font>o<font color="red">v</font>e ![image](https://hackmd.io/_uploads/SJEDISa60.png) *** ### rm 刪除檔案 <font color="red">r</font>e<font color="red">m</font>ove ![image](https://hackmd.io/_uploads/B1VkQraaA.png) * `rm -r`:刪除資料夾(r = recursive) * `rm -rf`:可<font color="red">強制</font>刪除檔案,<font color="red">要小心使用!</font> :::danger **摧毀系統(電腦)的指令** ```bash= rm -rf --no-preserve-root / ``` 沒試過,但感覺很酷:D ::: > `rmdir`與`rm -r`的差異: > `rmdir` only works if the folder is empty. `rm -r` will remove the folder and everything inside of it. *** ### echo 將字串輸出到終端上 ![image](https://hackmd.io/_uploads/HkwBF8p60.png) * `echo -n`:不換行 * `echo *.副檔名`:印出所有的‘.副檔名‘檔案 * 使用指令 `echo $PATH` 印出 PATH 環境變數 * path:系統要到哪些路徑底下找執行檔 * 內容全部都是路徑,每個路徑之間用分號( ; )隔開 * ![image](https://hackmd.io/_uploads/SyfKkiWAR.png) * 使用指令 `echo $$` 印出當前 shell 的 pid (process id) :::info 在前面我們有提到 > 每個執行的Process都被表示為檔案,可以在/proc目錄下找到相應的檔案,如/proc/{PID}/status和/proc/{PID}/cmdline。 那我們在的終端機裡打指令,終端機也會有一個 pid,而查看當前終端機 pid 的方法就是`echo $$` 除此之外,在 Linux/Unix 系統中,`top` 和 `ps` 則是可用來監控和管理 process 的兩個重要工具 **top** 的主要功能: - 顯示系統當前狀態:包括 CPU 使用率、RAM 使用情況、正在運行的 Process 數量等 - 動態更新:每隔幾秒鐘(預設是 3 秒)自動更新 - 按需排序和篩選:可以根據 CPU 使用率、RAM 使用等指標排序,查看最消耗資源的 Process - 與 Process 交互:可以直接在 `top` 界面中發送信號(如 `kill`)來終止Process。 **ps** 只會顯示命令執行時的系統狀態(靜態),不會持續更新 **ps** 的主要功能: - 列出 Process 狀態:包括 Process 的 PID、狀態、CPU 和 RAM 使用等。 - 靜態輸出:與 `top` 不同,`ps` 是靜態的,顯示當前某一刻的系統狀態,不會自動刷新。 - 過濾和篩選進程:可以通過各種選項篩選、過濾或格式化輸出 Process 資訊。 ```bash= ps aux # 列出所有進程的詳細信息 ps -ef # 顯示進程的完整格式 ps -u username # 列出特定使用者的進程 ps -p PID # 顯示特定進程的詳細信息 ``` ::: *** ### history 顯示用戶執行過的命令歷史 ```bash= history ``` ### sl - 重要套件 - 會考會考歐 ```bash sudo apt install sl ``` *** :::spoiler df -h ### df -h -> zfs 截ext4的圖 介紹欄位、意思,尤其是**mount on** 哪個partition掛在哪個掛載點 ->較好去修復壞掉的儲存裝置 ![image](https://hackmd.io/_uploads/ryhTCxyR0.png) - 有隨身碟掛載點 - 有 nfs - Synology NAS to Ubuntu with ZeroTier One(VPN) - 所以 IP 才會是 `192.168.193.64`,可自己設定 ::: :::spoiler lsblk ### lsblk ![image](https://hackmd.io/_uploads/SyHXlZ1CC.png) ::: :::spoiler 需補的指令 需補的指令 * su ->重要! * grep->(簡單的)正規表達式 ->蓬萊人偶 * alias * awk * mktmp * ^r:搜尋之前用過的指令 * suid、sgid ->小lab一起->sticky bit一起提 需補參數 * \>、>> ->蓬萊人偶 stdin、stdout、stderror ::: :::info 好康的分享 - Ubuntu Dock like Windows(點一下左邊應用程式圖示(Ex. Firefox)可以打開和最小化視窗) [name=RegChien] `gsettings set org.gnome.shell.extensions.dash-to-dock click-action 'minimize'` ::: :::danger 助教的筆記 1. /boot 是 bootstrap? 電腦自己會載入/boot再找到映像檔(? 2. inode 1 是什麼?為什麼root不是1? 保留給虛擬檔案,指到1的都沒有儲存在硬碟上 ![image](https://hackmd.io/_uploads/Hy0j_W1AR.png) [資料來源](https://ext4.wiki.kernel.org/index.php/Ext4_Disk_Layout#Special_inodes) [資料來源2](https://unix.stackexchange.com/questions/198673/why-does-have-the-inode-2) 3. inode怎麼教? 在ls教 4. cd 是builtin,why? 改變pwd,切換環境(working directory) 5. `sudo -i` 為什麼是打使用者的密碼,那這樣大家都打各自的密碼都能到root? 要有sudo權限才可以(創使用者時可將該使用者拔除sudo權限) 6. 救援檔案->檔案會存在硬碟內(資料沒有被馬上刪除)->mtime影響 7. etc/skel -> 放骨架。創建新使用者時,此檔案內的資料會一併複製到新使用者家目錄。 :::