ページ更新: 2015-08-17 (月) (555日前)

関連: 組み込み/mbed, 組み込み/STM32, 組み込み/AVR, 組み込み/RaspberryPi

(2015-08-14 新規作成)

モーターとモータードライバについてのメモ。

目次

[編集]

メモ #

[編集]

サーボモーター #

[編集]

DCモーター #

[編集]

ステッピングモーター (作業中 2015-08-11) #

ステッピングモーター を回してみる。

機材:

STMicroelectronics, L6470

参考:

[編集]

TA7291Pで駆動、ただし手動で #

最初にDCモーター (FA-130RA) を回してみる。

DCモーターを1つ。TA7291Pを1つ使う。電源は5V。2つのスイッチのうち、IN1を押すと正回転、IN2を押すと逆回転。スイッチの抵抗はプルアップ:

TA7291P_DCmotor_pullup-sw.jpg

DCモーターを2つ。TA7291Pを2つ使う。スイッチの抵抗はプルダウンに変更した:

TA7291P_DCmotor2_pulldown-sw.jpg

ステッピングモーターを回す。電源は9V。

  • 一相励磁ならスイッチを1つだけ「青、赤、黄、緑」の順で押すと正回転。逆順で逆回転。
  • 二相励磁ならスイッチを同時に2つ押す。「青・赤」、「赤・黄」、「黄・緑」、「緑・青」の順で押すと正回転。逆順で押すと逆回転:
  • 後で気が付いたのだが、このとき、IN1,IN2にも9Vを供給していた。TA7291P の IN1,IN2の Vhighの範囲は 3.5〜5.5V なので、動作範囲外になる。

TA7291P_StepperMotor-001.jpg TA7291P_StepperMotor-002.jpg

スイッチの代わりにマイコンのGPIOやPWMでIN1,IN2を切り替えてやれば、モーターが回転するはず。

以下、作業中

[編集]

L6470 + Nucleo 結線 (2015-08-14) #

モーターのケーブル作成。付属の2mmピッチピンヘッダに手持ちのケーブル (AWG24かAWG22だと思う) をはんだ付け。

モータードライバ基板に端子台とピンヘッダをはんだ付け。なお、SW(位置検出用)のピンヘッダは付属していないので、後で何か付けるつもり。

AE-L6470DRV_MDP-35A-001.jpg

mbed Nucleo F411RE と モータードライバ基板 AE-L6470DRV とステッピングモーター MDP-35A を接続。電源は 12V AC-DCアダプタから。 (L6470は最低8Vが必要なので)。 Nucleo L152RE に差し替えるかもと思ったので、F411REとAE-L6470DRVの間には中継基板を介した。

AE-L6470DRV_mbed-001.jpg

GND、SPI (SCK, MISO, MOSI, CS) を相互に接続:

AE-L6470DRV_mbed-002.jpg AE-L6470DRV_mbed-003.jpg

[編集]

L6470 + Nucleo SPI通信 (2015-08-14) #

SPI通信の確認のために、mbed Nucleo で、モータードライバの初期化、ステータス(レジスタh19)読み出し、レジスタの読み出しを試してみた。

データシート(DocID16737 Rev 6) より、SPIの仕様は:

  • SPI の最高速度は 5Mbit/s
    • p.1, 「All commands and data registers, (略) are sent through a standard 5-Mbit/s SPI.」
    • p.13, 「Maximum SPI clock frequency : Min 5MHz」
  • 1byte 転送する毎に CS negate が必要。
    • p.38, 「After each byte transmission the CS input must be raised and be kept high for at least tdis CS in order to allow the device to decode the received command and put the return value into the SHIFT register.」
  • CS assert後の待ち時間は 350ns, negate 後に再assertするときの間隔は 800ns。
    • Chip select setup time : Min 350 ns
    • tdis : Deselect time : Min 800 ns
  • データ転送は8bit単位、ビット順はMSBファースト。
  • SPIのモードは stsw-spin004 firmware library dSPIN discovery - STMicroelectronics の dspin.c の void dSPIN_Peripherals_Init(void) によると、SPI_CPOL_High で、 SPI_CPHA_2Edge だから、モード3だと思う。

ソースコード (mbed Nucleo F411RE で確認)

#include "mbed.h"

SPI device(SPI_MOSI, SPI_MISO, SPI_SCK);
DigitalOut cs(SPI_CS);

Serial pc(USBTX, USBRX);

const uint8_t GET_PARAM  = 0x20;    // 001x xxxx
const uint8_t RESET_DEVICE = 0xC0;  // 1100 0000
const uint8_t GET_STATUS = 0xD0;    // 1101 0000

/**
 * @param[in] cmd
 * @param[out] data
 * @param[in] len
 */
void readData(const uint8_t cmd, uint8_t data[], const int len) {
    cs = 0;
    wait_us(1); // > 350ns
    device.write(cmd);
    cs = 1;
    wait_us(1); // > 800ns

    for (int i = 0; i < len; ++i) {
        cs = 0;
        wait_us(1); // > 350ns
        data[i] = device.write(0);
        cs = 1;
        wait_us(1); // > 800ns
    }
}

/**
 * @param[in] cmd
 * @param[in] data
 * @param[in] len
 */
void writeData(const uint8_t cmd, uint8_t data[], const int len) {
    cs = 0;
    wait_us(1); // > 350ns
    device.write(cmd);
    for (int i = 0; i < len; ++i) {
        device.write(data[i]);
    }

    cs = 1;
    wait_us(1); // > 800ns
}

