Armadilloフォーラム

コンテナ内からSDカードをフォーマット

k.sato

2024年3月26日 9時29分

佐藤です。

お世話になっております。

/etc/fstabに下記を追加し、起動時にマウントされるようにしています。

/dev/mmcblk1p1  /var/app/volumes/sd             ext4    defaults                                         0 0

このSDカードをコンテナ内からフォーマットする方法を教えていただけませんか?

ホストから手動で下記のコマンドを打ってみたのですが、
umount後にmountでdev/mmcblk1p1が存在しないのを確認して「mkfs.ext4 /dev/mmcblk1p1」したのですが下記のエラーとなります。

armadillo:~# umount /var/app/volumes/sd/
armadillo:~# mkfs.ext4 /dev/mmcblk1p1
mke2fs 1.47.0 (5-Feb-2023)
/dev/mmcblk1p1 is apparently in use by the system; will not make a filesystem here!

podman stop」でコンテナを停止して「mkfs.ext4 /dev/mmcblk1p1」を行うと下記のように先に進めるのは確認しています。

armadillo:~# mkfs.ext4 /dev/mmcblk1p1
mke2fs 1.47.0 (5-Feb-2023)
/dev/mmcblk1p1 contains a ext4 file system
        last mounted on /home/atmark on Thu Jan  1 09:54:24 1970
Proceed anyway? (y,N)

以上、よろしくお願い致します。

コメント

at_dominique.m…

2024年3月26日 17時25分

佐藤さん

お世話になっています、
マルティネです。

> armadillo:~# umount /var/app/volumes/sd/
> armadillo:~# mkfs.ext4 /dev/mmcblk1p1
> mke2fs 1.47.0 (5-Feb-2023)
> /dev/mmcblk1p1 is apparently in use by the system; will not make a filesystem here!

お気づきのとおりに、ファイルシステムを完全に umount しないとフォーマットできません。
rm -rf 等でファイルの削除だけはできますが、それはダメですね?

コンテナの使い方によって違う方法を案内しますので、コンテナのコンフィグ ( /etc/atmark/containers/xyz.conf) を見せてもらえますか?(具体的に、コンテナのボリュームと権限を確認したいです)

よろしくお願いします。

k.sato

2024年3月27日 8時38分

マルティネ様

佐藤です。

お世話になっております。

> お気づきのとおりに、ファイルシステムを完全に umount しないとフォーマットできません。
> rm -rf 等でファイルの削除だけはできますが、それはダメですね?
申し訳ございません。
フォーマットしたいです。

> コンテナの使い方によって違う方法を案内しますので、コンテナのコンフィグ ( /etc/atmark/containers/xyz.conf) を見せてもらえますか?(具体的に、コンテナのボリュームと権限を確認したいです)
コンテナのコンフィグファイルを添付しました。

よろしくお願い致します。

ファイル ファイルの説明
my_project.conf コンテナのコンフィグファイル

at_dominique.m…

2024年3月27日 9時42分

佐藤さん、

マルティネです。

> フォーマットしたいです。

了解しました。

> コンテナのコンフィグファイルを添付しました。

ありがとうございます。
それでしたらホストのコンテナのマウント状態を共有できそうですが、コンテナからの umount 権利がないのでどうしても難しくなりますね。

私が考えている中では、選択肢は三つあります:
1/ コンテナに SYS_ADMIN の capability を追加することで、コンテナから mount/umount コマンドを実効できるようになって、コンテナ内から umount して mkfs を使えるようになります。
デメリットは、SYS_ADMIN の権限が大きすぎて、これがあればコンテナ外の実行もできてしまいますのでコンテナを使うメリットが半分なくなります…
https://armadillo.atmark-techno.com/forum/armadillo/17613 の様に権限のあるコンテナ(かホスト)でその umount/mount 機能だけを切り分けることで権限の問題を回避できますが、作りがどんどん複雑なります。
また、コンテナ内の /home/atmarkのファイルがアクセス中でしたら umount が失敗しますので、その場合はアクセスしているプログラムを強制的に停止させたりすると変な状態になる可能性もあります。

2/ 設定は少し複雑ですが、fstab でマウントするのではなく、「autofs」という機能で sd をアクセスする時だけに mount させることができます。
その場合は、sd にアクセスがなければフォーマットはできるようになりますが、アクセス中の場合は 1/ と同じく強制停止が必要になりますので、場合によっては向いてない可能性もあります。
(他のメリットは、アクセスが少ない場合は以前の問い合わせでできなかった USB/SD の入れ替えの対応はできます)

3/ armadillo 起動時にどこかのボリュームに sd_reformat等のファイルが存在する場合にコンテナを機動する前に sd をフォーマットするようにします。その場合はコンテナからその sd_reformat ファイルを作っておいてコンテナからを再起動すればホストで邪魔なしでフォーマットできますので、失敗することはないですが、再起動が必要ということになりますので頻度によっては不向きの場合も多いです。

