顯示具有 Hardware 標籤的文章。 顯示所有文章
顯示具有 Hardware 標籤的文章。 顯示所有文章

9.15.2010

Serial TS (Transport Stream) bus signal definition

Serial Type Transport Stream 的信號 pin 有:
  • TSCLK : clock
  • TSO : Data
  • TSEN : TS valid (有點類似 chip select)
  • TSPAC : Syn Byte (在送出 sync byte 的data 時會有動作)
  • TSER : TS Packet Error flag (packet 有 error 時會有動作)
Transport Stream 分為 3 部份:

Sync --- Stream Data -- Pariry

其中 Sync + Stream Data == 188 byte
Parity 有 16 byte

一般的 chip 可以指定 TSEN 要不要把 parity 的data 也算進去。
另外,除了 stream packet 外,在沒有信號,或是有 error 時,會有 NULL packet。
也可以決定在送 null packet 時,clock 要不要動作。

9.14.2010

奇怪mcu的I2C奇怪波形

悲哀的cheap mcu,送出的 I2C 撥波行徑然是..
poormcubadi2cwave
可以看到在 START command 前,會送出一個 CLK, SDA 都是 Low 的 plus,然後 start condition 後, SDA 竟然會有一個 high-puls。
雖然這樣沒有違反 I2C wave form standard(?)
ref : wiki

但是有些 chip 就是不吃這樣的波形呀。

能偷就偷,不知道這種 chip design house 的品質是怎樣做出來的...

9.09.2010

ULPI -- USB interface standard

USB Controller 與 PHY 的介面原為 22 pin 以上的 UTMI 介面。
後來為了減少 pin count,重新定義了12 pin 的 ULPI (UTMP+ Low Pin Interface)介面。

從此,USB controller 與 PHY 只要是標準 ULPI 介面的,都可以互換。

ULPI 的標準竟然含一個 由 PHY 輸出的 CLKOUT(60MHz)。
也就是說,ULPI 標準,規定了 crystal 要裝在 PHY 那一端。(?)

ULPI 也規定了內部的 register map,所以才能達到 chip 可以互換的要求。
規定了四類 register:
  • ID
  • Mode
  • Interrupt
  • Extra

8.05.2010

pipeline bubble

利用 assembly 來optimize speed 時,要注意,並不是 instruction line 短就夠了。
還要注意 pipline 的特性。

pipeline 將指令分成幾個 stage:
  • fetch,
  • decode/register read,
  • alu,
  • memory write,
  • register update.
如果這樣個 assembly codes:
ldr r0,#1
add r3,r0,r1
第二行指令在 decode/register read 時,r0 還沒update,因為上一行才執行到alu operation。所以在pipeline中的第二行指令就要停下來,等兩個clock,等上一行指令執行到register update後,才可以繼續。
這樣,就白白浪費 2 個 clock 了。

為了避免這樣的情況,寫 assembly 的時候,就可以在中間插入下面要作的 assembly code,不要白白浪費這兩個clock

在 (很久)前面的文章:yuv - rgb color space convert 的 assembly code 可以看到。最後一個作者的assembly code 就有做到這個(所以整個 code 的 flow 變得不好trace)。實測的結果,也是最快的。

在 Wiki 里也有說明:
instruction scheduling
Instruction scheduling is an important optimization for modern pipelined processors, which avoids stalls or bubbles in the pipeline by clustering instructions with no dependencies together, while being careful to preserve the original semantics.

8.04.2010

cache

cache 是一小塊和cpu時脈一樣的記憶體,作為 cpu 與 主記憶體間的 buffer。
當 cpu 要讀取 memory 時, cache 先把 memory 的資料讀進 cache 中,然後再讓 cpu 讀取。

cpu 每次讀取的單位是 int (32bit),但是 cache 為求效能,會一次讀入比 int 還多的資料。
cache 每次讀入的資料大小叫 line size,每次讀入的資料放入 一個 line。

cache 就是利用這樣預先讀取的能力,讓cpu 下次需要讀取記憶體時,可以直接由 cache 拿,不需要再向 主記憶體 讀取。


由於 cache 只有小小一塊,所以必須要有一個機制知道 cpu 需要存取記憶體時,那個 address的內容是不是已經在cache 里,如果在,是在 cache 的那一條 line ...

