LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムについて

mbed についてのご質問はこちら。情報交換などにもご利用ください。

LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムについて

投稿記事by 樫原 輝 » 2012年3月29日(木) 14:40

LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムの仕方がわかりません。

説明書を読んだのですが、センサ電源、センサI/O電源、外部I2C電源。。。等いろんな電源があり、また加速度センサの出力ピン、地磁気センサの出力ピンが2つしかないです。

どのように使えばいいのかがわかりません。
また、どのようなプログラムを作れば加速度と方角を知ることができるのかがわかりません。


前に3軸加速度センサー(MMA7361L)の時には加速度センサーにはX,Y,Zのアナログ入力ピンがそれぞれあり、どのようになっているのかがわかったのですが、今回のLSM303DLHには方向別のピンがないので、わからないです。



すいませんが、できる限り詳しく教えてください。
お願いします。


追記
一度三谷と考えてどのピンに指すのか考えてみました。
LSM303DLHの
VDD(p1,p5),VDD_IO_A,VDD_I2C_BUSはmbedのVOUT(3.3V)
SA0_A,GNDはmbedのGND(-)
SDA_Aはmbedのp9(I2C_sda)
SCL_Aはmbedのp10(I2C_scl)
SCL_Mはmbedのp27(I2C_scl)
SDA_Mはmbedのp28(I2C_sda)


これであってるでしょうか?

すみませんが、プログラムの方はわからないので、できるだけ詳しく教えてください。
よろしくお願いします。
樫原 輝
 
記事: 134
登録日時: 2011年7月07日(木) 17:26

Re: LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムについて

投稿記事by yamaguch » 2012年3月30日(金) 13:09

こんにちは、

接続はこれで合っていると思います。
プログラミングには I2C インタフェースと LSM303DLH のデータシートの理解が必須です。
I2C については mbed.org のハンドブックに説明があると思います。
データシートは検索すれば容易に見つかるでしょう。
ちょっと手強いかもしれませんが、頑張ってください。

山口
yamaguch
 
記事: 482
登録日時: 2010年7月06日(火) 17:37

Re: LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムについて

投稿記事by 樫原 輝 » 2012年3月31日(土) 13:54

回答ありがとうございます。

一度探して自分で作ってみます。

アドバイスありがとうございます。
樫原 輝
 
記事: 134
登録日時: 2011年7月07日(木) 17:26

Re: LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムについて

投稿記事by 樫原 輝 » 2012年8月10日(金) 12:26

こんにちは

今、缶サット甲子園の問題点を解決しているところです。


そこで、加速度が振り切ってしまったというところから、出来る限り高い加速度をはかることの出来るセンサーを探したところ、LSM303DLHが8gまではかれるということが分かりました。

何ヶ月か前に同じような質問をさせていただいたのですが、その質問に対する山口さんの回答を参考にmbedのhandbookにあるI2Cを読み、サンプルプログラムを見たのですが、よくわかりませんでした。
次にI2Cインターフェースについて調べたのですが、これもよくわかりませんでした。
HやLなどを使ってデータを区切っているのでしょうか?
また、クロックという語句があるのですが、それは間隔をとるためのものなのでしょうか?

一通り調べて、山口さんが作成したLSM303DLHのライブラリーを使おうとしたのですが、ライブラリーをインストールして動かしてみても値が返ってきません。
配線はどのようにしたらいいのでしょうか?


I2Cインターフェースの仕組みと、加速度はx,y,zと3つのデータがあるのに対し、ピンは2つだけでいいところが、分かりません。
以前使っていたMMA7361Lはアナログ出力だったため、3軸すべての値が別のピンで出力されていたので分かりやすかったのですが、I2Cではどのように送信しているのでしょうか?



質問が多くて申し訳ないです。すみませんが回答よろしくお願いします。
樫原 輝
 
記事: 134
登録日時: 2011年7月07日(木) 17:26

Re: LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムについて

投稿記事by yamaguch » 2012年8月10日(金) 13:12

樫原さん、こんにちは、