万全な方法はないですしどれも細かいところがありますので、その中から方向を選んでいただければ具体的に案内します。

よろしくお願いします。

k.sato

2024年3月27日 10時26分

佐藤です。

> 3/ armadillo 起動時にどこかのボリュームに sd_reformat等のファイルが存在する場合にコンテナを機動する前に sd をフォーマットするようにします。その場合はコンテナからその sd_reformat ファイルを作っておいてコンテナからを再起動すればホストで邪魔なしでフォーマットできますので、失敗することはないですが、再起動が必要ということになりますので頻度によっては不向きの場合も多いです。
3の再起動してもよいので確実にフォーマットできる方法を教えていただけますか?

at_dominique.m…

2024年3月27日 13時04分

マルティネです。

> 3の再起動してもよいので確実にフォーマットできる方法を教えていただけますか?

了解しました。
以下の変更で実装できると思います:

1/ しるしになるファイル名を /var/app/volumes/abos/sd_reformat にします。
コンテナコンフィグに /var/app/volumes側のマウントなかったので、新しいディレクトリを追加する形で「add_volumes /var/app/volumes/abos:/abos」等で共有します
2/ マウントしない可能性がありますので、/etc/fstab から sd の行に noauto を追加します:

/dev/mmcblk1p1  /var/app/volumes/sd             ext4    defaults,noauto                            0 0

3/ /etc/local.d はコンテナの起動の後に実行されてしまいますので、少し汚いですがコンテナのコンフィグファイルに処理を追加します…
my_project.conf の最後に以下のコードを追加します

# SD カードのフォーマットとマウント対応
if [ -e /var/app/volumes/abos/sd_reformat ]; then
    rm -f /var/app/volumes/abos/sd_reformat
    if mountpoint -q /var/app/volumes/sd; then
      umount /var/app/volume/sd
    fi
    # 失敗してもコンテナを起動したいと思いますので、あえてエラーチェックしませんが、
    # エラーの場合に /var/app/volumes/abos/format_error ファイルを生成させれば対応可能です。
    mkfs.ext4 -F /dev/mmcblk1p1
fi
if ! mountpoint -q /var/app/volumes/sd; then
    mount /var/app/volumes/sd
fi

4/ コンテナ内でフォーマットを起こしたい際に /abos/sd_reformat ファイルをせいせいして、再起動が必要です。
再起動は ABOS Web のバージョン 1.2.0 (2023年12月のABOS 3.18.5-at.7) で実行できますが、現在の ABOS のバージョンはなんでしょうか?(cat /etc/atmark-release)
その前のバージョンでしたらアップグレードか、それこそ https://armadillo.atmark-techno.com/forum/armadillo/17613 での再起動サービスが必要になります。
バージョンが足りる場合は abos-web の admin 管理画面で「Reboot」の権限のトークンを作っていただいて、コンテナから 「curl -k -H 'Authorization: Bearer xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx' -X POST https://host.containers.internal:58080/api/reboot 」で再起動できますので、それで再起動して再起動した後にまたコンテナが起動される際にフォーマット状態で新たにマウントされるはずです。

(部分的にとしか確認してませんので説明の問題の可能性があります。何か問題あれば聞いてください。)

よろしくお願いします。

k.sato

2024年3月28日 13時45分

マルティネ様

佐藤です。

お世話になっております。

教えていただいた方法で再起動時にSDカードのフォーマットが行えました。
ありがとうございます。

その時に起きたことについて質問します。

> 3/ /etc/local.d はコンテナの起動の後に実行されてしまいますので、少し汚いですがコンテナのコンフィグファイルに処理を追加します…
> my_project.conf の最後に以下のコードを追加します

# SD カードのフォーマットとマウント対応
if [ -e /var/app/volumes/abos/sd_reformat ]; then
    rm -f /var/app/volumes/abos/sd_reformat
    if mountpoint -q /var/app/volumes/sd; then
      umount /var/app/volume/sd
    fi
    # 失敗してもコンテナを起動したいと思いますので、あえてエラーチェックしませんが、
    # エラーの場合に /var/app/volumes/abos/format_error ファイルを生成させれば対応可能です。
    mkfs.ext4 -F /dev/mmcblk1p1
fi
if ! mountpoint -q /var/app/volumes/sd; then
    mount /var/app/volumes/sd
fi

これなのですが末尾とはmy_project.confの「set_command sh /startup.sh」の後でよいのでしょうか?
/startup.sh の前に入れたくなるのですがそういう物ではないのでしょうか?

> 4/ コンテナ内でフォーマットを起こしたい際に /abos/sd_reformat ファイルをせいせいして、再起動が必要です。
> 再起動は ABOS Web のバージョン 1.2.0 (2023年12月のABOS 3.18.5-at.7) で実行できますが、現在の ABOS のバージョンはなんでしょうか?(cat /etc/atmark-release)
> その前のバージョンでしたらアップグレードか、それこそ https://armadillo.atmark-techno.com/forum/armadillo/17613 での再起動サービスが必要になります。
> バージョンが足りる場合は abos-web の admin 管理画面で「Reboot」の権限のトークンを作っていただいて、コンテナから 「curl -k -H 'Authorization: Bearer xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx' -X POST https://host.containers.internal:58080/api/reboot 」で再起動できますので、それで再起動して再起動した後にまたコンテナが起動される際にフォーマット状態で新たにマウントされるはずです。

