---
# System prepended metadata

title: Linux
tags: [OS]

---

Linux
===

###### tags: `OS`
[TOC]


### 1. build 'C' code
```
>> g++ -g -o NREBandSeg NREBandSeg.cpp -lm -lstdc++
```


### 2. linux coding style
https://bit.ly/2p3tsrI

### 3. Digital Signature
``` linux=
# 在Linux環境下使用openssl指定e = 3, 1024 bit產生key pair
$ openssl genrsa -3 -out key.pem 1024

# 取出public key並轉成DER的格式
$ openssl rsa -inform PEM -outform DER -in key.pem -pubout -out key.pub


# 在Linux環境下使用openssl對FW(TBM_N1.bin)產生digital signature並指定SHA256及private key
$ openssl dgst -sha256 -sign key.pem -keyform PEM -binary -out sign.bin TBM_N1.bin

# 附加digital signature到FW的檔案後面
$ cat TBM_N1.bin sign.bin > TBM_N1_sign.bin
```

### 4. 修改adduser的家目錄
``` linux=
$ vi /etc/adduser.conf
   >> DHOME=/home2
   
# 變更使用者家目錄路徑 並移動目錄
$ sudo usermod -d /newhome/username -m username
```
https://stackoverflow.com/questions/20797819/command-to-change-the-default-home-directory-of-a-user


### 5. mount linux掛載硬碟
``` linux=
# 顯示目前系統硬碟的使用情形
$ df -h

# 新硬碟在這裡是看不到的，因為我們都還沒開始分割，看看 /dev 下所有的硬碟情況
$ ls /dev/[sh]d*

# 格式化硬碟格式
$ mkfs -t ext4 /dev/sdb1

# 新增掛載目錄
$ mkdir /home2

# 掛載硬碟
$ sudo mount /dev/sdb1 /home2

# 設定存取權限
$ chmod 777 /home2
```
https://blog.gtwang.org/linux/linux-add-format-mount-harddisk/
https://fengka.pixnet.net/blog/post/29032979

### 6. 更改目錄使用權限
```
sudo chmod  777 /etc/squid
```
https://blog.csdn.net/pythonw/article/details/80263428

### 7. 新增sudo權限
``` linux=
# 新增sudo權限
$ sudo adduser jessechen sudo
$ sudo usermod -aG sudo sammy

# 移除sudo權限
$ sudo deluser USERNAME sudo

# 查看sudo權限
$ grep sudo /etc/group
```

### 8. 查看群組
``` linux=
$ cat /etc/group

# 觀看 /etc/passwd, /etc/group 設定檔確認是否有其帳號
$ grep jonny /etc/passwd
$ grep admin /etc/group
```

### 9. 修改使用者密碼
``` linux=
$ sudo passwd cjhuang
```


### 10. 新增與刪除使用者
``` linux=
$ adduser USERNAME

# 增加一名為USERNAME的帳號
useradd USERNAME

# 刪除USERNAME這個帳號
userdel USERNAME

# 更改USERNAME的密碼，若無參數，則改自己的密碼。
passwd [USERNAME]

# 查詢使用者資料
finger USERNAME[@HOSTNAME]

# 讓新增的使用者具有管理者權限
adduser jonny admin

```
https://bit.ly/2OlObCq
http://note.drx.tw/2008/03/ubuntuadduser-part1.html


### 11. samba
  - 設定 Samba 分享檔案
``` linux=
$ sudo apt-get install samba

$ sudo vim /etc/samba/smb.conf 

 [joshuachao]            # [資料夾的名稱] 可以自行變更
   path = /home/smbuser  # 這個是要分享的資料夾路徑
   available = yes
   valid users = smbuser # 指定使用者
   read only = no
   browseable = yes
   public = yes
   writable = yes
   force user = joshuachao
   force group = joshuachao
   write list = @joshuachao
   security = share


# 重新啟動 samba 服務
$ sudo /etc/init.d/smbd restart 
$ sudo service smbd restart 


$ sudo smbpasswd -a [username] #建立samba帳號密碼
$ sudo smbpasswd -z [username] #刪除帳號

$ smbpasswd [username] # 變更密碼

```
https://bit.ly/2NHJohh
https://bit.ly/2yNXIvr