最直覺的方法就是去找每一個 cache line 的 address,看看那一個 line 所以 cache 的 記憶體位址是不是 cpu 現在要的。

這樣個 cache 叫 associative cache.

但是這樣作很耗空間(電路),因為每一個 line 都要作一個 address比較電路。
所以就有比較便宜的作法.. 把 把 address 分成兩部份:

tag, index

以 32 bit 的 address line 為例,可以分成:
  • tag : 31~20
  • index : 19~0
這樣要找cache 時就可以反過來用,用 address的 0~19作 index,找到那個 cache index line 的 tag,然後跟 31~20比較就可以。


後來又有折衷的辦法,就是...每個 index 可以有兩個 tag欄位和lines,這樣,每20 條位址線,就可以共用兩條 cache line。 -- 這就叫 2 way cache.
=>這樣就是:拿 index 找到對應的 2 個 tag ,比較和 address bit 31-20 一步一樣。

一此類推,可以有 4 way cache。

這一篇 (http://www.mirabilisdesign.com/Pages/Demonstrations/systemarchitecture/Cache_System/Functional_Cache_Model_Overview.html)雖然是 sim software 的說明,但是可以看到 ARM11 cache 的 impelement 圖例

cache line size 是 16 words (address 0~3), index size 是 4096 (address 4~15), tag filed 是 address 16~31,




所以 cache index size x byte size x way = cache size

7.20.2010

Mode Register Set - DDR

DDR 也有一堆參數可以設,但是 Memory 不像 MCU 或 periperial IC 一樣,有 register 可以設。
memory 的 address/data line 直接對應到內部的 cell,沒有 mapping到內部的 register。
所以 DDR Spec 規定了一個 bus pattern ,當 bus pattern 是這樣,A0~A14 就對應要寫入 register 的內容。 這個動作就叫做 Mode Register Set
一般好像 CS, CAS, RAS, WE 都是 low 的時候是 mode register set,這時後 A0~A14 的內容會被解讀為 mod register set command 的 op-code
好像在 chip power up sequence 中有MRS 的階段,所有 DDR 開機都要經過這個階段?有些把這個"寫入 DDR Mode Rester" 的動作叫 Load Mode Register - LMR)

Mode Register Set 還有 Extended Mode Register Set,可以用來設定 DDR 的 auto-refresh type (range) 和 DDR 的 output current/strength。

Mode Register Set 要 MCU 的 control 支援,通常 MCU 的 memory control unit 會提供 EMRS register 和 EMRS-cycle (設定 EMRS 鎖需要的clock)

7.19.2010

DDR

在 DRAM 的設計上,加快 memory core 的 clock rate 比較難,所以都朝著 增加 i/o bus clock 來改進。

DDR 的規格,就是這樣。設法從 memory core 一次提出多一點的 data,然後 queue 住,等 i/o 提取。
這樣就可以增加 i/o 的 clock rate.

RAS - Bank Select。所以 tRAS 就是 Bank open time.
RC - RAW Cycle 。tRC = tRAS + tRP.
Raw Access 的 cycle time =RAS pulse width + Precharge latency
RP 就是 precharge time.

為降低 power ,所以DDR2 由 2.5V 降到 1.8V
工作電壓降低也有助於增加clock rate (voltage swing).

高速後,layout trace delay 的問題也開始要考慮

DDR 解決的方法是在 data strobe 前加上 clock forwarding
DDR2 則再加入 different signal 的要求:DQS, /DQS.


Understanding RAM Timings
CL (CAS Latency) 是說,當 Read Cmd 後,需要多少 clock ,memory 的 data 才能 ready。
所以 CL=3 ,代表 read command 後,還要等 3 個 clock ,才能讀 data。

memory 有所謂的 burst mode,就是當下一個 data 和這一個 data 是連續的時候,下一個 data 不需要等 CL 個clock,可以在下一個 clock 就輸出。

DRAM Access 的 sequence 是這樣:

RAS -- CAS -- CMD -- Data Ready

  • RAS-- CAS 間需要的 clock : tRCD
  • CAS -- CMD 間需要的 clock : CL
  • 下完 PreCharge Command 後,接受下一個command需要的時間 : tRP
ODT - On Deivice Termination
就是把終端電阻放在chip 里,不是 lay在板子上。