環境を更新してABOS Web REST APIのrebootから再起動を行いました。

また、atde9の環境も更新したのですが、VSCodeで作成したプロジェクトである
「/my_project/container/resources」に「requirements.txt」が追加されていました。
Dockerfileにも「RUN python3 -m pip install -r requirements.txt」が追加されておりファイルに追記したpipのインストールが行えるよう。

現在、「FROM docker.io/${ARCH}/alpine:3.18」のコンテナを指定して、
RUN apk upgrade && apk add ${PACKAGES} && rm -f /var/cache/apk/* && pip3 --no-cache-dir install spidev && pip3 --no-cache-dir install modbus_tk && pip3 --no-cache-dir install uptime
としているのですが、requirements.txt を使用して簡単に記述できるのでしょうか?

# Write the name of the package that can be installed with pip
# numpy
spidev
modbus_tk
uptime

requirements.txt を上記として

RUN apk upgrade && apk add ${PACKAGES} && rm -f /var/cache/apk/*
RUN python3 -m pip install -r requirements.txt
もしくは
RUN pip3 --no-cache-dir install -r requirements.txt

を試してみたのですが [Generate development swu] を実行すると requirements.txt がデフォルトに戻ってしまいます。

# Write the name of the package that can be installed with pip
# numpy

全然検討違いのことをしていたら申し訳ございません。

よろしくお願い致します。

at_dominique.m…

2024年3月28日 14時44分

佐藤さん、

マルティネです。

> これなのですが末尾とはmy_project.confの「set_command sh /startup.sh」の後でよいのでしょうか?
> /startup.sh の前に入れたくなるのですがそういう物ではないのでしょうか?

コンフィグファイルの「set_command」命令はすぐにコンテナをそのコマンドで実行するのではなく、コンフィグファイルの実行が終了した後にコンテナが起動される際のコマンドを覚えるだけですので順番は関係ありません。
フォーマット・マウント処理は set_command の前でも、後でも問題ありませんので、自分に分かりやすい方で書いて問題ありません。

> また、atde9の環境も更新したのですが、VSCodeで作成したプロジェクトである
> 「/my_project/container/resources」に「requirements.txt」が追加されていました。

とても分かりにくいことになりましたが、my_project/container/resources/requirements.txt は毎回 my_project/app/src/requirements.txt からコピーされますので、後でお気づきになりましたが直接に container/resources の方を編集すると上書きされてしまいます。
app/src の方に内容を記載してください。

> # Write the name of the package that can be installed with pip
> # numpy
> spidev
> modbus_tk
> uptime

> requirements.txt を上記として

> RUN apk upgrade && apk add ${PACKAGES} && rm -f /var/cache/apk/*
> RUN pip3 --no-cache-dir install -r requirements.txt

はい、requirements.txt は resources の一つとしてコンテナ内にコピーされますので、このコマンドで問題ありません。
(また、--no-cache-dir の指摘もありがとうございます、記載した方が効率いいですのでこちらの方でも追加します)

ファイルが上書きされる問題以外はこれで大丈夫に見えますので、app/src/requirements.txt を編集しなおしてもう一度ビルドしてみてください。

また、alpine:3.18 で 「pip3 --no-cache-dir install -r ..」で問題ありませんが、alpine:3.19 へアップグレードされる際に「--break-system-packages」の追加も必要になります。

よろしくお願いします。

k.sato

2024年3月28日 16時09分

マルティネ様

佐藤です。

> とても分かりにくいことになりましたが、my_project/container/resources/requirements.txt は毎回 my_project/app/src/requirements.txt からコピーされますので、後でお気づきになりましたが直接に container/resources の方を編集すると上書きされてしまいます。
> app/src の方に内容を記載してください。
my_project/app/src/requirements.txt に記載すればよかったのですね。
勘違いしていて申し訳ございません。

> RUN apk upgrade && apk add ${PACKAGES} && rm -f /var/cache/apk/*
> RUN pip3 --no-cache-dir install -r requirements.txt

> はい、requirements.txt は resources の一つとしてコンテナ内にコピーされますので、このコマンドで問題ありません。
コマンドもありがとうございます。

> ファイルが上書きされる問題以外はこれで大丈夫に見えますので、app/src/requirements.txt を編集しなおしてもう一度ビルドしてみてください。
>
> また、alpine:3.18 で 「pip3 --no-cache-dir install -r ..」で問題ありませんが、alpine:3.19 へアップグレードされる際に「--break-system-packages」の追加も必要になります。

無事に[Generate development swu] してArmadilloの動作確認ができました。

ありがとうございました。