案例專題

回復管理員權限

使用者會因誤操作而導致管理者喪失管理員權限。筆者使用 linux 的時間不長就已遇過一次。請參考底下連結應就可救回來了。

  1. https://www.tecmint.com/fix-user-is-not-in-the-sudoers-file-the-incident-will-be-reported-ubuntu/
  2. https://www.ostechnix.com/how-to-restore-sudo-privileges-to-a-user/

重置 root 密碼

Claude-code / 2026-09-25

跟上面「回復管理員權限」不同:上面那段解決的是「使用者被踢出 sudoers 檔案,導致 sudo 指令失效」;這裡要解的是「連登入密碼本身都忘記了」,兩者處理方式不同。這是實體機器(有螢幕鍵盤能操作,或有機房 KVM/IPMI)情境下的標準做法,透過 GRUB 開機選單進入救援模式,不需要知道原密碼即可重設,前提是要有機器的實體存取權(這正是這個方法的風險所在,任何能碰到開機畫面的人都能用同一招重設密碼,所以機房/機殼實體安全要顧好)。

步驟
  1. 重開機,在開機畫面看到 GRUB 選單時按方向鍵停在上面(若沒自動出現,開機當下按住 Shift,UEFI 機器則按 Esc 多按幾下)。
  2. 選單裡找「Advanced options for Ubuntu」,進去選帶有 (recovery mode) 字樣的那個核心版本,按 Enter。
  3. 進入 Recovery Menu 後,選 root Drop to root shell prompt,會拿到一個沒有密碼就能用的 root shell。
  4. Recovery 模式下根目錄預設是唯讀掛載,先重新掛成可寫:
mount -o remount,rw /
  1. 設定新密碼(把 username 換成要重設的帳號名稱,要重設 root 本身就打 root):
passwd username
  1. 輸入兩次新密碼後,重開機即可用新密碼登入:
reboot -f

若 GRUB 選單本身有另外設密碼保護(多數家用/個人機器不會特別設),要先知道那組 GRUB 密碼或用其他方式(例如拆機掛硬碟到別台機器上改)才能進到這一步;若磁碟本身有全碟加密(LUKS),流程會不同,要先能通過開機時的磁碟解密才進得了 GRUB 選單後面的步驟。

喚醒遠端電腦-WoL

WakeOnLan/WoL,WakeOnWirelessLan/WoW
因筆者的無線網路卡都不支援 WoW,所以於此只介紹 WoL
簡單講,就是在區域網路內,本地端廣播 magic packet,其包含著目的地端網卡的 MAC address,讓同在區網內,關機狀態下的遠端電腦開機。這有幾個前提:

  • 網卡本身支援 WoL (十年內的網卡應都已支援)
  • BIOS 支援 WoL,並啟用該設定(BIOS 更早就已支援)。通常在電源管理的選項內
  • 作業系統下啟用 WoL
  • 能發送 magic packet 的程式

在 Linux 系統下,常見的就是兩支程式,一支用來啟用 WoL,即 ethtool。另一支 wakeonlan 用來發送 magic packet 喚醒關機狀態的電腦。此外 wakeonlan 還支援使用 ip address / hostname 來發送,即 WoWan,也就是可以從網際網路穿透區域網路到達欲喚醒的電腦。WoL/WoW/WoWan/WoWWan 其都必須提供網卡的 MAC address 以做為明確的目的地端。wakeonlan 使用預設的 UDP port 9 來發送。也可自訂例如 UDP port 7。而 Android 便有很多的 apps 就有類似 wakeonlan 的功能與設定。
此外,筆者的兩台電腦 WoL 都存在 fail-rate 的,也就是不總是可成功喚醒。且參考資料的方法都試過了仍未解。其可能的原因:

  • BIOS,亦即主板的 bug
  • 網卡或其 driver 的 bug
  • 喚醒的 magic packet 中途遺失。換言之喚醒的動作最好多下幾次。
  • 關機後,可透過查看網卡埠的燈號有亮著則應可喚醒(但沒亮仍可能可,隨網卡之設計)。然而在此可喚醒狀態下,源頭斷電,例如停電,那麼復電後,電腦是不可能再被喚醒的。
  • 簡單講,一般預設下,不做任何設定,順利的話,用以下指令便可喚醒:
    wakeonlan -i waterfalls.ddns.net -p 9 3A:12:55:B2:11:02
    或
    wakeonlan 3A:12:55:B2:11:02

