Howto

libgpiod 2 で仕様変更された gpioget, gpioset コマンドへの対応

概要

Alpine 3.21 および Debian trixie 以降では libgpiod がバージョン 2 に更新されました。 libgpiod 2 で引数の仕様が変更されたため、libgpiod 1 までの書き方は将来的に利用できなくなります。

仕様変更の影響について説明した後、新しい gpioget, gpioset の書き方を紹介します。

仕様変更の影響

コンテナ内で gpioget や gpioset 等のコマンドを使用しており、そのコンテナを libgpiod 2 を含む alpine 3.21 や Debian trixie 等に 更新する場合に影響を受けます。

この場合、これまでの方法では gpio の値を読み取りや変更ができなくなり、以下のようなエラーが出力されます。

/ # gpioset 0 15=0
gpioset: invalid line value: '0'
/ # gpioget 0 15
gpioget: cannot find line '0'
gpioget: cannot find line '15'

2025年1月29日以降にビルドされた Alpine 3.21 イメージ (libgpiod-2.2-r1) では一時的に両方の使い方をサポートしていますが、一時的な対応なので新しい使い方へ移行してください。 こちらのバージョンで対応が必要な場合は以下の警告が表示されます。

armadillo:~# gpioset 0 15=0
WARNING: No gpiochip set and first argument looks like a chip, trying
WARNING: compatibility with libgpiod 1.x.
WARNING: This will stop working in alpine 3.22

新しい使い方

基本的に一番目の「gpiochip」引数を -c または --chip で指定します。

また、名前が設定されている場合には --chip を設定せずに名前でも使用できます。
例えば、Armadillo IoT G4 では以下の四つのコマンドが同じです。

/ # gpioget -c 0 15
"15"=inactive
/ # gpioget -c gpiochip0 15
"15"=inactive
/ # gpioget -c /dev/gpiochip0 15
"15"=inactive
/ # gpioget CON11_24
"CON11_24"=inactive

注意:

  • 名前は gpioinfo コマンドで確認できます。
  • 1月末にリリースされた Linux 5.10.233-r0 から名前が設定されていますので、それ以前のバージョンをご利用の場合は使用できません。
  • gpiochip やピンを変更する予定はありませんが、名前を利用できる場合は名前で指定することを推奨しています。

gpioget

gpioget コマンドは gpio を input に設定し、gpio の値を読みます。

gpioget コマンドの出力も大きく変更されましたので、今までの出力が好ましい場合は --numeric を指定してください。

/ # gpioget -c 0 15
"15"=inactive
/ # gpioget --numeric -c 0 15
0
/ # gpioget --numeric CON11_24
0

gpioset

gpioset コマンドは gpio を output に設定し、gpio の値を設定します。

libgpiod バージョン 1 の gpioset では gpio の値を設定した直後にコマンドを完了していましたが、gpio を解除すると値が変更されることがあります。このため、この使い方は非推奨です。 libgpiod バージョン 2 ではコマンドが停止しなくなり、使い方が難しくなりましたが安全に使用できます。

やむを得ず前の動作に合わせたい場合は「--toggle 0」で gpioset コマンドを停止させることはできますが、以下のとおりに値が自動的に変更されることがありますので非推奨です。

/ # gpioset --toggle 0 CON11_24=1; gpioget --numeric CON11_24; sleep 1; gpioget --numeric CON11_24
1
0

新しい使い方は、gpioset を停止させません。 使い方はいくつかあります。

  • 一つの値を設定し、その値を永続的に維持したい場合は --daemonize を利用できます。
/ # gpioset --daemonize -c 0 15=1
/ # gpioset --daemonize CON11_24=1
  • 値を決まった期間で点滅したい場合は --toggle オプションを利用できます。
# コマンド実行直後に値を 1 に設定し、1秒間 1 / 1秒間 0 を繰り返します。
/ # gpioset --toggle 1s CON11_24=1
# コマンド実行直後に値を 1 に設定し、1秒間 1 / 500ms間 0 nを繰り返します。
/ # gpioset --toggle 1s,500 CON11_24=1
  • 任意のタイミングで値を変更したい場合は shell の機能で gpioset を background 実行し適切なタイミングで停止します。複雑な使い方なので、可能であれば shell 以外の言語で開発し適切なライブラリをご利用ください。
# gpioset を background で実行し、pid を記録します。
gpioset CON11_24=1 &
# または gpioset -c 0 15=1 &
pid=$!

# background の gpioset を停止し、停止を待った上で新たな gpioset を実行します。
kill "$pid"
wait "$pid"
gpioset CON11_24=0 &
# または gpioset -c 0 15=0 &
pid=$!

注意:

  • gpioset が実行されてる間は gpioget を使用できません。設定した値を参照する必要がある場合は覚えておく必要があります。

gpioinfo

gpioinfo コマンドで chip が利用されてる pin の情報を確認できます。

/ # gpioinfo -c 0
gpiochip0 - 32 lines:
	line   0:	"GPIO01_00"     	output consumer="FW_UPDATE_IND"
	line   1:	"GPIO01_01"     	input active-low consumer="PWROFF"
	line   2:	"GPIO01_02"     	input
	line   3:	"GPIO01_03"     	input consumer="interrupt"
	line   4:	"GPIO01_04"     	input
	line   5:	"GPIO01_05"     	input active-low consumer="REBOOT"
	line   6:	"GPIO01_06"     	output consumer="PWR_IND"
(省略)
	line  15:	"GPIO01_15"     	output consumer=gpioset
(省略)

gpioset コマンドの 「--consumer <name>」オプションで gpioset 以外の文字列を設定できます。

gpiomon

gpiomon コマンドは gpio を input に設定し、gpio の値を監視します。

/ # gpiomon --debounce-period 5 -c 0 15
87744.864021856	rising	gpiochip0 15
87745.020019907	falling	gpiochip0 15
87745.580022905	rising	gpiochip0 15
87745.696023341	falling	gpiochip0 15
armadillo:~# gpiomon CON11_22 CON11_24
13473.284027104	rising	"CON11_24"
13474.524027353	falling	"CON11_24"
13475.484026962	rising	"CON11_22"
13475.552021758	falling	"CON11_22"