樫原 輝 さんが書きました:何ヶ月か前に同じような質問をさせていただいたのですが、その質問に対する山口さんの回答を参考にmbedのhandbookにあるI2Cを読み、サンプルプログラムを見たのですが、よくわかりませんでした。
次にI2Cインターフェースについて調べたのですが、これもよくわかりませんでした。
HやLなどを使ってデータを区切っているのでしょうか?
また、クロックという語句があるのですが、それは間隔をとるためのものなのでしょうか?

I2Cインタフェースはセンサーなどを2本の信号線でつなぐインタフェースです。
電源と GND 以外に2本ということで、データ線とクロック線があります。
どちらも High または Low の値を取る信号線です。
データはデータ線で送るのですが、データ線だけでは切れ目が分からないので、クロック線を使って拍子を取る(同期を取る)ような仕組みです。
それほど複雑なインタフェースではないので、根気よく調べてみてください。

他のインタフェースと比較すると理解しやすいと思います。
(1) シリアル(Serial)
 送信、受信用の2本の信号線を使って通信する方法です。
 クロック線はありませんが、通信速度が決まっていて「調歩同期」とよばれる仕組みで同期を取ります。
 通信速度があまり速くないのと1対1の通信しかできません。

(2) SPI
 送信用、受信用とクロックの3本の信号線を使って通信する方式です。
 クロック線の電圧の変化に合わせてデータを送受信するので高速な通信が可能です。
 複数の相手と通信をすることができますが、相手を選択するための信号線(スレーブ選択)が必要になります。
 N 個の相手と通信するためには N 本の信号線が必要です。

(3) I2C
 データ線とクロック線の2本の信号線を使って通信する方式です。
 SPI に似ていますが、データ線を送信と受信の両方に使います。
 また、7ビットのアドレスを使って相手を識別するので、
 信号線を増やすことなく複数の相手と通信することができます。
 クロックを使っているので SPI ほど速くはないですが、シリアルに比べると格段に高速です。

一通り調べて、山口さんが作成したLSM303DLHのライブラリーを使おうとしたのですが、ライブラリーをインストールして動かしてみても値が返ってきません。
配線はどのようにしたらいいのでしょうか?


I2C のデバイスには SDA(データ)と SCL(クロック)の端子があります。
これらを mbed の SDA と SCL につなぎます。
さらに、通常、SDA, SCL の線はプルアップしておく必要があります。
(データの送受信が行われていないときには SDA, SCL は High になっています)
これには 10〜20kΩ 程度の抵抗を使って、SDA と VOUT(それと SCL と VOUT) をつなぎます。

I2Cインターフェースの仕組みと、加速度はx,y,zと3つのデータがあるのに対し、ピンは2つだけでいいところが、分かりません。
以前使っていたMMA7361Lはアナログ出力だったため、3軸すべての値が別のピンで出力されていたので分かりやすかったのですが、I2Cではどのように送信しているのでしょうか?


アナログだと直感的ですが、I2C では、mbed からリクエストを送って、その応答として各軸の値をもらうような感じです。

実は、ここが I2C の面白いところなので、いろいろ調べてみてください。
mbed を作った NXP (Philips) が今から 30 年前に開発したインタフェースです。

最新の仕様書は
http://www.nxp.com/documents/user_manual/UM10204.pdf
にあります。

山口
yamaguch
 
記事: 482
登録日時: 2010年7月06日(火) 17:37

Re: LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムについて

投稿記事by 樫原 輝 » 2012年8月10日(金) 16:45

こんにちは、山口さん


詳しい説明ありがとうございます。
I2Cについては、まだ100%理解することは出来ていませんが、だいたい仕組みをつかむことは出来ました。


まずは、同じI2Cでmbedと通信している気圧センサー(MPL115A2)のプログラムを我が部の大崎と一緒に解読しようとしました。
気圧センサーのプログラムについては、だいたいは理解することが出来ました。
次に、問題のLSM303DLHを使おうとしました。
同じく、山口さんが作成したライブラリーを使用しました。
サンプルプログラムに「INT1」や「INT2」があるのですが、このピンの配線はいるのでしょうか?
また、サンプルプログラムにはピンがPWMOUTにも接続されており、I2Cには2本しか配線されていなかったのですが、加速度、地磁気は一つのSDA,SCLで通信して大丈夫なのでしょうか?