使用 ethtool

首先我們先取得運作中的卡,執行 ip a 會得到如圖的結果。我們看到有實體三張卡,藍框處,enp3s0,enp5s0 是有線網卡,wlp2s0 是無線網卡。紅線處有被指定區網 ip 也就是 active 運作中的卡。因此我想透過有線來喚醒,圖中的 enp5s0 記住這個網卡的識別名及它的 MAC address,在綠框中,會是如 3A:12:55:B2:11:02 這樣的形式。

  • 安裝 ethtool
  • sudo apt install ethtool
  • 啟用 WoL
  • sudo ethtool -s enp5s0 wol g
  • 查詢是否已啟用
  • sudo ethtool enp5s0

看到 wake-on: g 就表示已啟用成功了。不過這只是手動,一次性的。我們希望每次開機後都能執行一次。很多種方法,以下列出其一。

使用 systemd service

建立以下內容的檔案,並取名為 mywol.service。記得內容的 enp5s0 改成您的網卡名。

[Unit]
Description=Configure Wake On LAN

[Service]
Type=oneshot
ExecStart=/sbin/ethtool -s enp5s0 wol g

[Install]
WantedBy=basic.target
  • 接著執行:
  • sudo chown root:root mywol.service
  • sudo mv mywol.service /etc/systemd/system/
  • sudo systemctl daemon-reload
  • sudo systemctl enable mywol.service
  • sudo systemctl start mywol.service
  • 這樣就全設定完成了。

使用 wakeonlan

  • sudo apt install wakeonlan
  • 當使用 magic packet 在區網廣播時,使用的是如上列的 enp5s0 的 MAC address
  • wakeonlan 3A:12:55:B2:11:02
  • 走網際網路時,請記得,撥接寬頻和 IP 分享器都要開啟 port forwarding
  • 若 https://waterfalls.ddns.net 的 ip address 是 61.70.169.189 且使用 UDP port 7 的話,則如下兩種下法:
  • wakeonlan -i waterfalls.ddns.net -p 7 3A:12:55:B2:11:02
  • wakeonlan -i 61.70.169.189 -p 7 3A:12:55:B2:11:02
  • 當然,wakeonlan 是用在別台電腦,喚醒您這台已關機的電腦的。

參考資料

  1. https://blog.gtwang.org/linux/linux-basic-systemctl-systemd-service-unit-tutorial-examples/
  2. https://zhuanlan.zhihu.com/p/51357835
  3. https://www.cyberciti.biz/tips/linux-send-wake-on-lan-wol-magic-packets.html
  4. https://kmmr.pixnet.net/blog/post/35347778
  5. https://superuser.com/questions/205468/ethtool-wol-what-does-wake-on-physical-activity-actually-mean-and-how-can
  6. https://www.cyberciti.biz/faq/configure-wireless-wake-on-lan-for-linux-wifi-wowlan-card/
  7. https://askubuntu.com/questions/764158/how-to-enable-wake-on-lan-wol-in-ubuntu-16-04
  8. https://wiki.debian.org/WakeOnLan
  9. https://bbs.archlinux.org/viewtopic.php?id=243461
  10. https://askubuntu.com/questions/1053302/wake-on-lan-not-working-if-i-turn-of-with-ubuntu
  11. https://ubuntuforums.org/showthread.php?t=2233674
  12. https://askubuntu.com/questions/138445/wake-on-lan-worked-3-times-then-no-more

無法正常關機或重開機

筆者的電腦當執行 reboot 或關機,就會停住,電源還 ON 著。筆者的此狀態應是 Linux 已結束掉所有行程,只差了一個系統關電的動作。因此透過以下的修改,便可順利重開機或關機了。

  • 在此檔內容找尋以下設定
  • /etc/default/grub
  • GRUB_CMDLINE_LINUX_DEFAULT=”quiet splash”
  • 先修改成所建議的以下設定
  • GRUB_CMDLINE_LINUX_DEFAULT=”quiet splash acpi=force”
  • 測試結果,失敗,從而再改成這樣
  • GRUB_CMDLINE_LINUX_DEFAULT=”acpi=force”
  • 存檔離開並執行
  • sudo update-grub

