CubeMXでSMBusを設定し、X_CUBE_SMBUSパッケージを追加しました。Middlewaresフォルダに「stm32_PMBUS_stack」と「stm32_SMBUS_stack」があるのは確認したのですが、次に何をすべきか分かりません。使い方が分かりません。
ミドルウェア内部の低レイヤーソースコードを無理に読み解こうとすると目が回るだけだからやめておこう。STのお決まりのパターンはいつも同じだ。X_CUBE_SMBUSパッケージをダウンロードしたのなら、そのままパッケージのインストールディレクトリ(だいたいSTM32Cube\Repositoryの下)に行ってProjectsフォルダを探せばいい。その中には、特定の評価ボード(NUCLEOやEVALなど)向けのそのまま使えるExampleが必ずあるはずだ。PMBus関連のプロジェクトを見つけたら、開いてそのmain.cとstm32_xx_it.cを直接見てみよう。重点的に見るべきは2点:1つ目は、メインループ内で呼び出されているStack Process処理関数。2つ目は、スレーブがコマンドを受信した後のコールバックがどう書かれているかだ。そのアプリケーション層のコードをコピーして少し修正すれば、すぐ動くよ。
兄弟、焦らないで。確かにこのパッケージはドキュメントがまとまってなくて、俺も初めて使ったときはしばらく混乱したよ。
今の君の状態:ハードウェア層(CubeMX)の設定はできたが、プロトコル層(stack)をアプリケーションコードにどう繋げばいいかわからない。
俺なりにメインの流れを整理するから、これに沿って進めてみて:
ステップ1:正しいプロジェクト構造を生成したか確認する CubeMXのSoftware PacksでX-CUBE-SMBUSを追加する際、ModeウィンドウにSMBus stackとPMBus extensionの2つのチェックボックスがあるが、両方にチェックを入れること。コード生成後、プロジェクト内には以下があるはずだ:
Middlewares/ST/STM32_SMBus_Stack/—— これがコアプロトコルスタックDrivers/BSP/—— ボードサポート(選択した場合)
ステップ2:stackの動作方式を理解する このstackはHAL_I2C_xxxを呼ぶためのものではなく、1層の状態機械をカプセル化している。君のコードは主に以下の3つの関数とやり取りする:
STACK_SMBUS_Init()—— 初期化、I2CハンドルをバインドするSTACK_SMBUS_HostCommand()—— ホスト用、通信を開始するSTACK_SMBUS_ExecuteCommand()—— スレーブ用、コマンド受信後のコールバック
ステップ3:スレーブの書き方 スレーブで最も重要なのがCMD_Tableだ。これは配列で、stackに「コマンドコード0x01を受け取ったらどのレジスタを読み、0x02を受け取ったらどのレジスタに書き込むか」を伝えるものだ。
const tSMBUS_CMD_Table MyCmdTable[] = {
{0x01, MyReadHandler, MyWriteHandler, 1}, // コマンドコード, 読み出しコールバック, 書き込みコールバック, データ長
{0x02, MyReadHandler2, NULL, 2},
};
その後、STACK_SMBUS_ExecuteCommand()内でstackhandle.CurrentCommandに基づいてディスパッチ処理を行う。
ステップ4:ホストの書き方 ホストはずっとシンプルだ。コマンド構造体を構築して、STACK_SMBUS_HostCommand(&stackhandle, &cmd)を呼ぶだけでいい。ただし、この関数はノンブロッキングなので、結果は割り込みコールバック内でstackhandle.Stateを確認すること。
特別な注意点:
- 公式のサンプルプログラムは
Projectsディレクトリにあるので、自分のボードに最も近いもの(例えばNUCLEO-G431RBやF072のDiscoveryなど)を探すこと。 - AN4502は必ず読むこと。これは公式のアプリケーションノートだ。分厚いが、第8章の「Configuration」と第9章の「Project example」は命綱になる。
- 2つのSTM32間を配線する際、SDAとSCLは両方プルアップすること。ボード内部にプルアップがあっても、外部にさらに4.7kΩを追加した方が安定する。PMBusはI2Cよりも信号完全性に敏感だからだ。
また問題があれば具体的なエラーメッセージを貼ってくれれば、みんなで見てあげるから。
おそらく、間違った視点からフォルダを見ているのでしょう。stm32_SMBUS_stackは下位の通信レイヤであり、stm32_PMBUS_stackはその上層でPMBusコマンドの処理を行います。
次に必要な手順は通常、HALのSMBusペリフェラルを有効にし、プロジェクトにミドルウェアのソースファイルを含め、main()でスタックを初期化し、ライブラリで要求されるコールバック関数を実装することです。コールバックがなければ、スタックは受信したフレームを渡す宛先を持てません。
皆さんのご回答ありがとうございます。まずは試してみます。
試した結果はどうでしたか?
この部分はチームメイトに丸投げしちゃった、エネルギーが足りなくて ![]()