LSM303DLHの仕様書を見ると、ピンの役割として11ピンが加速度センサSDA、10ピンが加速度センサSCL、9ピンが地磁気センサSDA、8ピンが地磁気センサSCLとなっています。
しかし、サンプルプログラムですと、mbedのピンの指定が、I2CがSDA,SCLが1つずつ、PWMOUTが2つのピンに接続されているだけで、I2CのSDA,SCLが1ピンずつ足りないように思うのですが、どうなのでしょうか?
また、lsm.getHeading()とlsm.attachの役割が分からないです。


先ほどの回答で教えていただいた、プルアップは10kΩの抵抗を使い配線しました。(気圧センサーMPL115A2の配線を参考にしました)


すみませんが、回答よろしくお願いします。
樫原 輝
 
記事: 134
登録日時: 2011年7月07日(木) 17:26

Re: LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムについて

投稿記事by 樫原 輝 » 2012年8月10日(金) 17:21

追記です
配線の様子を画像で投稿します。
間違いがあれば指摘よろしくお願いします。
添付ファイル
mbed_2.jpg
mbed_2.jpg (196.87 KiB) 表示数: 15747 回
mbed_1.jpg
mbed_1.jpg (194.88 KiB) 表示数: 15747 回
樫原 輝
 
記事: 134
登録日時: 2011年7月07日(木) 17:26

Re: LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムについて

投稿記事by yamaguch » 2012年8月10日(金) 19:16

樫原 輝 さんが書きました:次に、問題のLSM303DLHを使おうとしました。
同じく、山口さんが作成したライブラリーを使用しました。
サンプルプログラムに「INT1」や「INT2」があるのですが、このピンの配線はいるのでしょうか?
また、サンプルプログラムにはピンがPWMOUTにも接続されており、I2Cには2本しか配線されていなかったのですが、加速度、地磁気は一つのSDA,SCLで通信して大丈夫なのでしょうか?

まず、ライブラリのヘッダーファイル(LSM303DLH.h)を見てください。
http://mbed.org/users/yamaguch/code/LSM ... ource.html
自分用なので、API ドキュメント用のコメントはサボっています。
コンストラクタは
LSM303DLH(PinName sda = p9, PinName scl = p10, PinName int1 = NC, PinName int2 = NC);

です。引数には4つのピンの名前を sda, scl, int1, int2 の順番に指定するようにしています。
省略すると sda = p9, scl = p10 が指定したことになります。
また、int1, int2 は機能を使わないときには省略します。(あとで説明します)

次の2つの関数はセンサーが動作するときのパラメタを設定するためのものです。
どのくらいの頻度で測定するのか、あるいは測定する範囲はどれくらいかなどを設定します。
設定する値は、ヘッダファイル内の上の方に enum で定義してあります。
詳細については、マニュアルを読んでください。
bool setOutputDataRate(ACC_ODR acc_odr, MAG_ODR mag_odr);
bool setMeasurementRange(ACC_RANGE acc_range, MAG_RANGE mag_range);

次の read() は、加速度と方位のデータを読むための関数です。
読んだ値は内部に記録され、getHeading() で使われます。

read(float *ax, float *ay, float *az, float *mx, float *my, float *mz)

は、実際に読み取ったデータを受け取る場合に使います。
加速度ベクトルを (accelx, accely, accelz), 方位ベクトルを (magx, magy, magz)に受け取りたいときには、これらの変数を float 型で宣言しておき

コード: 全て選択
read(&accelx, &accely, &accelz, &magx, &magy, &magz);
のように呼び出します。

getHeading()は、どの方角を向いているかを角度で返します。0 だと北,90 だと東、180 は南という感じです。
(多分あっていると思いますが、ひょっとすると逆回りかもしれません)

getHeading(x, y, z) は (x, y, z) の方向を基準にして、現在の方向がどれだけ(何度)ずれているかを返します。

attach() は、割り込みの動作を指定するための関数です。
予め、しきい値を決めておいて、その範囲に入ると何かの処理をしたいような場合に指定します。
分かりやすいのは自由落下の状態を検知するような例です。

Example のプログラムでは INT1, INT2 を使っています。割り込みの条件を満たすと INT1 detected のようなメッセージがターミナルに表示されます。条件を指定するパラメタはマニュアルの 35〜37ページあたりに書いてありますが、
例の最初の
lsm.attach(INT1, 0x95, 31, 3, int1Detected);

