1.前言
在使用 Ubuntu 系統時,可能會遇到無法安裝套件的問題,導致系統無法正常更新或安裝其他軟體。本文將詳細分析該問題的原因,並提供有效的解決方案。
(這個問題花了2天多才找到解決方案,搭配一張頭快爆炸的圖,以形容當時的情況)
2.問題描述
在執行 sudo apt install -f 命令嘗試修復損壞的套件時,出現以下錯誤訊息:
Reading package lists... Done
Building dependency tree... Done
Reading state information... Done
The following additional packages will be installed:
libc6
Suggested packages:
glibc-doc debconf | debconf-2.0 locales libnss-nis libnss-nisplus
The following packages will be upgraded:
libc6
1 upgraded, 0 newly installed, 0 to remove and 0 not upgraded.
35 not fully installed or removed.
Need to get 3265 kB of archives.
After this operation, 13.8 MB of additional disk space will be used.
Do you want to continue? [Y/n] y
Get:1 http://security.ubuntu.com/ubuntu noble-security/main amd64 libc6 amd64 2.39-0ubuntu8.3 [3265 kB]
Fetched 3265 kB in 6s (571 kB/s)
debconf: delaying package configuration, since apt-utils is not installed
dpkg: warning: files list file for package 'gcc-11-base:amd64' missing; assuming package has no files currently installed
dpkg: warning: files list file for package 'manpages-dev' missing; assuming package has no files currently installed
dpkg: warning: files list file for package 'gcc-14-base:amd64' missing; assuming package has no files currently installed
dpkg: warning: files list file for package 'manpages' missing; assuming package has no files currently installed
dpkg: warning: files list file for package 'binutils-common:amd64' missing; assuming package has no files currently installed
dpkg: warning: files list file for package 'linux-libc-dev:amd64' missing; assuming package has no files currently installed
dpkg: warning: files list file for package 'gcc-12-base:amd64' missing; assuming package has no files currently installed
(Reading database ... 0 files and directories currently installed.)
Preparing to unpack .../libc6_2.39-0ubuntu8.3_amd64.deb ...
dpkg (subprocess): unable to execute new libc6:amd64 package pre-installation script (/var/lib/dpkg/tmp.ci/preinst): Permission denied
dpkg: error processing archive /var/cache/apt/archives/libc6_2.39-0ubuntu8.3_amd64.deb (--unpack):
new libc6:amd64 package pre-installation script subprocess returned error exit status 2
dpkg (subprocess): unable to execute new libc6:amd64 package post-removal script (/var/lib/dpkg/tmp.ci/postrm): Permission denied
dpkg: error while cleaning up:
new libc6:amd64 package post-removal script subprocess returned error exit status 2
Errors were encountered while processing:
/var/cache/apt/archives/libc6_2.39-0ubuntu8.3_amd64.deb
needrestart is being skipped since dpkg has failed
E: Sub-process /usr/bin/dpkg returned an error code (1)
3.問題分析
根據錯誤訊息,主要有以下幾點需要關注:
1.權限被拒絕(Permission denied):以安裝libc6套件為例
dpkg (subprocess): unable to execute new libc6:amd64 package pre-installation script (/var/lib/dpkg/tmp.ci/preinst): Permission denied
這表明在執行 libc6套件的預安裝腳本時,權限被拒絕,導致安裝過程無法繼續。
2.dpkg 資料庫異常:
dpkg: warning: files list file for package 'gcc-11-base:amd64' missing; assuming package has no files currently installed
正常情況下,系統應有數千個已安裝的檔案和目錄,但這裡顯示為 0,可能表示 dpkg 資料庫損壞或無法存取。
3.缺少檔案列表檔案:
dpkg: warning: files list file for package 'gcc-11-base:amd64' missing; assuming package has no files currently installed
這意味著 dpkg 無法找到已安裝套件的檔案列表,進一步說明套件管理系統存在問題。
4.可能原因
- 掛載選項導致權限問題:/var 分區被掛載為 noexec,禁止在該分區執行任何腳本或二進位檔案。 [CIS的設定,版主就是為這個所苦,所有修復指令都下了,還是無法解決,最後才找到這個原因]
- 檔案系統權限錯誤:關鍵目錄或檔案的權限設定不正確,導致無法執行安裝腳本。
- dpkg 資料庫損壞:套件管理器無法正確讀取已安裝套件的資訊。
- 檔案系統錯誤:磁碟或檔案系統存在錯誤,導致檔案遺失或權限異常。
5.解決方案
步驟一:檢查掛載選項
首先,檢查 /var 及其子目錄是否被掛載為 noexec。
mount | grep ' /var'
如果輸出類似以下內容,表示存在 noexec 選項:
/dev/sdc1 on /var type ext4 (rw,nosuid,nodev,noexec,relatime)
/dev/sdc4 on /var/audit type ext4 (rw,nosuid,nodev,noexec,relatime)
/dev/sdc3 on /var/log type ext4 (rw,nosuid,nodev,noexec,relatime)
/dev/sdc2 on /var/tmp type ext4 (rw,nosuid,nodev,noexec,relatime)
步驟二:臨時移除 noexec 選項
為了允許執行必要的安裝腳本,需臨時移除這些分區的 noexec 選項。
sudo mount -o remount,exec /var
sudo mount -o remount,exec /var/tmp
sudo mount -o remount,exec /var/log
sudo mount -o remount,exec /var/audit
步驟三:驗證掛載選項已更改
再次執行以下命令,確認 noexec 已被移除:
mount | grep ' /var'
輸出應不再包含 noexec,例如:
/dev/sdc1 on /var type ext4 (rw,nosuid,nodev,relatime)
/dev/sdc4 on /var/audit type ext4 (rw,nosuid,nodev,relatime)
/dev/sdc3 on /var/log type ext4 (rw,nosuid,nodev,relatime)
/dev/sdc2 on /var/tmp type ext4 (rw,nosuid,nodev,relatime)
步驟四:重新嘗試安裝
現在,可以重新嘗試安裝 libc6 套件:
sudo apt install -f
此時,安裝過程應能正常進行,不會再出現權限被拒絕的錯誤。
步驟五:永久解決方案
為了防止在系統重啟後問題再次出現,需要修改 /etc/fstab 檔案,移除 noexec 選項。
1.備份 /etc/fstab 檔案:
sudo cp /etc/fstab /etc/fstab.bak
2.編輯 /etc/fstab:
sudo nano /etc/fstab
找到與 /var 及其子目錄相關的行,移除 noexec 選項。例如,將以下內容:
/dev/sdc1 /var ext4 defaults,nosuid,nodev,noexec 0 2
/dev/sdc2 /var/tmp ext4 defaults,nosuid,nodev,noexec 0 2
/dev/sdc3 /var/log ext4 defaults,nosuid,nodev,noexec 0 2
/dev/sdc4 /var/audit ext4 defaults,nosuid,nodev,noexec 0 2
修改為:
/dev/sdc1 /var ext4 defaults,nosuid,nodev 0 2
/dev/sdc2 /var/tmp ext4 defaults,nosuid,nodev 0 2
/dev/sdc3 /var/log ext4 defaults,nosuid,nodev 0 2
/dev/sdc4 /var/audit ext4 defaults,nosuid,nodev 0 2
重新掛載分區:
sudo mount -o remount /var
sudo mount -o remount /var/tmp
sudo mount -o remount /var/log
sudo mount -o remount /var/audit
步驟六:修復 dpkg 資料庫
如果仍有錯誤提示,可以嘗試修復 dpkg 資料庫:
sudo dpkg --configure -a
sudo apt update
sudo apt upgrade
步驟七:考慮安全策略
如果是根據 CIS(Center for Internet Security) 基準進行系統配置,使用了 noexec 選項,可以編寫腳本在需要時臨時移除 noexec,並在操作完成後自動恢復。例如:
#!/bin/bash
# 定義需要處理的分區
PARTITIONS=("/var" "/var/tmp" "/var/log" "/var/audit")
# 臨時移除 noexec
for partition in "${PARTITIONS[@]}"; do
sudo mount -o remount,exec "${partition}"
done
# 在此處執行您的安裝或更新操作
sudo apt install -f
# 等待 10 分鐘後自動恢復 noexec
sleep 600
# 恢復 noexec
for partition in "${PARTITIONS[@]}"; do
sudo mount -o remount,noexec "${partition}"
done
6.結論
導致無法安裝 libc6 套件的主要原因是系統分區被掛載為 noexec,導致無法執行必要的安裝腳本。通過臨時移除 noexec 選項並修改 /etc/fstab 檔案,問題得以解決。
在實施安全策略時,需要在安全性和系統功能性之間找到平衡。可以通過編寫腳本的方式,在需要時臨時調整系統配置,確保系統既安全又能正常運行。
轉貼本文時,需註明來自黑修斯的隨手札記原創作者 hughes chen(黑修斯),及附上原文連結,同時 禁止修改,禁止商業使用 。
0 留言
不一定能即時回覆問題,有時間會盡量答覆。