- windows10 連不上samba的解决
https://blog.csdn.net/jiay2/article/details/123689399
https://www.asus.com/tw/support/FAQ/1037477/


### 12. scp
  - 遠端複製檔案與目錄
``` linux=
# 從本地端複製到遠端
$ scp /path/file1 myuser@192.168.0.1:/path/file2

# 從遠端複製到本地端
$ scp myuser@192.168.0.1:/path/file2 /path/file1

  -r 複製整個目錄

# sample:
$ scp -r louiswang@192.168.105.63:/home/louiswang/AQ360_v3/ /home/easanjhang/AQ360_backup/
```
https://bit.ly/2pcKpAp

### 13. du
  - 顯示文件或目錄Size
``` linux=
$ du -h test
```
https://bit.ly/2N7YrS5


### 14. Android編譯之lunch命令

- 按照google给出的編譯步驟如下：
``` linux=
$ source build/envsetup.sh:加载命令 (設定環境變數)

$ lunch：選擇平台編譯選項

$ make：執行編譯
```
https://bit.ly/2CSWcgA


### 15. diff
- 比對兩個文字檔，比較時忽略空白
``` linux=
$ diff -w name_list.txt name_list_new.txt
```


### 16. ifconfig
- 查看Linux系统 網路IP
``` linux=
$ ifconfig -a
```


### 17. chown 
- Linux 更改檔案擁有者與群組

``` linux=
# 將 myfile 的擁有者改為 myuser
$ sudo chown myuser myfile

# 將 myfile 的群組改為 mygroup
$ sudo chown :mygroup myfile

# 遞迴更改整個目錄下的所有檔案
sudo chown -R myuser:mygroup myfolder
```
https://bit.ly/2DWlwDg


### 18. date
- 更改系統時間

``` linux=
# 修改系統時間
$ sudo date -s "2016/11/11 10:21:32"
$ sudo date -s "2016-11-11 10:21:32"

# 取出系統時間
$ date
```


### 19. 遠端桌面若登不進去，可嘗試 xrdp restart
``` linux=
$ sudo service xrdp restart
```
https://ifun01.com/RHIDF9V.html




### 20. cat 命令:

- Cat命令主要有三大功能:

   1. Linux Cat命令一次顯示整個檔案。$ cat  filename
   2. Linux Cat命令從鍵盤建立一個檔案。$ cat > filename(只能建立新檔案,不能編輯已有檔案.)
   3. Linux Cat命令將幾個檔案合併為一個檔案。$cat  file1   file2 > file
https://www.itread01.com/p/204415.html

``` linux=
$ cat filename  # 顯示整個檔案
```


### 21. rm:
``` linux=
$ sudo rm -Rf dir_path # 強制刪除資料夾（不管他底下有無檔案)
```





### 22. fast boot bootimge.bat:

``` linux=
/******* fastbootbootimge.bat 內容 *******/
adb reboot bootloader
pause;
fastboot flash boot boot.img
pause;
fastboot reboot
pause;
/******* fastbootbootimge.bat 內容 *******/
```

### 23. linux build code

``` linux=
/* 至AQ360_v3的目錄下進行底下操作 */
/* 設定環境變數 */
>> source ./build/envsetup.sh
>> lunch 31
/* 對linux driver做編譯 */
>> make bootimage –j4
```

### 24. Putty 免密碼登入
  https://blog.haohtml.com/archives/13170
``` linux=
  chmod 700 ~/.ssh
```


### 25. 透過 adb shell cat & echo 來測試API
``` linux=
adb devices
adb root
adb remount
adb shell
shell>> cd sys\class\mini_isp\mini_isp_device
shell>> cat mini_isp_exposure_param
shell>> echo 11 22 33 > mini_isp_exposure_param
shell>> dmesg | grep miniisp
```