では INT1 割り込みの条件として 0x95 = 10010101 で、最初の2ビットが AND 条件、のこりの 010101 がX, Y, Z 軸の低い方のしきい値を使うという意味です。31 はしきい値の値、その後の 3 は持続時間です(多分ミリ秒)で合わせると3軸全ての加速度が 31 より小さくなった状態が 3ミリ秒続いたら INT1 割り込みの信号を線を HIGH にして、int1Detected() を呼び出しなさいというような設定をしています。「自由落下の検出」ですね。もう一つの方は AND 条件でどれか軸の加速度が 127 を超えたらINT2割り込み状態にして int2Detected() を呼び出すような設定です。
強く振るとか放り投げるとかしてみると分かると思います。

http://www.st.com/internet/com/TECHNICAL_RESOURCES/TECHNICAL_LITERATURE/DATASHEET/CD00260288.pdf

LSM303DLHの仕様書を見ると、ピンの役割として11ピンが加速度センサSDA、10ピンが加速度センサSCL、9ピンが地磁気センサSDA、8ピンが地磁気センサSCLとなっています。
しかし、サンプルプログラムですと、mbedのピンの指定が、I2CがSDA,SCLが1つずつ、PWMOUTが2つのピンに接続されているだけで、I2CのSDA,SCLが1ピンずつ足りないように思うのですが、どうなのでしょうか?
また、lsm.getHeading()とlsm.attachの役割が分からないです。


加速度センサと地磁気センサではI2C のアドレスが異なっています。ですから、SDA, SCL は一組でいいのです。その後の2本は INT1 と INT2 用のピンです。
PwmOut に使っているわけではありません。

山口
yamaguch
 
記事: 482
登録日時: 2010年7月06日(火) 17:37

Re: LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムについて

投稿記事by 樫原 輝 » 2012年8月11日(土) 11:23

こんにちは、山口さん

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


大体理解することが出来ました。
山口さんが作ってくださったサンプルプログラムで、もう一度配線を見直して動かしてみました。
すると、センサー値は読み取ることが出来なかったのですが、割り込み処理には成功していました。

これは、センサーは値を読み取っているけれども、センサーが出力(または、mbedが読み取ることが)できていないということですか?
何か配線上問題があるのでしょうか?
僕たちが作った回路の配線図を添付させていただくので、すみませんが、間違いがありましたら教えてください。お願いします。

コード: 全て選択
#include "LSM303DLH.h"

LSM303DLH lsm(p28, p27, p23, p22);

void int1Detected() {
    printf("INT1 detected\n");
}

void int2Detected() {
    printf("INT2 detected\n");
}
/*
* AOI AND 1 0
* 6D  6D  0 0
* ZH      0 1
* ZL      1 0
* YH      0 1
* YL      1 0
* XH      0 1
* XL      1 0
*/
int main() {
    lsm.attach(INT1, 0x95, 31, 3, int1Detected);
    lsm.attach(INT2, 0x2A, 127, 3, int2Detected);
    while (true) {
        if (lsm.read()) {
            printf("acc: (%f, %f, %f), mag: (%f, %f, %f)\n", lsm.ax, lsm.ay, lsm.az, lsm.mx, lsm.my, lsm.mz);
            printf("direction = %.0f\n", lsm.getHeading() * 180 / 3.14159265358979);
        }
        wait(5);
    }
}
           
添付ファイル
Epson_1205.png
Epson_1205.png (227.37 KiB) 表示数: 15736 回
樫原 輝
 
記事: 134
登録日時: 2011年7月07日(木) 17:26

Re: LSM303DLH ディジタル3軸地磁気センサ+3軸加速度モジュールの配線とプログラムについて

投稿記事by yamaguch » 2012年8月11日(土) 12:52

こんにちは、

樫原 輝 さんが書きました:すると、センサー値は読み取ることが出来なかったのですが、割り込み処理には成功していました。


センサー値は読み取ることができなかったというのは、具体的にどういう出力がされたのですか。

割り込み処理に成功したというのは、自由落下や強く振ってみることで "INT1 detected", "INT2 detected" と表示されたということですか。

山口
yamaguch
 
記事: 482
登録日時: 2010年7月06日(火) 17:37

次へ

Return to mbed 質問箱

cron