SDRAM, DDR, and DDRII 示意圖

這一篇 有很好的圖示,說明 SDRAM, DDR, DDRII 的 clock 差異

因為直接連圖不好意思,所以說明一下大概的原理:

假設 RAM Cell clock 都是 100MHz...
  • SDRAM 的 data 輸出和 data clock 的 rising edge 同步,所以也是 100MHz,因為一次一筆,所以不用 buffer 就直接輸出。
  • DDR 的 data 輸出和 data clock 的 rising edge, falling edge 都同步,所以一樣用 100MHz,但是因為一個edge 只能 output 一筆,所以內部要先 buffer 一份
  • DDR II 把輸出clock 增加一倍,而且也是 rising/falling edge 都輸出,所以內部要 buffer 3 份 data
... 這樣說起來有點奇怪,還是直接看圖好了..
IMGP1396
本來以為內部buffer 的 data 用來解釋 CL (data - to CMD delay) ,但是好像不是喔。
內部 buffer 只需要 delay 待會 才要的 data,第一筆 data 還是可以直接 output 出去,不需要 delay 的喔。

6.09.2010

ISDBT Error Correction Code

ISDBT 信號使用 Reed Solomoon 作 Error Correction Code。

有時候,為了要能測試出 RF 接收的特性,必須把接收端的 Reed Solomoon Correction 關閉。

6.04.2010

CPU 與週邊 的速度

CPU 跑 600,週邊 IO 的 clock 是 60。
所以當 CPU 對 GPIO register 寫資料時,是同步在 60MHz...


ldr r0, =GPIO1_PAD_EN
mov r1, #0x00100000 ; pin 20
str r1,[r0]
ldr r0, =GPIO1_CTRL20
mov r1,#0x120
mov r2,#0x160
1
str r1,[r0]
nop
str r2,[r0]
nop
b %b1

這一段 code,有沒有加 nop 輸出的方波都是 10MHz。
但是把 nop 改為

str r1,[r0]
str r1,[r0]
str r2,[r0]
str r2,[r0]
b %b1

這樣改完,輸出方波變成 5MHz。


也就是說..如果一直 polling 週邊得的話,就等於是用 60MHz 在跑....

2.05.2010

ISDB-T TRP file content info

日本 ISDB-T (13 seg) 的 streamming file : *.trp。

由 property 來看:
  • Video : Mpeg4 Video (H264) 320x172 , 14.99fps
  • Audio : AAC 48000Hz sterro 37Kbps

可以用 K lite Codec Pack 新版來看。

* 最新的版本還可以看到:

General
Complete name : G:\log.trp
Format : MPEG-TS
Format profile : No PAT/PMT
File size : 17.8 MiB

Video
ID : 1024 (0x400)
Format : AVC
Format/Info : Advanced Video Codec
Format profile : Baseline@L1.2
Format settings, CABAC : No
Format settings, ReFrames : 1 frame
Width : 320 pixels
Height : 180 pixels
Display aspect ratio : 16:9
Frame rate : 29.970 fps
Resolution : 8 bits
Colorimetry : 4:2:0
Scan type : Progressive

Audio
ID : 1280 (0x500)
Format : MPEG Audio
Video delay : -899ms

再詳細用 Play -- Filter --Audio Filte -- Proerties -- [IN]log.trp/Audio 看:

Filter : Audio Switcher - CLSID : {18C16B08-6497-420E-AD14-22D21C2CEAB7}

- Connected to:

CLSID: {0F40E1E5-4F79-4988-B1A9-CC98794E6B55}
Filter: ffdshow Audio Decoder
Pin: Out

- Connection media type:

Audio: PCM 48000Hz stereo 1536kbps

AM_MEDIA_TYPE:
majortype: MEDIATYPE_Audio {73647561-0000-0010-8000-00AA00389B71}
subtype: MEDIASUBTYPE_PCM {00000001-0000-0010-8000-00AA00389B71}
formattype: FORMAT_WaveFormatEx {05589F81-C356-11CE-BF01-00AA0055595A}
bFixedSizeSamples: 1
bTemporalCompression: 0
lSampleSize: 1
cbFormat: 18