參考資料:https://askubuntu.com/questions/764568/ubuntu-16-04-hangs-on-shutdown-restart

使用 command line 開關 wlan

  • 因筆者嘗試過兩台電腦,應對的情況並不一致。故命令及說明,皆僅供參考。
  • 此用法是在至少有一組 ssid,password,已被提供且已被收錄的前題下,並且此 AP 是正存在可被存取的。以下做的,只要開關,就能連上 AP。
  • ifconfig -a 可查看包含有線及無線網路卡的當下設定。同理 iwconfig 也可。
  • iwconfig + 無線網卡名,則可查看無線網卡當下的狀態。例如 iwconfig wlp3s0,iwconfig wlan0
  • 承上,我們先前在 GUI 上關閉了無線網路,特別注意 TX-Power 欄位,是 i dBm 或是 off,若是 i dBm 則 RF 訊號並沒有被關閉,而有可能三種狀況,已正常連接到 AP,能正常連接到 AP 但並沒有 AP 被搜尋到,或對 AP 的連接網路被關閉。
  • 承上,故我們所要處理的狀況是上述的第三種,以及 off 的狀況。只要下 sudo nmcli radio wifi on 則開啟無線網路並自動搜尋 AP 及連線。sudo nmcli radio wifi off 則關閉。
  • 承上,但即便 on 後,可能狀態沒改變,那就是因為 RF 並未被順道開啟,故下
    rfkill -J list 查看無線裝置,下
    sudo rfkill unblock wlan 開啟 wlan RF,下
    sudo rfkill block wlan 關閉 wlan RF
    sudo rfkill block bluetooth 關閉 bluetooth RF
    同理,nmcli radio wifi off 可能會順道關閉 RF
  • 簡單講,使用 rfkill 只能開關 RF,而 nmcli radio wifi 會啟用停用無線網路連接,且可能會順道開關 RF;即,單執行 nmcli 不見得能順利連上線,因 RF 尚未被打開。
  • 以下另一種用法,摘錄:
  • To see list of saved connections, use (SavedWiFiConn)
    nmcli c
    to disconnect specific AP,nmcli c down (SavedWiFiConn)
    to connect specific AP,nmcli c up (SavedWiFiConn)
    to disconnect WiFi,nmcli d disconnect (WifiInterface)
    to connect WiFi,nmcli d connect (WifiInterface)
  • To see list of available WiFi hotspots (WiFiSSID)
    nmcli d wifi list
    or more realtime detail
    sudo iwlist (WifiInterface) scanning
  • with assignments
    nmcli d wifi connect (WiFiSSID) password (WiFiPassword)
  • 以上兩類用法並不互相重疊,即,首提第一類是源頭的控制,並且此類的兩支指令,rfkill 及 nmcli on/off,後者不見得能將 radio 和 wifi 都打開,故需配合 rfkill 指令。第二類指令最好也使用 sudo 下,而若仍失敗,則是第一類指令未先作用到,須先下。
  • 20220105 追加
    若 wifi 都無法驅動,例如預設安裝 ubuntu server 後,它沒驅動成功 wifi,那麼可能是這套件沒有安裝:wpasupplicant
    其他 network/wireless 工具:networkctl,iwlist

CD-Rom 複製到 USB disk

  • 當我們做這樣的複製的時候可能會有點阻礙,這樣說,CD 片上面的資料的排列,並不見得是複製的順序,即若系統依日期的順序取檔做複製,但 CD 上的排列是以檔名為順序,這表示 CD-Rom 的讀寫頭將有相當頻繁的位移。因此,若能採取最少位移的複製,將是最快速最保險的做法,即,以 raw 的方式做讀取。故我們使用公用程式 dd 來複製。
  • CD-Rom 直接複製到 USB-Disk,如下 script file。
#!/bin/bash


