背景
今回のターゲット
先日、お仕事とは関係ない、とある家庭用機器を開封したところ、このようなパッケージのフラッシュメモリがありましたので検証に用います。下の赤い定規の1目盛りが1mmです。
デジタル顕微鏡で拡大した画面を携帯で撮影したため、画像が荒くてごめんなさい
Macronix社のMX25L8006Eというフラッシュメモリで、パッケージの横にピンが出ています。
変換基板のはんだづけと接続
今回はピン間隔が0.8mmと珍しいピッチだったので、千石電商さんで変換基板を購入しました。はんだづけし、各ピンがジャンプしていないことを確認します。
その後、BusPirateとフラッシュメモリをこのように接続します。
ピン名が CS# または /CS のように記載されているものは、アイドル時にはHigh、アクティブ時にLowとなるピンです。
BusPirateの設定
設定設定時のログを記載します。SPI通信に関わる各項目は、大抵はデフォルト値でよいのですが、正確にはフラッシュメモリのデータシートを見ながら設定する必要があります。
例1:ビットの読出タイミングはクロックの立ち上がり or 立ち下がり?
例2:クロックはActive High or Active Low?
今回は、以下の変更以外はデフォルトの値を用いています。
- SPIモード・1MHzの通信を選択
- Highレベルの電圧を3.3V固定
HiZ>i
Bus Pirate v3.5
Firmware v6.1 r1676 Bootloader v4.4
DEVID:0x0447 REVID:0x3046 (24FJ64GA002 B8)
http://dangerousprototypes.com
HiZ>m
1. HiZ
2. 1-WIRE
3. UART
4. I2C
5. SPI
6. 2WIRE
7. 3WIRE
8. LCD
x. exit(without change)
(1)>5
Set speed:
1. 30KHz
2. 125KHz
3. 250KHz
4. 1MHz
(1)>4
Clock polarity:
1. Idle low *default
2. Idle high
(1)>
Output clock edge:
1. Idle to active
2. Active to idle *default
(2)>
Input sample phase:
1. Middle *default
2. End
(1)>
CS:
1. CS
2. /CS *default
(2)>
Select output type:
1. Open drain (H=Hi-Z, L=GND)
2. Normal (H=3.3V, L=GND)
(1)>2
Ready
SPI>W
POWER SUPPLIES ON
SPI>v
Pinstates:
1.(BR) 2.(RD) 3.(OR) 4.(YW) 5.(GN) 6.(BL) 7.(PU) 8.(GR) 9.(WT) 0.(Blk)
GND 3.3V 5.0V ADC VPU AUX CLK MOSI CS MISO
P P P I I I O O O I
GND 3.34V 5.00V 0.00V 3.33V L L H H L
接続が正しいことを確認するテスト
フラッシュメモリの中身を読み出す前に、物理的な接続やSPIのモードが正しいことを確認します。予め既知である値が正しく読み出せなければ、フラッシュメモリから読み出したファームウェアやデータも正しくありません。今回は既知の値として、JEDEC IDを使用します。
JEDEC IDとは、JEDECという半導体製造メーカーの団体が、各ベンダやICチップごとに固有の値を設定したものです。今回のフラッシュメモリのデータシートによると、JEDEC IDは 0xC2 0x20 0x14、読み出しコマンドは 0x9F と分かりました。0x9Fを送信すると、その後3バイトの情報を送信してくれます。
使用したコマンドとログを記載します。今回はBusPirateがSPIのMaster、MX25L8006EがSPIのSlaveです。記載のようにJEDEC IDが読めたので、物理的な接続、およびSPIの動作モードは正しいようです。
ログ:
SPI>{ 0x9f r:3 ]
/CS ENABLED
WRITE: 0x9F READ: 0x00
READ: 0xC2 0x20 0x14
/CS DISABLED
コマンドの解説
{ : Start with read, /CSをLowにし、Slaveとの通信を開始する。この際、Slaveからの読出も行う
0x9f : BusPirateからMX25L8006Eに対するRDID(Read Identification)コマンド
r:3 : 3バイト読み出す。この時、クロックはBusPirateが自動で送信してくれる。
] : /CSをHighにし、Slaveとの通信を終了する。
読み出し
ついにフラッシュメモリに記録された情報を読み出します。読み出しコマンドはデータシートによると 0x03、その後にアドレスを24ビット指定します。その後、クロックを送ると、アドレスをインクリメントしながら返信してくれます。
以下に、試しに16バイト読み出した際のコマンドとログを記載します。何か読めました。
ログ:
SPI>{ 0x03 0 0 0 r:16 ]
/CS ENABLED
WRITE: 0x03 READ: 0x00
WRITE: 0x00 READ: 0x00
WRITE: 0x00 READ: 0x00
WRITE: 0x00 READ: 0x00
READ: 0x58 0x00 0x00 0x00 0x35 0x10 0x00 0x00 0x36 0x10 0x00 0x00 0xB0 0x27 0x00 0x00
/CS DISABLED
コマンドの解説:
{ : Start with read
0x03 : BusPirateからMX25L8006Eに対するREADコマンド
0 0 0 : 読み出すアドレス24ビット。アドレスマップの先頭を指す。
r:16 : 16バイト読み出す。この時、クロックはBusPirateが自動で送信する。] : /CSをHighにし、Slaveとの通信を終了する。
BusPirate v3.6のバッファが48kバイト程度しかないため、私はログを取りながら32kバイトずつ読み、バイナリに固めます。
ログ:
SPI>{ 0x03 0 0 0 r:32768 ]
/CS ENABLED
WRITE: 0x03 READ: 0x00
WRITE: 0x00 READ: 0x00
WRITE: 0x00 READ: 0x00
WRITE: 0x00 READ: 0x00
READ: 0x58 0x00 0x00 0x00 0x35 0x10 0x00 0x00 0x36 0x10 0x00 0x00 0xB0 0x27 0x00 0x00 0xB1 0x27 0x00 0x00 0xB8 0x4A 0x00 0x00 0xB9 0x4A 0x00 0x00 0xDE 0x66 0x00 0x00 0xDF 0x66 0x00 0x00 0xCC 0x82 0x00 0x00 0xCD ...(以下省略)
トラブルシューティング
本当はロジックアナライザで確認するのが最も確実なのですが、手元のBusPirateを用いて、意図的に正しく動作しない状態で動作させてみました。
JEDEC IDを読んでも 0x00 しか返ってこない
MOSIピン、MISOピン、HOLD# ピンの接続を確認してください。試しに、HOLD# ピンに何も接続していない状態だとこうなりました。
SPI>{ 0x9f r:3 ]
/CS ENABLED
WRITE: 0x9F READ: 0x00
READ: 0x00 0x00 0x00
/CS DISABLED
READコマンドを実行しても、全部 0xFF なんだけど
正しく動作している BusPirateの設定
SPI>i
Bus Pirate v3.5
Firmware v6.1 r1676 Bootloader v4.4
DEVID:0x0447 REVID:0x3046 (24FJ64GA002 B8)
http://dangerousprototypes.com
CFG1:0xFFDF CFG2:0xFF7F
*----------*
Pinstates:
1.(BR) 2.(RD) 3.(OR) 4.(YW) 5.(GN) 6.(BL) 7.(PU) 8.(GR) 9.(WT) 0.(Blk)
GND 3.3V 5.0V ADC VPU AUX CLK MOSI CS MISO
P P P I I I O O O I
GND 3.34V 5.00V 0.00V 3.33V L L H H L
POWER SUPPLIES ON, Pull-up resistors OFF, Normal outputs (H=3.3v, L=GND)
MSB set: MOST sig bit first, Number of bits read/write: 8
a/A/@ controls AUX pin
SPI (spd ckp ske smp csl hiz)=( 4 0 1 0 1 0 )
*----------*
最後に
- 適合するアダプタが無い、もしくは入手困難である
- アダプタは入手可能だが、配送期間を待てない
- アダプタの使用頻度と価格のバランスが悪い
- ROMライタでサポートされていない