const uint8_t data_bits[] = {
    0,  // dummy
    22,
    9,
    22,
    20,
    12, // h05
    12,
    10,
    13, // h08
    8,  // h09
    8,
    8,
    8,
    14, // h0D
    8,
    8,
    8,
    4,
    5,  // h12
    4,
    7,  // h14
    10, // h15
    8,  // h16
    8,
    16,
    16, // h19
};

/** 切り上げ */
static inline uint8_t roundUp(const uint32_t value, const uint8_t unit) {
    return (value + unit - 1) / unit;
}

int main() {

    pc.baud(115200);
    pc.printf("CPU SystemCoreClock is %.2f MHz\r\n", (float)SystemCoreClock/1000.0f/1000.0f);

    // initialize SPI
    cs = 1;
    device.frequency(5 * 1000 * 1000); // MAX 5MHz
    device.format(8, 3);    // 8bit, mode 3? (SPI_CPOL_High, SPI_CPHA_2Edge)

    writeData(0x00, NULL, 0);
    writeData(0x00, NULL, 0);
    writeData(0x00, NULL, 0);
    writeData(0x00, NULL, 0);
    writeData(RESET_DEVICE, NULL, 0);

    uint16_t count = 0;
    for (;;count++) {
        // GetStatus
        uint8_t status[2];
        {
            readData(GET_STATUS, status, 2);
        }

        // GetParam
        uint8_t regs[1 + 0x19][3];
        for (int r = 1; r <= 0x19; r++) {
            const uint8_t cmd = GET_PARAM | r;
            const uint8_t nbytes = roundUp(data_bits[r], 8);
            readData(cmd, regs[r], nbytes);
        }

        pc.printf("%5d: GetStatus(%02X) %02X %02X\r\n",
            count, GET_STATUS, status[0], status[1]);
        for (int r = 1; r <= 0x19; r++) {
            const uint8_t cmd = GET_PARAM | r;
            const uint8_t nbytes = roundUp(data_bits[r], 8);
            pc.printf("%5d: GetParam(%02X) %02X, data ", count, cmd, r);
            for (uint8_t b = 0; b < nbytes; ++b) {
                pc.printf("%02X ", regs[r][b]);
            }
            pc.printf("\r\n");
            wait_ms(10);
        }

        wait_ms(1000);

    }
}

ログ:

  • データシート p.40, Table 9. Register map と付き合わせたところ、Reset Hex と一致した。
CPU SystemCoreClock is 96.00 MHz
   0: GetStatus(D0) 7C 03
   0: GetParam(21) 01, data 00 00 00
   0: GetParam(22) 02, data 00 00
   0: GetParam(23) 03, data 00 00 00
   0: GetParam(24) 04, data 00 00 00
   0: GetParam(25) 05, data 00 8A
   0: GetParam(26) 06, data 00 8A
   0: GetParam(27) 07, data 00 41
   0: GetParam(28) 08, data 00 00
   0: GetParam(29) 09, data 29
   0: GetParam(2A) 0A, data 29
   0: GetParam(2B) 0B, data 29
   0: GetParam(2C) 0C, data 29
   0: GetParam(2D) 0D, data 04 08
   0: GetParam(2E) 0E, data 19
   0: GetParam(2F) 0F, data 29
   0: GetParam(30) 10, data 29
   0: GetParam(31) 11, data 00
   0: GetParam(32) 12, data 08
   0: GetParam(33) 13, data 08
   0: GetParam(34) 14, data 40
   0: GetParam(35) 15, data 00 27
   0: GetParam(36) 16, data 07
   0: GetParam(37) 17, data FF
   0: GetParam(38) 18, data 2E 88
   0: GetParam(39) 19, data 7E 03
   1: GetStatus(D0) 7E 03
   1: GetParam(21) 01, data 00 00 00
   1: GetParam(22) 02, data 00 00
   1: GetParam(23) 03, data 00 00 00
   1: GetParam(24) 04, data 00 00 00
   1: GetParam(25) 05, data 00 8A
   1: GetParam(26) 06, data 00 8A
   1: GetParam(27) 07, data 00 41
   1: GetParam(28) 08, data 00 00
   1: GetParam(29) 09, data 29
   1: GetParam(2A) 0A, data 29
   1: GetParam(2B) 0B, data 29
   1: GetParam(2C) 0C, data 29
   1: GetParam(2D) 0D, data 04 08
   1: GetParam(2E) 0E, data 19
   1: GetParam(2F) 0F, data 29
   1: GetParam(30) 10, data 29
   1: GetParam(31) 11, data 00
   1: GetParam(32) 12, data 08
   1: GetParam(33) 13, data 08
   1: GetParam(34) 14, data 40
   1: GetParam(35) 15, data 00 27
   1: GetParam(36) 16, data 07
   1: GetParam(37) 17, data FF
   1: GetParam(38) 18, data 2E 88
   1: GetParam(39) 19, data 7E 03
   2: GetStatus(D0) 7E 03
   ...

ロジックアナライザ:

  • SPI クロックを 5MHz に設定しているのに、1/(170ns + 160ns) = 3.03 MHz くらいしかでていない。STBee が 18MHz (72MHz / 4) くらいは出せたと思うのだが。96MHz / 8 / 4 で 3MHz なのか?
  • SCK からの MISO が確定するまで 30〜50ns。

L6470-20150814-1byte-001.png L6470-20150814-1byte-002.png