# directly copy cd-rom contents at '/media/ken/$2' to usb-disk at '/media/ken/MyBackups'. where this cd-device is '/dev/sr0'.
# it is assumed that the two devices are mounted at the base-path $THE_BASE=='/media/ken'.
# if the cd-drom would be mounted as 'TheCd', then use "sudo ./this_script.sh ken TheCd" where $2=='TheCd', the user is $1=='ken'.


# modify to as yours.
THE_CDDEV="/dev/sr0"
THE_BASE="/media/ken"
BACKUP_DIR="$THE_BASE/MyBackups"
TMP_DIR="/tmp"


if [ $# -ne 2 ];
then
    echo use "sudo ./this_script.sh user cd-mount-point"
    exit 1
fi

THE_SOURCE="$THE_BASE/$2"
THE_TARGET="${BACKUP_DIR}"
USED_DIR="${TMP_DIR}/$1-created-$2"
BEGIN_TIME=`date`;

sleep 1
echo "======================="
echo "rsyncing ..."
echo ""

mkdir -p $USED_DIR/$2

dd if=$THE_CDDEV of=$USED_DIR/$2.iso bs=$(isoinfo -d -i $THE_CDDEV | grep -i -E 'block size' | sed 's/([^0-9]*)([0-9]*)/2/') count=$(isoinfo -d -i $THE_CDDEV | grep -i -E 'volume size' | sed 's/([^0-9]*)([0-9]*)/2/') status=progress

mount -o loop -o ro $USED_DIR/$2.iso $USED_DIR/$2
rsync -aAXH $USED_DIR/$2 ${THE_TARGET}
umount $USED_DIR/$2
rm -rf $USED_DIR

chown -R $1:$1 ${THE_TARGET}/$2

echo ""
echo "rsync began at:    ${BEGIN_TIME}"
echo "rsync finished at: `date`"
echo ""

ls -la ${THE_TARGET}/$2/
echo ""
du -sh ${THE_TARGET}/$2/
echo ""
  • 基於上述之情境,我們再追加一下學習一下常用指令,
  • 假設,我們以前將資料備份到 cd,有百片之多,現在經由上面處理的方式(較節省時間地)輕易地回存到 usb disk。接著,案例如我們想把壓縮檔中的所有是 pdf 或特定檔案類型的資料取出來,那麼就做如下的操作,但此例並非完整/不符意,可自行融會貫通。
  • 補充:後來弄完整了;做了以下這支 shell script,可以將當前目錄底下以及子目錄以及所有壓縮檔內的再壓縮檔內不管藏得多深,所指定的檔案名稱都能夠列舉出來。用法細節請看檔案內容說明。例如 $> this_shell_script “.*pdf.*”

再補充,
當使用過上面的程式後,我們也順帶瞭解到 sha1sum 的用法。假設有 A,B 兩個不同目錄,我們可以産生(find-all / sha1sum)個別的底下的所有檔案的 checksums。又或是,由上述的程式來獲得類似的東西。
因此,我們可以透過底下這支程式,來將此 A,B 兩個不同來源中,經由比對 checksum 揪出所有相同檔案者。進而例如可以處置以使得 A,B 中不會有重覆存在的檔案。注意這是比對檔案內容(sha1sum)而非檔名,即不同檔名無妨。
還有很重要的一點,checksum 是降維編碼,故 checksum 相同不見得檔案內容全等,當然要遇到此例外的機率很低多低得見該演算法的理論。若資料重要,保險起見還得經 bit-wise 二次比對;反之相異則必然有差異。

其次,the identf,
使用參數 -abcd 後之結果,
帶 “-” 為首者代表對方所欠缺者。
行中僅有 checksum 者代表對方有,己方沒有。
其餘的差異便剩是(每群中之) [[id]] 後的路徑與檔名。

故,吾人可依以上之結果資訊,做進一步處理。例如,使用同一來源(例如 Disk-D)之兩份比對檔 A.txt, B.txt,即 A==B。則結果將可得 Disk D 中所有相同檔案之分群。接著再於各群中做 binary compare,即可挑出所有重覆檔案者。

  • [serf.sh, identf.sh] 這段落是欲改版註記;先註記,再適時改版
  • identf
  • 內容中之使用說明,有一段“前後對調 -> 排序 -> 再對調回來,用了 -k1,1 事實上反而不妥,只要單純 sort 即可(之後之欄位也排序不影響前面已序),參數拿掉。
  • 當雙方同群比對時,只會追尾佔位,應也是須從頭佔位,使得相同者有相同的對應編號。
##### serf.sh example(almost all interested types): ./serf.sh '.*.(zip|rar|ace|arj|t?gz|tar|z|7z|bz2|lzh|txt|ex[e_]{1}|bat|msi|sys|dll|ocx|bin|pdf|djvu|html?|mht|chm|css|csv|js|ps|iso|nrg|gho|ghs|cab|avi|rm(vb)?|jpe?g|bmp|ico|gif|mp[34]{1}|mpe?g|png|doc|ini|hlp|info?|ttf|pptx?|pps|xlsx?|reg|dat|db|bak|log|asm|inc|c(c|pp|xx)?|h(pp)?|lib|aif|amr?|ap[ek]{1}|class|java|conf|deb|fig|flac?|flv|json|mov|php|rpm|sh|sch|stl|svg|vhdl?|wav)$' 'cs' 'null'


##### sudo find ~+ -type f -regextype sed ! -iregex '.*.(zip|rar|ace|arj|t?gz|tar|z|7z|bz2|lzh|txt|ex[e_]{1}|bat|msi|sys|dll|ocx|bin|pdf|djvu|html?|mht|chm|css|js|ps|iso|nrg|gho|cab|avi|rm(vb)?|jpe?g|bmp|ico|gif|mp[34]{1}|mpe?g|png|doc|ini|hlp|inf|ttf|pptx?|pps|xlsx?|reg|dat|db|bak|log|asm|inc|c(pp|xx)?|h(pp)?|lib)' | rev | sort -u -s -t '.' -k1,1 | cut -d "." -f1 | rev | wc -l

# ~+
find 會在當前目錄下預設 recursive 搜尋,若未明確指定時。
結果將會以當前目錄起頭,例如,./CD_101/dat/...
此字串指示將省略的擴展回來,成,/media/ken/MyBackups/CD_101/dat/...

# -regextype sed -regex
以 sed 的 re 的規則進行搜尋,iregex 表示忽略大小寫/皆可。

# !
互補搜尋,即搜出所不符合者/not match。

# (sub_str1|sub_str2)
符合 sub_str1 或 sub_str2 者。
注意都要加脫離字元,之後不再強調。
而括號也可用以做為之後的向前索引,依出現的順序對應,/(A)(B)(C)(D)/3 2 1 4/,1 代表 A 依此類推。

# ?
前鄰接字元出現 0 個或 1 個。

# {n}
前鄰接字元出現恰好 n 個,n>=1。

# [abc0-9]
指定範圍或當中字元。所代表者僅一個可能字元。

# rev
將字串反轉,"abcd" 成 "dcba"

# sort -u -s -t 'x'
-u unique
-s stable,序後維持出現的先後次序當二者相等時。故其實 -u -s 合用無意義。
-t 'x' delimiter,單個字元,預設是空白字元。
-k 指定欄位。x,y 表示欄位 x 到欄位 y。x.u,y.v 表示欄位中第 u 字元開始到第 v 字元。xyuv >=1。(未求證)

# cut -d "." -f1
-d delimiter
-f1 保留第一欄位。
-f3- 保留第三欄位及以後。


##### sudo find ~+ -type f -regextype sed -iregex '.*.(zip|rar|ace|arj|t?gz|tar|z|7z|bz2|lzh|ex[e_]{1}|iso)' | rev | sort -s -t '.' -k1,1 | rev | sed 's/(.*)/"1"/' | xargs -t -n1 7z l 2>/dev/null | grep -i ".pdf$"

# sed 's/(.*)/"1"/'
將例如 abc d 加上雙引號 "abc d"。
這一行應是不可以用 xargs -0 來取代。因為即便能取出 abc d 為一 token 但終究沒有雙引號,後續處理,其空格仍有影響力。

# xargs -t -n1 other_command
適當地整理並將參數餵給 other_command
-0 將給定的那行字串附加 "" 結尾。
-t verbose
-nx x>=1,預設是所有參數以空白隔開。此表示依序將每 x 個參數弄成一行。
所以上頭所謂取代,不可以表示成 xargs -0 | xargs -n1

# 2>/dev/null 將錯誤輸出導向 null/不輸出

# 2>&1 將錯誤輸出導向標準輸出/合併

# sed -n '/Date/,/files/p' 抑制自動輸出,指定印出從符合 Date 開始到符合 files 結束。
# sed -n '123,456p;456q' 抑制自動輸出,指定印出從第 123 行開始到 456 行停止。到 456 行結束。
# sed -n '123,$p;456q' 抑制自動輸出,,指定印出從第 123 行開始到檔尾停止。一到 456 行或已檔尾便結束。

# reference: https://www.mankier.com/1/find (since it is nice to have examples)
# https://www.junmajinlong.com/shell/find_usage/
# https://www.junmajinlong.com/shell/find_intermediate/
# https://unix.stackexchange.com/questions/379181/escape-a-variable-for-use-as-content-of-another-script
# https://superuser.com/questions/178587/how-do-i-detach-a-process-from-terminal-entirely
# https://unix.stackexchange.com/questions/269805/how-can-i-detach-a-process-from-a-bash-script

Linux errors and fixes or workaround

  • RTKit error: org.freedesktop.DBus.Error.AccessDenied
    https://bugs.archlinux.org/task/70083
    https://gitlab.freedesktop.org/pipewire/pipewire/-/issues/1069
    kw(The workaround that I found is to edit)
  • Intel AX210 “failed to evaluate _DSM” messages
    https://community.intel.com/t5/Wireless/Intel-AX210-quot-failed-to-evaluate-DSM-quot-messages/td-p/1435605

Firefox 之設定搬遷

  • 在 profiles.ini 內有記錄該存放所有設定與記錄與書籤乃至於 cookies & passwords 之資料夾;故連同 profiles.ini 和該資料夾備份起來,可移至/取代另一台電腦上的 firefox 設定,即完成完整的搬遷。路徑之細節如下連結。
  • https://support.mozilla.org/en-US/questions/1065938

如何以特權執行視窗程式

  • 使用 gksudo,不過似已被 ubuntu 捨棄。
  • 故轉而使用 pkexec:export DISPLAY=:0.0 & pkexec meld
    不過通常會出錯,應是環境變數引入不完整。
  • 或 sudo -H meld,其於終端下下 command,通常可成功。
  • 若想要 create icon,點擊特權地執行,可參考 *.desktop 檔案的格式。其放置位置若於 ~/.local/share/applications/ 底下,則可被系統納入選單中供點選。
  • 更細節的解法如下連結。
    https://sites.google.com/site/installationubuntu/home/ubuntu-17-10/alternatives-for-gksu-and-gksudo

多久後執行命令

做了一份腳本,指定 n 秒後 schd(n, cmd),若期間未曾執行 schdc() 以取消之,則將會執行 cmd。這是例如防範遠端時,可能接下來的操作會造成斷線且無以挽救,故以此腳本預備命令來復原之。

Diff colorize

暫停行程

auto-apt/checkinstall

書籤

綜合

  1. 部落格綜合 https://www.blogfuntw.com/
  2. 影片綜合 https://www.youtube.com/channel/UCGRKh-BLOPp_uSAcYGzRn7Q/videos
  3. http://www.wowotech.net/

WordPress 相關

  1. https://www.wp101.com.tw/blog
  2. https://blog.gtwang.org/web-building
  3. https://www.smashingmagazine.com/2016/01/create-customize-wordpress-child-theme/
  4. https://developer.wordpress.org/themes/advanced-topics/child-themes

網頁程式

  1. https://materialmixer.co

CSS

  1. https://css-tricks.com/
  2. https://wordpress.org/support/topic/import-not-allowed-in-additional-css-error/
  3. https://envato.com/blog/css3-typography-code-snippets/
  4. https://winningwp.com/css-for-beginners-where-to-learn-css-from-scratch/
  5. https://mediatemple.net/blog/tips/why-your-custom-css-doesnt-work-in-wordpress-and-how-to-fix-it
PHP Code Snippets Powered By : XYZScripts.com