### 26. adb shell dmesg查看log

```linux=
adb devices
adb shell dmesg
adb shell dmesg | grep miniisp
```

### 27. vim 指令

```linux=
$ vim test.c
...
>> $ :/xxx_string    // 往後搜尋字串
>> $ :?xxx_string    // 往前搜尋字串

>> $ :set nu         // 顯示行號
>> $ :set nonu       // 取消顯示行號

```

### 28. find 指令
```linux=
// 在目前的目錄底下，找尋檔案名稱為 dt_gpio.c 的檔案
>> $ find . -name dt_gpio.c
// 在home目錄底下，找尋檔案名稱為 dt_gpio.c 的檔案
>> $ find /home -name dt_gpio.c

// find 加上 -type 參數可以指定檔案的類型，常用的選項有：
  // d：目錄。
  // p：具名的 pipe（FIFO）。
  // f：一般的檔案。
  // l：連結檔，如果與 -L 或 -follow 參數同時使用時，就只會搜尋到有問題的連結檔，如果想要與 -L 同時使用，請改用 -xtype。
  // s：socket 檔案。
>> $ find . -type d -name rpi3_folder
>> $ find . -type f -name "*.c" // 列出目前目錄底下所有的.c檔案

```

### 29. grep指令
``` linux=

>> $ grep -arn 'rev 1.2' --include=*.dtb

// 顏色標示
// --color=always
// -r 遞迴搜尋檔案
// -a 搜尋text
// -n 標示行號

>> $ grep -i rpi *   // 在當前目錄下搜尋所有文件，-i 忽略大小寫
>> $ grep -ir rpi *   // 在當前目錄下搜尋所有文件，-r 遞迴子目錄也搜尋
>> $ grep -w "bcm2710-rpi-zero-2-w" *   // 在當前目錄下搜尋所有文件，-w 精確搜尋某字串
>> $ grep -l "rpi" *   // 在當前目錄下搜尋所有文件，-l 只顯示配對成功的文件檔名


```

### 30. sfdisk指令
```linux=
# 用參數 -d 可以 dump 資料
>> sudo sfdisk -d /dev/sdb > /backup/disk-part.dmp

# 把備份的檔案丟給 sfdisk 
>> sudo sfdisk /dev/sdb < /backup/disk-part.dmp

# 可看SD卡的分區和總大小
>> sudo fdisk -l /dev/sdb
# -------------------------------------------------------------
# Disk /dev/sdb: 29.14 GiB, 31293702144 bytes, 61120512 sectors
# Disk model: SD  Transcend   
# Units: sectors of 1 * 512 = 512 bytes
# Sector size (logical/physical): 512 bytes / 512 bytes
# I/O size (minimum/optimal): 512 bytes / 512 bytes
# Disklabel type: dos
# Disk identifier: 0x3c4ef1b4
# 
# Device     Boot  Start      End  Sectors  Size Id Type
# /dev/sdb1         8192   532479   524288  256M  c W95 FAT32 (LBA)
# /dev/sdb2       532480 61120511 60588032 28.9G 83 Linux
# -------------------------------------------------------------

# 檢查在已掛接檔案系統上調整大小的效果
 >> df -h
# ------------------------------------------------
# Filesystem      Size  Used Avail Use% Mounted on
# tmpfs           1.1G  1.5M  1.1G   1% /run
# /dev/sda3       196G   94G   93G  51% /
# tmpfs           5.5G     0  5.5G   0% /dev/shm
# tmpfs           5.0M  4.0K  5.0M   1% /run/lock
# /dev/sda2       512M  6.1M  506M   2% /boot/efi
# tmpfs           1.1G  108K  1.1G   1% /run/user/1000
# /dev/sdb1       255M  128M  128M  51% /media/easonchang/bootfs
# /dev/sdb2       107M   85M   15M  86% /media/easonchang/rootfs
# ------------------------------------------------

# 改變檔案系統大小
>> sudo e2fsck -f /dev/sdb2 
>> sudo resize2fs /dev/sdb2

# 查詢 Ext 家族 superblock以及GDT 資訊。
>> sudo dumpe2fs /dev/sdb1



```