WAVEFORMATEX:
wFormatTag: 0x0001
nChannels: 2
nSamplesPerSec: 48000
nAvgBytesPerSec: 192000
nBlockAlign: 4
wBitsPerSample: 16
cbSize: 0 (extra bytes)

pbFormat:
0000: 01 00 02 00 80 bb 00 00 00 ee 02 00 04 00 10 00 ....€.........
0010: 00 00 ..



用 一樣的 MPC MPEG Filter 來看
[IN] input:

Filter : MPC - Mpeg Splitter (Gabest) - CLSID : {DC257063-045F-4BE2-BD5B-E12279C464F0}

- Connected to:

CLSID: {E436EBB5-524F-11CE-9F53-0020AF0BA770}
Filter: G:\log.trp
Pin: Output

- Connection media type:

Unknown

AM_MEDIA_TYPE:
majortype: MEDIATYPE_Stream {E436EB83-524F-11CE-9F53-0020AF0BA770}
subtype: MEDIASUBTYPE_MPEG2_TRANSPORT {E06D8023-DB46-11CF-B4D1-00805F6CBBEA}
formattype: TIME_FORMAT_NONE {00000000-0000-0000-0000-000000000000}
bFixedSizeSamples: 1
bTemporalCompression: 0
lSampleSize: 1
cbFormat: 0

[OUT] Video

Filter : MPC - Mpeg Splitter (Gabest) - CLSID : {DC257063-045F-4BE2-BD5B-E12279C464F0}

- Connected to:

CLSID: {04FE9017-F873-410E-871E-AB91661A4EF7}
Filter: ffdshow Video Decoder
Pin: In

- Connection media type:

Video: MPEG4 Video (H264) 320x192 14.99fps

AM_MEDIA_TYPE:
majortype: MEDIATYPE_Video {73646976-0000-0010-8000-00AA00389B71}
subtype: Unknown GUID Name {31435641-0000-0010-8000-00AA00389B71}
formattype: FORMAT_MPEG2_VIDEO {E06D80E3-DB46-11CF-B4D1-00805F6CBBEA}
bFixedSizeSamples: 1
bTemporalCompression: 0
lSampleSize: 1
cbFormat: 159

VIDEOINFOHEADER:
rcSource: (0,0)-(0,0)
rcTarget: (0,0)-(0,0)
dwBitRate: 0
dwBitErrorRate: 0
AvgTimePerFrame: 667333

VIDEOINFOHEADER2:
dwInterlaceFlags: 0x00000000
dwCopyProtectFlags: 0x00000000
dwPictAspectRatioX: 320
dwPictAspectRatioY: 192
dwControlFlags: 0x00000000
dwReserved2: 0x00000000

MPEG2VIDEOINFO:
dwStartTimeCode: 0
cbSequenceHeader: 27
dwProfile: 0x00000042
dwLevel: 0x0000000c
dwFlags: 0x00000004

BITMAPINFOHEADER:
biSize: 40
biWidth: 320
biHeight: 192
biPlanes: 0
biBitCount: 0
biCompression: AVC1
biSizeImage: 0
biXPelsPerMeter: 0
biYPelsPerMeter: 0
biClrUsed: 0
biClrImportant: 0

pbFormat:
0000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
0010: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
0020: 00 00 00 00 00 00 00 00 c5 2e 0a 00 00 00 00 00 ...............
0030: 00 00 00 00 00 00 00 00 40 01 00 00 c0 00 00 00 ........@......
0040: 00 00 00 00 00 00 00 00 28 00 00 00 40 01 00 00 ........(...@...
0050: c0 00 00 00 00 00 00 00 41 56 43 31 00 00 00 00 .......AVC1....
0060: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
0070: 00 00 00 00 1b 00 00 00 42 00 00 00 0c 00 00 00 ........B.......
0080: 04 00 00 00|00 13 67 42 e0 0c b6 81 41 9f 9e 10 ......gB.A.
0090: 00 00 3e 90 00 07 53 08 40 00 04 68 ce 3c 80 ..>..S.@..h<€ - Enumerated media type 0: Set as the current media type


以上的 demuxer 是用 Gabest 的 MPEG Splitter。
這個是 open source project, Wiki : Media Player Classic

相關的Link

2.01.2010

pid and contunuity code in Transport Stream

雖然 Wiki 上寫的 pid 是在 high byte,continuity code 也是在 high byte。
但是實際上做起來:
byte 0 : sync 0x47
byte 1 : pid high and xxx bit
byte 2 : pid low and
byte 3 : continuity code and xxx

pid = ((byte1 << 8) | byte2) & 0x1FFF
cnt = byte3 % 0x0F

11.25.2009

SD card cannot be identified,

SD card 有一些不能 idenfy。
進入發現是 identification error.

trace initialize procedure:

* CMD0
* CMD8
* ACMD41 - repeat,
* Ready

在 ACMD41 時,一直response not ready。
因為是有 response,不是 timeout,所以 hardware trace layout 應該是OK的。

只有猜是因為 ACMD41 command 後,card要作 voltage switch,猜測是 power 的問題,所以請 hardware 在 SDcard socket 端 power 加上電容,就 OK了。


這個有關 SD card inititlize 的 討論:
http://www.avrfreaks.net/index.php?name=PNphpBB2&file=viewtopic&p=620292

這一篇說得很清楚,附圖,和 SD spec, 和 procedure
http://blog.chinaunix.net/u1/58780/showart.php?id=673609

這一篇講 ACMD41的動作
http://hi.baidu.com/lizhenqian79/blog/item/620420a10bc7ce88471064bb.html

這一篇也有說ACMD41:
http://www.laogu.com/laogubbs/see_30547.htm

acmd41的返回值中,OCR的bit31为0表明卡此时处于busy状态,*请隔50ms后重新发cmd55,acmd41命令*,重复**部分直到返回的OCR的bit31为1为止.请仔细阅读spec.

這一篇有 SD card spec 的 link
http://hi.baidu.com/hao01222/blog/item/f69a48554c53dec7b745ae9e.html

7.23.2009

SD card, Command and Response

SD Card 的 Command 依照SD Card 的"回應"有很多"類型"。
回應就是"Response",一樣利用 SD card interface 的 "CMD" pin 來傳送。
= 所以 CMD line 是雙向 line

host 從CMD 送出command 後,讓 CMD維持 high-impendance,SD card 就可以拉動 CMD line,做出回應。
  • Spec 4.12 Timings 有詳細說明bus 的 timing.
Spec 上用 R1, R2, R3, R6 來區分Response 的內容。
每個 Response 的 data 數量不一樣。

每個Command都有規定的 Response 。

像 CMD2, CMD10 就要回應 R2。

6.15.2009

M2M communicatin - by Camera and Display

machine to machine 2 way communication - in visual.

就是利用 display 和 camera 來溝通。
互相用 camera 拍攝對方的 display,
display 上顯示傳遞到對方的資料。對方就可以經由 camera "讀取" 到。

這個在目前"有 video camera"功能的手機上可以實做。
只需要software 的 effort。不需要而外增加 hardware。

顯示的內榮決定傳輸頻寬,可以利用 2D bar code或是單純的 black-white screen。

5.13.2009

openmoko - flash kernel and rootfs

安裝 usb 連線軟體: dfu-util。
Debian 直接用 apt 安裝就可以。

通常需要
  1. kernel - uImage
  2. rootfs
bootloader 不一定要重燒

rootfs 通常是有 jffs2 在檔名中,kernel 通常就有 uImage 在檔名中。

開機進入 nor boot (nand boot) ? 就可以接上 usb ,和 dfu-util 溝通。

按著hold key 開機,進入nor boot 畫面,插上 usb。dmesg..

[786627.436013] usb 2-3: new full speed USB device using ohci_hcd and address 2
[786627.654996] usb 2-3: configuration #1 chosen from 2 choices
[786627.677190] usb 2-3: New USB device found, idVendor=1d50, idProduct=5119
[786627.677198] usb 2-3: New USB device strings: Mfr=1, Product=2, SerialNumber=3
[786627.677202] usb 2-3: Product: Neo1973 Bootloader U-Boot 1.3.2-moko12
[786627.677205] usb 2-3: Manufacturer: OpenMoko, Inc
[786627.677207] usb 2-3: SerialNumber: 0000000
[786628.281641] cdc_acm: This device cannot do calls on its own. It is no modem.
[786628.281641] cdc_acm 2-3:1.0: ttyACM0: USB ACM device
[786628.288104] usbcore: registered new interface driver cdc_acm
[786628.288112] cdc_acm: v0.26:USB Abstract Control Model driver for USB modems and ISDN adapters
所以應該是有偵測到...

燒錄過程要注意的是...沒有操作30 sec 後,機器會自動 power off。
所以看到螢幕黑掉,就要重新 power on.

rootfs download 比較久。

重開機很花時間,約需要 2 min,約 1min 後才會出現splash screen.然後滅掉..

4.27.2009

用錢可以解決的事: 感度與範圍

比較敏感的 Sensor 比較容易飽和 -- 也就是說,量測尺範圍不夠。
量測範圍大的 Sensor,就比較遲鈍 -- 因為刻度變大了。

那要怎麼做出量測範圍大,靈敏度又好的 Sensor 呢?


就裝兩個 Sensor 就好了呀,小Sensor 飽和了就看大Sensor 的值....

3.26.2009

SD Password Protect Command Sequence

set password :
  • CMD7 : Select Card
  • CMD16 : Set Block Length
  • CMD42 with Block Data
reset password :
  • CMD7 : Select Card
  • CMD16 : Set Block Length
  • CMD42 with BlockData
Lock
  • CMD7 : Select Card
  • CMD16: Set Block Length
  • CMD42 with BlockData
Unlock
  • CMD7 : Select Card
  • CMD16 : Set Block Length
  • CMD42 with BlockData
Erase
  • CMD7 : Select Card
  • CMD16 : Set Block Length (to 1 byte only)
  • CMD42 with BlockData



Result of CMD42

3.20.2009

sequence on CMD42

SD card 的溝通也是要靠 Address 的, (RCA : Relative Card Address),但是 address 0x00 是 broadcast address,所有的 card 都要收。

CMD7 (SELECT_DESELECT) 是用來 toggle SD card 進入/退出 Transfer Mode 。

Card Lock/Unlock Command 類似 Block Write Command。
其中 transfer 的 data 部份,就是 password, setting... etc。
所以 CMD42 的 Response 也跟 Block Write Command 的 Result 一樣 ?


Card Identification.. 然後 Configuration...然後進 Transfer state..

procedure :

先作 setting password


Linux 真是偉大,在某一版看到 implement,但是好像沒有 接受
http://groups.google.com.tw/group/linux.kernel/browse_thread/thread/7ddefc84c21ede84/d47cd82a306fd9d8?q=mmc_lock_unlock#d47cd82a306fd9d8


int mmc_lock_unlock(struct mmc_card *card, struct key *key, int mode)
+{
+ struct mmc_request mrq;
+ struct mmc_command cmd;
+ struct mmc_data data;
+ struct scatterlist sg;
+ struct mmc_key_payload *mpayload;
+ unsigned long erase_timeout;
+ int err, data_size;
+ u8 *data_buf;
+
+ mpayload = NULL;
+ data_size = 1;
+ if (mode != MMC_LOCK_MODE_ERASE) {
+ mpayload = rcu_dereference(key->payload.data);
+ data_size = 2 + mpayload->datalen;
+ }
+
+ data_buf = kmalloc(data_size, GFP_KERNEL);
+ if (!data_buf)
+ return -ENOMEM;
+ memset(data_buf, 0, data_size);
+
+ data_buf[0] = mode;
+ if (mode != MMC_LOCK_MODE_ERASE) {
+ data_buf[1] = mpayload->datalen;
+ memcpy(data_buf + 2, mpayload->data, mpayload->datalen);
+ }
+
+ memset(&cmd, 0, sizeof(struct mmc_command));
+
+ cmd.opcode = MMC_SET_BLOCKLEN;
+ cmd.arg = data_size;
+ cmd.flags = MMC_RSP_R1 | MMC_CMD_AC;
+ err = mmc_wait_for_cmd(card->host, &cmd, CMD_RETRIES);
+ if (err != MMC_ERR_NONE)
+ goto out;
+
+ memset(&cmd, 0, sizeof(struct mmc_command));
+
+ cmd.opcode = MMC_LOCK_UNLOCK;
+ cmd.arg = 0;
+ cmd.flags = MMC_RSP_R1B | MMC_CMD_ADTC;
+
+ memset(&data, 0, sizeof(struct mmc_data));
+
+ mmc_set_data_timeout(&data, card, 1);
+
+ data.blksz = data_size;
+ data.blocks = 1;
+ data.flags = MMC_DATA_WRITE;
+ data.sg = &sg;
+ data.sg_len = 1;
+
+ memset(&mrq, 0, sizeof(struct mmc_request));
+
+ mrq.cmd = &cmd;
+ mrq.data = &data;
+
+ sg_init_one(&sg, data_buf, data_size);
+ err = mmc_wait_for_req(card->host, &mrq);
+ if (err != MMC_ERR_NONE)
+ goto out;
+
+ memset(&cmd, 0, sizeof(struct mmc_command));
+
+ cmd.opcode = MMC_SEND_STATUS;
+ cmd.arg = card->rca << 16;
+ cmd.flags = MMC_RSP_R1 | MMC_CMD_AC;
+
+ /* set timeout for forced erase operation to 3 min. (see MMC spec) */
+ erase_timeout = jiffies + 180 * HZ;
+ do {
+ /* we cannot use "retries" here because the
+ * R1_LOCK_UNLOCK_FAILED bit is cleared by subsequent reads to
+ * the status register, hiding the error condition */
+ err = mmc_wait_for_cmd(card->host, &cmd, 0);
+ if (err != MMC_ERR_NONE)
+ break;
+ /* the other modes don't need timeout checking */
+ if (mode != MMC_LOCK_MODE_ERASE)
+ continue;
+ if (time_after(jiffies, erase_timeout)) {
+ dev_dbg(&card->dev, "forced erase timed out\n");
+ err = MMC_ERR_TIMEOUT;
+ break;
+ }
+ } while (!(cmd.resp[0] & R1_READY_FOR_DATA));
+ if (cmd.resp[0] & R1_LOCK_UNLOCK_FAILED) {
+ dev_dbg(&card->dev, "LOCK_UNLOCK operation failed\n");
+ err = MMC_ERR_FAILED;
+ }
+
+ if (cmd.resp[0] & R1_CARD_IS_LOCKED)
+ mmc_card_set_locked(card);
+ else
+ mmc_card_clear_locked(card);
+
+out:
+ kfree(data_buf);
+
+ return err;
+}


裡面有完整的CMD42 的 command sequence..
但是這段 code 在linux kernel 中找不到...

這一個Thread 有相關的討論..

Something about SD

High Speed SD card 的 clock 增加一倍(up to 50MHz),使用 4 bit data line,所以 interface bandwidth 是 25MB/s。

但是 Class 6 的 SD card,速度只有到 6MB/s。
25 -- 6, 哇,Overhead 好大呀!
SD Card power on 時,只使用 D0 傳輸,適當的 initialize (SET_BUS_WIDTH)後,就可以選擇使用 D0 ,或是 D0~D4傳輸。
即使在 D0 (1 line) 傳輸狀態,D1~D4也不可以挪作他用,要保持 tri-state。

問題:只使用 D0 傳輸時,就是 SPI Mode 嗎?
好像不是,SPI 還會用 D3 當 CS用,拿CMD當Di (datain)用。
SD interface 是序列傳輸的 interface,有專屬的雙向 CMD, Data line。
CMD 只有一條線,Data 可以有 1 ~ 4 條。
我以前以為 data (0~3) 是共用的,然後用 CMD 的 high/low 來代表目前 data送的是 command 還是 data.
CMD line 用來傳輸 host 給 SD card 的 command ,同用來傳輸 SD card 給 host 的 response。

Command, Response 都是由單一條 CMD line 傳送的,所以 Command packet,Response Packet 的 size 都不必是 8 的倍數。(?)
但是好像實際都是8 的倍數呀。
SD card 操作的形式都是 由 Command 來操作。
有些 Command 有 Response,Card 會回送 Response回來,
有些 Command 會 引發 Data 的操作,例如 Read Block command,SD card 收到後,就會將 傳送 Data 回 Host,同時回應 Response 回 host。

Write Command 也會引發 Data傳輸,
Host 送給 SD card,SD card 收到後,以D0 作為 busy 信號,
host 送完 Data 要 check D0 (busy) 狀態,等 SD card 動作結束,放掉 D0 後,才可以進行下一個 command/data 操作。