### 31. mount image file

  - [Partition ID definition]( https://www.win.tue.nl/~aeb/partitions/partition_types-1.html)

```linux=
>> sudo mount -o loop /home/easonchang/rpi3_2/buildroot-2023.08.3/output/images/rootfs.ext2 ~/rpi3_2/sd_mnt/

>> vim sd_mnt/etc/fstab // 可以看檔案系統type
>> file ~/rpi3_2/buildroot-2023.08.3/output/images/rootfs.ext2

>> sudo umount ~/rpi3_2/sd_mnt/
```

![image](https://hackmd.io/_uploads/HkuFkOBrp.png)

![image](https://hackmd.io/_uploads/rk3EHTHS6.png)

![image](https://hackmd.io/_uploads/SyTN8zsBT.png)
![image](https://hackmd.io/_uploads/SyxHKaSHa.png)
![image](https://hackmd.io/_uploads/rk6qJuHHT.png)

![image](https://hackmd.io/_uploads/rJVMwGjHT.png)
![image](https://hackmd.io/_uploads/Sk0JDfiSp.png)
![image](https://hackmd.io/_uploads/HkxRRDziHp.png)

### 32. fdisk

``` linux=
# 可查詢sdcard.img的分區訊息
>> fdisk -u -l rpi-test-image-raspberrypi4-20240109023052.rootfs.wic
```
![image](https://hackmd.io/_uploads/HkREwz0Op.png)

### 33. Ubuntu login information
![image](https://hackmd.io/_uploads/HkZC39WqC.png)

### 34. ssh Cryptography
  - SSH key type常用的加密演算法DSA、RSA、 ECDSA、Ed25519
  1. 可分為兩類
    - DSA 以及 RSA，依賴於對兩個大質數之積進行分解
    - ECDSA 以及 Ed25519，依賴於橢圓曲線離散對數問題
  2. DSA因為安全問題，已不再使用
  3. ECDSA因為政治原因和技術原因，也不推薦使用。
  4. RSA是目前兼容性最好，應用最廣泛的key類型，為ssh-keygen使用的default類型
  5. Ed25519是目前最安全、加解密速度最快的類型，但它目前存在兼容性問題，舊版SSH工具無法使用。

  - ![image](https://hackmd.io/_uploads/B1xP69WqC.png)
  - ![image](https://hackmd.io/_uploads/Bkkt6cbqC.png)
  - https://medium.com/@RiverChan/%E5%9F%BA%E7%A4%8E%E5%AF%86%E7%A2%BC%E5%AD%B8-%E5%B0%8D%E7%A8%B1%E5%BC%8F%E8%88%87%E9%9D%9E%E5%B0%8D%E7%A8%B1%E5%BC%8F%E5%8A%A0%E5%AF%86%E6%8A%80%E8%A1%93-de25fd5fa537


### 35. openssl產生一組Ubuntu passwd

  - 透過openssl可以手動產生一組passwd hash，取代/etc/shadow亦能順利登入
    - Sample: openssl passwd -6 -salt xyz  556677
    - (Note: -6 SHA512)
    - 可順利使用密碼 “556677”登入
    - ![image](https://hackmd.io/_uploads/r1AC65bcA.png)
  - 修改/etc/shadow，即可使用密碼 “556677”登入
    - ![image](https://hackmd.io/_uploads/SkBE0qb5C.png)
  - https://unix.stackexchange.com/questions/81240/manually-generate-password-for-etc-shadow

  - yescript
```
perl -e ' print crypt "P@ssW0Rd", "\$y\$j9T\$tEsTSalT\$" '
```
  - 說明:
    - “perl -e” 表示直接在命令列執行後方提供的 Perl 程式碼，而不需要另外建立檔案。該指令會呼叫 Linux 系統中的 crypt() 函式（由 libcrypt.so 提供），利用指定的明碼與 salt 組合產生對應的雜湊值。此範例也是 /etc/shadow 標準格式的 SALT。
    - \$y$		：表示此雜湊使用 yescrypt
    - j9T		：yescrypt 成本參數（work factor）
    - TESTSALT	：自己定義的 salt


### 36. Practical Effects of Setting “UsePAM yes” on SSH in Linux
  - https://www.baeldung.com/linux/usepam-yes-ssh-effects

### 37. Ubuntu Password: yescrypt vs. sha-512
  - Ubuntu Password hash存在/etc/shadow
  - 參考下面方式可以手動重建Password hash
  - 若要使用mkpasswd要安裝以下package
    - sudo apt install whois
    - 安裝後，可以在/usr/bin/mkpasswd找到package
  - ![image](https://hackmd.io/_uploads/HkJEFCZ5C.png)
  - ![image](https://hackmd.io/_uploads/rk-U9AW50.png)
  - https://medium.com/@hillsborosui/unix-shadow-file-%E5%8A%A0%E5%AF%86%E9%A1%9E%E5%9E%8B-87480f15ab90
  - https://unix.stackexchange.com/questions/690679/what-does-j9t-mean-in-yescrypt-from-etc-shadow
  - https://github.com/openwall/yescrypt/blob/main/yescrypt.h
  - https://manpages.ubuntu.com/manpages/focal/en/man5/crypt.5.html
  - https://manpages.debian.org/unstable/libcrypt-dev/crypt.5.en.html#Hashed~5
  - https://www.baeldung.com/linux/hashing-methods-password

### 38. Shell scipt: Parsing sshd_config [key value]

```bash=
# /etc/ssh/sshd_config
# ...
# ListenAddress 198.51.100.1:22
# ...

# get interface ip address
# >> 198.51.100.1:22
eth1_addr=$(ip addr show eth1 | grep "inet\b" | awk '{print $2}' | cut -d/ -f1)
# >> 198.51.100.1
eth1_domain=$(echo $eth1_addr | cut -d. -f1,2,3)

user=$(awk '/^ListenAddress\s+'$eth1_domain'/{ sub(/^ListenAddress\s+/, ""); sub(/:.*/, ""); print }' /etc/ssh/sshd_config.d/test.conf)
echo $user

# (^ListenAddtess[ ]+)([\d]{1,3}\.[\d]{1,3}\.[\d]{1,3}\.[\d]{1,3}):([\d]{1,5})
```
  - /etc/NetworkManager/dispatcher.d/test.sh
```bash=
#!/usr/bin/env bash

interface=$1
event=$2

sshd_cfg_file=/etc/ssh/sshd_config.d/test.conf

if [[ $interface = "eth1" ]] || [[ $event = "up" ]]
then
    eth1_addr=$(ip addr show eth1 | grep "inet\b" | awk '{print $2}' | cut -d/ -f1)
    eth1_domain=$(ip addr show eth1 | grep "inet\b" | awk '{print $2}' | cut -d/ -f1 | cut -d. -f1,2,3)

    if [ -e $sshd_cfg_file ]
    then
        # ToDo...
        # sed -i 's#ListenAddress '$eth1_domain'.*#ListenAddress '$eth1_addr':22#g' $sshd_cfg_file
    fi

    return 0
fi
```

### 38. sshd_config: limit user accounts

  - /etc/ssh/sshd_config
```sshd_config=
ListenAddress 198.51.100.1:55
ListenAddress 172.16.252.84:33
PermitRootLogin no
PermitEmptyPasswords no

Match Address 198.51.100.*
    AllowUsers    msitest
Match Address 172.16.252.*
    AllowUsers    eason
    PubkeyAuthentication yes
    PasswordAuthentication yes
```
  - NG 案例
    - Case 01
      - msitest也會被Deny
        ```
        DenyUsers *@198.51.100.*, !msitest
        # 對於同一帳號而言，如果同時 Allow 跟 Deny 的話，結果會視為 Deny 
        ```
    - Case 02
        ```
        # 原本預期只允許msitest從usb0連進來
        # 但無法有效被限制，其他User也可以從usb0進來
        Match User msitest
            AllowUsers    msitest@198.51.100.*
        ```

### 39. remount folder讀寫(r/w)權限
```
sudo mount -o remount,rw /FW_backup
sudo mount -o remount,rw /
```

### 40. 清空垃圾桶
```
rm -rf ~/.local/share/Trash/files/*
```
### 41. 尋找某指令目錄 (whereis)
```
whereis iptables
```

### 42. echo 重新導向，需要sudo權限的用法
```
echo "Some content" | sudo tee /path/to/file > /dev/null

sudo ./gen_usb_default_shadow.sh 1234 2024-12-01 2024-12-31 msisalt | sudo tee /etc/extrausers/msishadow.txt > /dev/null
```

### 43. 查詢檔案data，使用Hex檢視
```linux=
# 查看檔案最後 64 bytes 的 hex dump
tail -c 64 yourfile.bin | xxd

# 快速查偏移區的值
xxd -s 0x100 -l 64 yourfile.bin
```

### 44. 指令寫入journal log(logger)
```linux=

# 測試log寫入
logger -t OCPP -s -p user.info "your message"
logger -t OCPP -s -p user.info "This Eason0 is a test log $(date +%s)"

# 檢視log紀錄
journalctl -n 100 

# 檢視log紀錄，指定Tag
journalctl -t OCPP

# 查詢指定.journal檔案
sudo journalctl --file=/var/log/journal/60dc736c5ff6467eb7463faf14277fea/system.journal  -n 100 

# 統計每個service總筆數
sudo journalctl -b -o json | grep -o '"_SYSTEMD_UNIT":"[^"]*"' | cut -d':' -f2 | tr -d '"' | sort | uniq -c | sort -nr >> "$LOG_FILE"
```

### 45. iotop 監控磁碟 I/O 活動（讀寫）
  - **iotop** 是一個在 Linux 上使用的命令列工具，類似於 top，但它專門用來監控磁碟 I/O 活動（讀寫），可即時顯示哪些程序正在大量讀寫磁碟，幫助找出「磁碟 I/O 吃重的程式」。

```linux=
# 使用 iotop 以累積模式（accumulated mode）
sudo iotop -ao

# 每隔 10 秒，顯示一次有 I/O 活動的進程累積數據，
# 共輸出 3 次（總時間為 30 秒），
# 每列前會加上時間戳記，
# 格式為非互動的純文字模式（適合寫 log）。
sudo iotop -ao -n 3 -d 10 -b -t

# -a	累積模式，顯示從程式啟動以來各程序的總 I/O 用量
# -o	只顯示目前有 I/O 活動的程序（非 0 I/O）
# -n 3	執行 3 次後自動結束
# -d 10	每 10 秒更新一次（每次採樣間隔）
# -b	批次模式，不進入互動介面，適合寫入檔案
# -t	顯示每一行前面加上時間戳（timestamp）

```

### 46. inotifywait 監控檔案系統事件

inotify-tools 是一套 Linux 上用來監控檔案系統事件的工具，基於 Linux 核心的 inotify 機制。這套工具提供了命令列介面，讓使用者可以監看檔案或目錄的變化，例如檔案被讀取、寫入、刪除、移動等等。



| 事件    |   說明    |
| ------ | -------- |
|access  | 檔案被讀取 |
|modify  | 檔案內容被修改 |
|attrib  | 屬性被改變 (如權限、時間戳記等) |
|close_write | 以寫入方式開啟後被關閉 |
|move | 移動（包括 move_from / move_to） |
|create | 新檔案或目錄建立 |
|delete | 檔案或目錄被刪除 |


```
sudo apt install inotify-tools
```

- 建立監控腳本：/usr/local/bin/journal_copy.sh
```linux=
#!/bin/bash

SRC_DIR="/run/log/journal/$(cat /etc/machine-id)/"
DST_DIR="/var/log/journal/$(cat /etc/machine-id)/"
mkdir -p "$DST_DIR"

inotifywait -m -e close_write --format '%w%f' "$SRC_DIR" --recursive | while read FILE
do
    if [[ "$FILE" == *.journal ]]; then
        echo "[COPY] $FILE -> $DST_DIR"
        cp -u "$FILE" "$DST_DIR/"
    fi
done
```
### 47. 讀取emmc info

```linux=
cat /sys/class/mmc_host/mmc0/mmc0:0001/pre_eol_info 
cat /sys/class/mmc_host/mmc0/mmc0:0001/life_time
```

### 48. vsftp


  - 透過ftp連線到遠端抓檔案的指令
```linux=
ftp <server-ip>
ftp 172.16.252.82

Name: your_username
Password: your_password
ftp> cd /FW_backup/share/upload        # 切換到遠端目錄
ftp> get report.txt                    # 下載單一檔案
ftp> mget *.log   
```

  - windows透過FileZilla
![image](https://hackmd.io/_uploads/BJcvSzCIgg.png)


  - vsftp無法支援若家目錄透過symlink 到/run/
    - 原因：如果家目錄是 /FW_backup/share，symlink 指向 /run/log/hmi，FTP 使用者可能會無法跟隨 symlink 出去（因為 /run/log/hmi 不在 chroot 內）
```linux=
sudo mkdir -p /FW_backup/share/upload
sudo mkdir -p /run/log/hmi

sudo chmod 777 /FW_backup/share/upload
sudo chmod 777 /run/log/hmi

sudo mount --bind /run/log/hmi /FW_backup/share/upload
```

  - vsftpd.conf 設定檔
```linux=
# 允許匿名登入
anonymous_enable=YES

# 允許匿名使用者上傳檔案
anon_upload_enable=YES

# 允許匿名使用者建立目錄（可選）
anon_mkdir_write_enable=YES

# 允許匿名使用者刪除/改寫檔案（可選）
anon_other_write_enable=YES

# 寫入功能要開啟
write_enable=YES

# 指定本地使用者登入後的家目錄為 /FW_backup/share
local_root=/FW_backup/share
anon_root=/FW_backup/share

# 匿名使用者登入時不需要密碼
no_anon_password=YES

# 啟用使用者白名單機制
userlist_deny=NO

# 表示 /etc/vsftpd.user_list 裡的使用者允許登入（白名單），若為 YES 則表示列出者不允許登入（黑名單）
userlist_enable=YES
userlist_file=/etc/vsftpd.user_list

# 將log導向syslog或journal
xferlog_enable=NO
syslog_enable=YES
```

### 49. 動態重新mount為f2fs的分區


```linux=
# 若為Yocto請安裝
# IMAGE_INSTALL:append = " f2fs-tools"

# 確認已安裝 whereis mkfs.f2fs

# 格式化為 F2FS
sudo umount /dev/mmcblk0p5 
sudo /usr/sbin/mkfs.f2fs /dev/mmcblk0p5 -f

# 重新掛載
sudo mkdir -p /FW_backup
sudo mount -t f2fs /dev/mmcblk0p5 /FW_backup

# 檢查
df -T /FW_backup
```

















Reference
===


[1. 常用Unix/Linux命令](https://gywbd.github.io/posts/2014/8/50-linux-commands.html)
[2. 在linux kernel裡操作open file(create/open/read/write](https://bit.ly/2E5bDlI)
[3. SPIdev (Implement SPI driver)](http://linux-sunxi.org/SPIdev)
[4. SPI driver source code](https://elixir.bootlin.com/linux/latest/source/drivers/spi/spi.c)
[5. Linux-DEVICE_ATTR()介绍及使用示例](https://www.cnblogs.com/lifexy/p/9799778.html)
[6. Linux-I2C driver](https://www.cnblogs.com/lifexy/p/7816324.html)
