PDA

View Full Version : giao tiep voi sd card


trachao
23-05-2009, 10:51 PM
Minh dang lam giao tiep voi sd card de doc du lieu file mp3 trong the nho' de phat ra am thanh.co' ai biet lam,hoac co' tai lieu ve mon' nay` ko chi giup minh voi'.

lcd_amptech
24-05-2009, 10:56 AM
@trachao
Bạn xem ở đây nè, code viet cho atmega8. Sơ đồ kết nối chân như trong định nghĩa trong code nên mình không post sơ đồ mạch lên.
Tài liệu thì có đầy trên mạng, bạn lên google kiếm.
http://my.opera.com/lcdamptech/blog/truy-cap-the-nho-sd-bang-atmega8

tahi
20-11-2009, 03:52 PM
em đang dính bệnh rất lạ , gửi cmd0 để reset thẻ thì ok, cmd1 để chuyển sang trạng thái data transfer mode cũng ok, nhưng đến lúc gửi lệnh đọc single block (cụ thể là sector 0)thì luôn response về mã lỗi 0x20, là address error. Gửi lệnh đọc các sector khác cũng bị tình trạng tương tự. Không biết bác nào bị bệnh này chưa, cho em hỏi với...

bien_van_khat
20-11-2009, 05:35 PM
code bạn tự viết hay dùng thư viện. Thư viện và code mẫu cho SD card rất nhiều trên Net, bạn có thể tham khảo thư viện MDD của microchip.

http://www.microchip.com/stellent/idcplg?IdcService=SS_GET_PAGE&nodeId=2680&dDocName=en537044

tahi
23-11-2009, 12:01 PM
code tham khảo của bác falleaf (dùng cho chú dsPIC30F4013).Cụ thể là trong thread này:
http://www.picvietnam.com/forum/showthread.php?t=1663


#define BLOCK_SIZE 512
unsigned char SD_ReadBlock(unsigned long addr, unsigned char *buf)
{
unsigned int i;
unsigned char status;
unsigned char CMD17_READ_SINGLE_BLOCK[] = {17,0x00,0x00,0x0,0x00,0xFF};
CMD17_READ_SINGLE_BLOCK[1] = ((addr & 0xFF000000) >> 24);
CMD17_READ_SINGLE_BLOCK[2] = ((addr & 0x00FF0000) >> 16);
CMD17_READ_SINGLE_BLOCK[3] = ((addr & 0x0000FF00) >> 8);
CMD17_READ_SINGLE_BLOCK[4] = ((addr & 0x000000FF));
SD_Enable();
i=0;
do
{
status = SD_WriteCommand(CMD17_READ_SINGLE_BLOCK);
send_hex(status,"CMD17:");
if(i++ > 50)
{
putsUART1((unsigned int*)"Read sector failed\n\r");
break;
}
}
while(status != 0x00);
//Waif
Delay_Us(150);
// Send the read command
if(status != 0)
{
// ABORT: invalid response for read single command
return 1;
}
// Now wait for the "Start Block" token (0xFE)
// (see SanDisk SD Card Product Manual v1.9 section 5.2.4. Data Tokens)
do
{
status = SPIRead();
send_hex(status,"waitf token:");
} while(status != 0xFE);
// Read off all the bytes in the block
for(i = 0; i < BLOCK_SIZE; ++i)
{
status = SPIRead();
*buf = status;
buf++;
}
// Read CRC bytes
status = SPIRead();
status = SPIRead();
SD_Disable();
// Following a read transaction, the SD Card needs 8 clocks after the end
// bit of the last data block to finish up its work.
// (from SanDisk SD Card Product Manual v1.9 section 5.1.8)
SPIWrite(0xFF);
return 0;
}

trong main
status = SD_ReadBlock(0, buffer);
Hàm SD_WriteCommand vẫn giữ nguyên. Hàm read đã có write dummy data (write FF)
Còn lệnh nào có response R1 mà test đuợc không nhỉ. Tốc độ giao tiếp phụ thuộc thế nào với các loại thẻ khác nhau.
Khởi tạo thẻ nhớ với tốc độ 150k, gửi lệnh cmd0 để reset thẻ, R1 = 0x01 (ok..đã in idle state). Sau đó gửi lệnh cmd1 để vào data transfer mode. Chuyển tốc độ lên 1.25MHz. R1 = 0x00 (đã vào mode transfer)
Sau đó gửi lệnh CMD17 để đọc single block thì toàn response 0x20
Ở đây em chỉ đọc 512 byte bắt đầu từ địa chỉ 0x00, không biết đó có phải sector 0 hay ko. (em đã quét cả dải địa chỉ mà vẫn báo về như thế...)
CRC có chú ý gì ko?

bien_van_khat
23-11-2009, 02:00 PM
code tham khảo của bác falleaf (dùng cho chú dsPIC30F4013).Cụ thể là trong thread này:
http://www.picvietnam.com/forum/showthread.php?t=1663


#define BLOCK_SIZE 512
unsigned char SD_ReadBlock(unsigned long addr, unsigned char *buf)
{
unsigned int i;
unsigned char status;
unsigned char CMD17_READ_SINGLE_BLOCK[] = {17,0x00,0x00,0x0,0x00,0xFF};
CMD17_READ_SINGLE_BLOCK[1] = ((addr & 0xFF000000) >> 24);
CMD17_READ_SINGLE_BLOCK[2] = ((addr & 0x00FF0000) >> 16);
CMD17_READ_SINGLE_BLOCK[3] = ((addr & 0x0000FF00) >> 8);
CMD17_READ_SINGLE_BLOCK[4] = ((addr & 0x000000FF));
SD_Enable();
i=0;
do
{
status = SD_WriteCommand(CMD17_READ_SINGLE_BLOCK);
send_hex(status,"CMD17:");
if(i++ > 50)
{
putsUART1((unsigned int*)"Read sector failed\n\r");
break;
}
}
while(status != 0x00);
//Waif
Delay_Us(150);
// Send the read command
if(status != 0)
{
// ABORT: invalid response for read single command
return 1;
}
// Now wait for the "Start Block" token (0xFE)
// (see SanDisk SD Card Product Manual v1.9 section 5.2.4. Data Tokens)
do
{
status = SPIRead();
send_hex(status,"waitf token:");
} while(status != 0xFE);
// Read off all the bytes in the block
for(i = 0; i < BLOCK_SIZE; ++i)
{
status = SPIRead();
*buf = status;
buf++;
}
// Read CRC bytes
status = SPIRead();
status = SPIRead();
SD_Disable();
// Following a read transaction, the SD Card needs 8 clocks after the end
// bit of the last data block to finish up its work.
// (from SanDisk SD Card Product Manual v1.9 section 5.1.8)
SPIWrite(0xFF);
return 0;
}

trong main
status = SD_ReadBlock(0, buffer);
Hàm SD_WriteCommand vẫn giữ nguyên. Hàm read đã có write dummy data (write FF)
Còn lệnh nào có response R1 mà test đuợc không nhỉ. Tốc độ giao tiếp phụ thuộc thế nào với các loại thẻ khác nhau.
Khởi tạo thẻ nhớ với tốc độ 150k, gửi lệnh cmd0 để reset thẻ, R1 = 0x01 (ok..đã in idle state). Sau đó gửi lệnh cmd1 để vào data transfer mode. Chuyển tốc độ lên 1.25MHz. R1 = 0x00 (đã vào mode transfer)
Sau đó gửi lệnh CMD17 để đọc single block thì toàn response 0x20
Ở đây em chỉ đọc 512 byte bắt đầu từ địa chỉ 0x00, không biết đó có phải sector 0 hay ko. (em đã quét cả dải địa chỉ mà vẫn báo về như thế...)
CRC có chú ý gì ko?

Bạn sử dụng trình dịch gì?

tahi
24-11-2009, 05:22 PM
MPLAB IDE 8.36 với C30 version 3.20

Loại thẻ nào có thể ăn với lệnh CMD55+ACMD41...Em gửi lệnh này sau khi đã reset thẻ thì nó báo về
R1 = 0x05 (illegal command + in idle state)

bien_van_khat
24-11-2009, 08:37 PM
MPLAB IDE 8.36 với C30 version 3.20

Loại thẻ nào có thể ăn với lệnh CMD55+ACMD41...Em gửi lệnh này sau khi đã reset thẻ thì nó báo về
R1 = 0x05 (illegal command + in idle state)

Chỉ có SD card mới trả lời CMD55. MMC ko trả lời CMD55.
Bạn phải chờ tới khi card trả lời CMD55 hoặc timeout rồi mới gửi ACMD41

Bạn thử gửi ACMD41 với các tham số

unsigned char ACMD41_SD_SEND_OP_COND[] = {41,0x40,0x00,0x00,0x00,0xFF};


Đoạn code bạn sử dụng vốn chỉ là đoạn code mẫu, để tránh mất thời gian debug vô ích mình khuyên bạn nên dùng MDD.

tahi
26-11-2009, 10:04 AM
// Send CMD55, required to precede all "application specific" commands
unsigned char CMD55_APP_CMD[] = {55,0x00,0x00,0x00,0x00,0x00};
status = SD_WriteCommand(CMD55_APP_CMD); // Do not check response here
send_hex(status,"CMD55:");

// Send the ACMD41 command to initialize SD Card mode (not supported by MMC cards)
i = 0;
unsigned char ACMD41_SD_SEND_OP_COND[] = {41,0x40,0x00,0x00,0x00,0xFF};
do
{
status = SD_WriteCommand(ACMD41_SD_SEND_OP_COND);
// Might return 0x04 for Invalid Command if MMC card is connected
send_hex(status,"ACMD41:");
if(i++ > 50)
{
return 3;
}
} while( (status & R1_IN_IDLE_STATE) != 0 );


Gửi CMD55 trả về 0x01 , in idle state
Gửi ACMD41 trả về 0x05, in idle state and illegal command
có phải lệnh CMD1 và CMD55+ACMD41 là tương đương nhau ?

Bản MDD 1.2.1 down về, ko thấy support dòng dsPIC33, cũng ko thấy chỗ nào gán thanh ghi cho dspic33, mặc dù tiêu đề ghi là có hỗ trợ. Đương nhiên là có thể sửa từ PIC24,

Hay là phần cứng có vấn đề gì (e chỉ nối MOSI, MISO, SS, CLK). Thằng này có tính năng remappable, nhưng em chỉ remap cho thằng MOSI, MISO, CLK, còn SS thì define cho 1 pin khác.

bien_van_khat
26-11-2009, 10:56 AM
// Send CMD55, required to precede all "application specific" commands
unsigned char CMD55_APP_CMD[] = {55,0x00,0x00,0x00,0x00,0x00};
status = SD_WriteCommand(CMD55_APP_CMD); // Do not check response here
send_hex(status,"CMD55:");

// Send the ACMD41 command to initialize SD Card mode (not supported by MMC cards)
i = 0;
unsigned char ACMD41_SD_SEND_OP_COND[] = {41,0x40,0x00,0x00,0x00,0xFF};
do
{
status = SD_WriteCommand(ACMD41_SD_SEND_OP_COND);
// Might return 0x04 for Invalid Command if MMC card is connected
send_hex(status,"ACMD41:");
if(i++ > 50)
{
return 3;
}
} while( (status & R1_IN_IDLE_STATE) != 0 );


Gửi CMD55 trả về 0x01 , in idle state

=> card bạn dùng là SD card

Gửi ACMD41 trả về 0x05, in idle state and illegal command

Đáng lẽ card phải trả lời 0x01, sau đó bạn tiếp tục gửi CMD55 + ACMD41 cho tới khi card trả lời 0x00

có phải lệnh CMD1 và CMD55+ACMD41 là tương đương nhau ?

CMD1 là chuyển từ IDLE sang hoạt động và dùng cho thẻ SD/MMC
CMD55+ACMD41 để chuyển từ IDLE sang hoạt động và chỉ dùng cho thẻ SD

Tuy nhiên vì thẻ SD tương thích với thẻ MMC nên mình nghĩ bạn có thể bỏ qua CMD55+ACMD41 và gửi lệnh SET_BLOCK_LEN = 512 (command 16), sau đó kết thúc phần init bằng 8 lần ghi 0xff.

Đoạn code mẫu của anh Hiệp thiếu lệnh SET_BLOCK_LEN, có lẽ đây là lý do làm bạn nhận về mã lỗi địa chỉ sai.


Hay là phần cứng có vấn đề gì (e chỉ nối MOSI, MISO, SS, CLK). Thằng này có tính năng remappable, nhưng em chỉ remap cho thằng MOSI, MISO, CLK, còn SS thì define cho 1 pin khác.
Bạn ko nên dùng chân SS của SPI, dùng 1 chân IO bình thường để nối tới chân CS của card (hình như bạn đang làm như vậy, bạn nói chưa rõ).

Khi khởi động, card ở chế độ SD, do đó chân SDO của card là opendrain, bạn cần 1 con điện trở pull-up ở chân này, từ 10k-50k.

tahi
30-11-2009, 02:34 PM
Cảm ơn bác đã giúp. Đoạn gửi ACMD41 đúng là em hơi sơ xuất, em chỉ loop mỗi gửi ACMD41, đáng nhẽ phải loop cả CMD55 và ACMD41

Bạn ko nên dùng chân SS của SPI, dùng 1 chân IO bình thường để nối tới chân CS của card (hình như bạn đang làm như vậy, bạn nói chưa rõ).

Em gán cho 1 thằng I/O bình thường

Khi khởi động, card ở chế độ SD, do đó chân SDO của card là opendrain, bạn cần 1 con điện trở pull-up ở chân này, từ 10k-50k.

Em ko có con trở pull-up nào. Đồng thời dính hiến tượng, cắm thẻ thì reset (sụt áp)

Khi send 6 byte lệnh, có delay giữa các byte hay ko hay là gửi liên tiếp,

unsigned char SD_WriteCommand(unsigned char* cmd)
{
unsigned int i;
unsigned char response;
unsigned char savedSD_CS = SD_CS;
// SD Card Command Format
// (from Section 5.2.1 of SanDisk SD Card Product Manual v1.9).
// Frame 7 = 0
// Frame 6 = 1
// Command (6 bits)
// Address (32 bits)
// Frame 0 = 1

// Set the framing bits correctly (never change)
cmd[0] |= (1<<6);
cmd[0] &= ~(1<<7);
cmd[5] |= (1<<0);
// Send the 6 byte command
SD_Enable();
for(i = 0; i < 6; ++i)
{
SPIWrite(*cmd);
Delay_Us(100); //để 10 thì ăn, còn để 0 hoặc 100 là response về FF
cmd++;
}
// Wait for the response
i = 0;
do
{
response = SPIRead();
if(i > 500) //If this value = 100, will recieved 0xFF with cmd17
{
break;
}
i++;
} while(response == 0xFF);

SD_Disable();

// Following any command, the SD Card needs 8 clocks to finish up its work.
// (from SanDisk SD Card Product Manual v1.9 section 5.1.8)
SPIWrite(0xFF);
SD_CS = savedSD_CS;
return(response);
}

bien_van_khat
30-11-2009, 03:28 PM
Đồng thời dính hiến tượng, cắm thẻ thì reset (sụt áp)

Bạn phải kiểm tra chắc chắn là phần cứng đúng. Vì thẻ ngốn dòng nhiều nhất khi ghi, nhưng cũng không quá 100mA

Khi send 6 byte lệnh, có delay giữa các byte hay ko hay là gửi liên tiếp,

Gửi liên tiếp ko delay, nhưng lần ghi sau cùng phải chờ tới khi module SPI xuất hết dữ liệu ra, tức là cờ ngắt bật thì mới được đưa chân CS về 1. Vì sau khi ghi vào thanh ghi SPIxBUF, cần tốn 1 thời gian tùy thuộc vào tốc độ baud thì dữ liệu mới ghi ra bus hết. Nếu bạn đưa chân CS về 1 ngay sau khi ghi SPIxBUF thì byte cuối cùng thẻ sẽ không nhận!


Và chú ý bạn phải gửi lệnh SET_BLOCK_LEN, đây là lệnh bắt buộc trong quá trình khởi tạo thẻ

Bạn muốn tự viết driver thẻ?

tahi
30-11-2009, 09:25 PM
Và chú ý bạn phải gửi lệnh SET_BLOCK_LEN, đây là lệnh bắt buộc trong quá trình khởi tạo thẻ

Em đọc tài liệu thấy bảo là, block length =512 là default mà .

Bạn muốn tự viết driver thẻ?

Đương nhiên là không rồi, e chỉ viết các hàm init cơ bản để test thôi. Em đã down mấy cái example về sử dụng MDD của microchip ko thấy nó hỗ trợ cho dòng 33F...Có cái thì bọn nó viết lại gần hết SD-SPI.c, cũng chẳng theo gì MDD. Còn có mấy cái project cho 30F thì ok...Bác có cái template nào viết cho dòng 33F ko, post lên cho em tham khảo với.

bien_van_khat
30-11-2009, 11:23 PM
Em đọc tài liệu thấy bảo là, block length =512 là default mà .

Mình chưa kiểm tra kỹ vụ này.


Đương nhiên là không rồi, e chỉ viết các hàm init cơ bản để test thôi. Em đã down mấy cái example về sử dụng MDD của microchip ko thấy nó hỗ trợ cho dòng 33F...Có cái thì bọn nó viết lại gần hết SD-SPI.c, cũng chẳng theo gì MDD. Còn có mấy cái project cho 30F thì ok...Bác có cái template nào viết cho dòng 33F ko, post lên cho em tham khảo với.

port giữa pic24, PIC33 và PIC32 rất dễ, vì các thanh ghi ngoại vi 3 dòng này giống nhau.


Mình nghĩ bạn dùng PIC33FJxxGP8xx, nếu vậy có lẽ chỉ cần thay file header và điều chỉnh lại các chân remap của SPI là xong!

tahi
14-12-2009, 11:08 AM
Em đã đọc được single block, nhưng em chưa hiểu lắm. Khi format thẻ với định dạng khác nhau thì đọc MBR có giống nhau không ? (theo em là có nhưng thực tế là đọc lần nào cũng như lần nào)

Em soi lại cại MDD file system, trong khi đợi data token.. (của lệnh CMD17 sau khi response = 0 thì đợi data token..) không thấy bọn nó cho chân SD_CS = 0;

Không thấy bọn nó switch speed sau khi init thẻ xong.

bien_van_khat
14-12-2009, 12:13 PM
Em đã đọc được single block, nhưng em chưa hiểu lắm. Khi format thẻ với định dạng khác nhau thì đọc MBR có giống nhau không ? (theo em là có nhưng thực tế là đọc lần nào cũng như lần nào)


Định dạng Partition thay đổi thì boot record của partition đó thay đổi chứ Master Boot Record thì không có gì khác. Nếu thay đổi partition (kích thước, số lượng, active) thì MBR mới thay đổi.

tahi
15-12-2009, 10:59 AM
Sau khi đọc được MBR, em thấy trong 512 byte của nó có dòng "Invalid partition table , error loading operating system missing operating system" Dòng này bắt đầu từ địa chỉ 139 (hay 0x8B)
Đọc MBR chính là đọc sector 0 có phải không ạ ? Còn boot sector là của từng thằng partition ? Ý em muốn hỏi về 3 khái niệm MBR, boot sector và sector 0 của thằng SD card, hàm đọc sector em gán địa chỉ là 0 thì đọc đuợc cái gì trong 3 thằng đó
Do cái em đọc được nó không có những thông tin dưới đây, nên nó ko nhảy vào được cái if này, mặc dù đã format thẻ là FAT16

#ifdef USE_16BIT
if (ReadByte( dsk->buffer, BSI_FSTYPE ) == 'F' && \
ReadByte( dsk->buffer, BSI_FSTYPE + 1 ) == 'A' && \
ReadByte( dsk->buffer, BSI_FSTYPE + 2 ) == 'T' && \
ReadByte( dsk->buffer, BSI_FSTYPE + 3 ) == '1' && \
ReadByte( dsk->buffer, BSI_BOOTSIG) == 0x29)
#else
if (BSec->FAT.FAT_16.BootSec_FSType[0] == 'F' && \
BSec->FAT.FAT_16.BootSec_FSType[1] == 'A' && \
BSec->FAT.FAT_16.BootSec_FSType[2] == 'T' && \
BSec->FAT.FAT_16.BootSec_FSType[3] == '1' && \
BSec->FAT.FAT_16.BootSec_BootSig == 0x29)
#endif
{
dsk->firsts = 0;
dsk->type = FAT16;
}

bien_van_khat
15-12-2009, 11:25 AM
Sau khi đọc được MBR, em thấy trong 512 byte của nó có dòng "Invalid partition table , error loading operating system missing operating system" Dòng này bắt đầu từ địa chỉ 139 (hay 0x8B)
Đọc MBR chính là đọc sector 0 có phải không ạ ? Còn boot sector là của từng thằng partition ? Ý em muốn hỏi về 3 khái niệm MBR, boot sector và sector 0 của thằng SD card, hàm đọc sector em gán địa chỉ là 0 thì đọc đuợc cái gì trong 3 thằng đó
Do cái em đọc được nó không có những thông tin dưới đây, nên nó ko nhảy vào được cái if này, mặc dù đã format thẻ là FAT16

#ifdef USE_16BIT
if (ReadByte( dsk->buffer, BSI_FSTYPE ) == 'F' && \
ReadByte( dsk->buffer, BSI_FSTYPE + 1 ) == 'A' && \
ReadByte( dsk->buffer, BSI_FSTYPE + 2 ) == 'T' && \
ReadByte( dsk->buffer, BSI_FSTYPE + 3 ) == '1' && \
ReadByte( dsk->buffer, BSI_BOOTSIG) == 0x29)
#else
if (BSec->FAT.FAT_16.BootSec_FSType[0] == 'F' && \
BSec->FAT.FAT_16.BootSec_FSType[1] == 'A' && \
BSec->FAT.FAT_16.BootSec_FSType[2] == 'T' && \
BSec->FAT.FAT_16.BootSec_FSType[3] == '1' && \
BSec->FAT.FAT_16.BootSec_BootSig == 0x29)
#endif
{
dsk->firsts = 0;
dsk->type = FAT16;
}


MBR bao giờ cũng là sector 0 của ổ đĩa, sau khi hoàn tất POST, Bios sẽ đọc MBR của ổ đĩa được chọn để boot. Đoạn đầu của MBR là đoạn code để thực hiện kiểm tra xem phân vùng nào trong đĩa sẽ dùng để boot. Đoạn cuối của MBR sẽ có 1 struct mô tả trên đĩa có bao nhiêu phân vùng primary, kích thước, có active hay ko....

Nếu tìm thấy phân vùng active, nó sẽ load sector 0 của phân vùng đó, sector này gọi là Boot Sector hoặc Boot Record. Đoạn code trên BR sẽ làm nhiệm vụ load hệ điều hành trên phân vùng đó.

Tùy thuộc vào chương trình dùng để format, thẻ của bạn có thể có hoặc ko có MBR, nhưng luôn luôn có ít nhất 1 BR.

Nếu có MBR thì nó nằm ở sector 0 của thẻ, bạn phải tìm BR của các phân vùng primary dựa vào struct bắt đầu ở offset 446

Nếu ko có MBR thì sector 0 là BR của phân vùng duy nhất trên thẻ.

Mình nghĩ thẻ của bạn có MBR, bạn chỉ mới đọc sector 0 là MBR, còn phải lọc và tìm BR nữa.

tahi
16-12-2009, 09:57 AM
Cám ơn bác, em đã đọc được MBR. Em viết lại cho nó dễ hiểu hơn tý. Các bạn khác có thể tham khảo tài liệu AN1045 của microchip để hiểu sơ qua về MBR và cách dùng thư viện MDD

Với thằng thẻ có MBR, đầu tiên là đọc MBR (sector 0). Trong 512 Bytes của sector 0, thì từ byte thứ 446 là thông tin về partition. Người ta gọi là partition entry(với 512byte/sector thì chỉ có tối đa 4 partition ), mỗi thằng partion entry thì có 16 byte (ví dụ thằng partition entry 1 sẽ từ 446 đến 446 + 16). Trong 16 byte partition entry có thông tin về partition đó có được active ko, sector bắt đầu, sector kết thúc, số sector từ MBR đến địa chỉ bắt đầu của partition đó..=>đọc MBR rồi lọc lấy partition entry rồi nhảy đến boot sector của partition đó. Trong 512 bytes của boot sector sẽ có thông tin để nhảy vào root entry (nơi chưa thông tin về file cần đọc)

@bien_van_khat:
em có 2 cái sd card, 1 cái có MBR, thì init được và đọc được, còn cái không có MBR thì ko init được. Vậy làm thế nào để có MBR, không init được thì mình có đọc dữ liệu từ thẻ không (theo suy luận của em là có, nhưng trong code, có thủ tục khởi tạo, nó không khởi tạo vào mode tranfer thì nó cũng chẳng đọc được cái gì)

bien_van_khat
16-12-2009, 10:47 AM
em có 2 cái sd card, 1 cái có MBR, thì init được và đọc được, còn cái không có MBR thì ko init được. Vậy làm thế nào để có MBR, không init được thì mình có đọc dữ liệu từ thẻ không (theo suy luận của em là có, nhưng trong code, có thủ tục khởi tạo, nó không khởi tạo vào mode tranfer thì nó cũng chẳng đọc được cái gì)

Khởi tạo thành công thì bạn mới có thông tin về phân vùng, ví dụ vị trí bảng FAT, kích thước FAT, kích thước cluster, ..... Ko có thì sao mà đọc được dữ liệu

tahi
16-12-2009, 04:07 PM
Khởi tạo thành công thì bạn mới có thông tin về phân vùng, ví dụ vị trí bảng FAT, kích thước FAT, kích thước cluster, ..... Ko có thì sao mà đọc được dữ liệu
Thế thì những thẻ ko có MBR thì chịu không đọc đuợc à. Hay là ko đọc MBR nữa mà nhảy thẳng vào boot sector của partition...

Hiện tại code em mặc dù đọc file ok, nhưng rất củ chuối:
Quá trình khởi tạo thẻ của em như sau:

- Gửi CMD0 bằng cách điều khiển I/O thông thường..(Viết truyền nhận SPI thủ công, bằng cách dịch bít). Thấy trả về 0x01, thẻ đã đuợc reset.
- Sau đó, khởi tạo SPI, dùng hàm truyền, nhận SPI trong file spi.c. (2 hàm này bọn nó ko kiểm tra các bít SPIRBF, SPITBF, hàm read cũng chẳng có write 0xFF, em cho thêm vào thì chạy ok). Gửi lại 2 lệnh CMD0 để reset (response = 1 ,reset), rồi CMD1 khởi tạo thẻ (response = 0, kết thúc init)
-Sau đó em test lệnh đọc 1 sector(CMD17)
gửi cmd17 (res 0, ko lỗi) sau đó đợi token (đợi 0xFE), có token rồi bắt đầu đọc liên tiếp 512 byte dữ liệu.

Nói tóm lại là em viết phải viết lại hàm SendMMCCmd() và MDD_SDSPI_SectorRead(). Mặc dù về cơ chế của nó cũng chẳng khác gì của mình

Vấn đề là em muốn sửa lại ko dùng điều khiển I/O nữa, nói chung là dùng toàn bộ thư viện.
Hiện tượng hiện tại là: nếu bỏ đoạn dùng I/O, reset vẫn chạy bình thường. Nhưng rút thẻ ra cắm lại, thì đến chỗ gửi cmd0 bằng SPI thì toàn trả về 0....(Nếu có đoạn code kia thì cắm, rút mái thoải, vẫn ok)

Thêm nữa, trong thư viện, đường SS =0 mỗi khi bắt đầu gửi lệnh và =1 mỗi khi gửi xong. Trong giải thuật đọc 1 sector, đến phần đợi data_token, đường SS bị nâng lên 1. VẬy đường SS này có ảnh hưởng thế nào đến việc response của thẻ.

bien_van_khat
17-12-2009, 09:19 AM
Thế thì những thẻ ko có MBR thì chịu không đọc đuợc à. Hay là ko đọc MBR nữa mà nhảy thẳng vào boot sector của partition...

Theo quan điểm của mình, MBR chỉ có tác dụng khi thẻ có nhiều phân vùng. Code của bạn phải có khả năng xác định sector 0 là BR hay MBR

Hiện tượng hiện tại là: nếu bỏ đoạn dùng I/O, reset vẫn chạy bình thường. Nhưng rút thẻ ra cắm lại, thì đến chỗ gửi cmd0 bằng SPI thì toàn trả về 0....(Nếu có đoạn code kia thì cắm, rút mái thoải, vẫn ok)

Rút thẻ ra cắm lại, bạn có init ko? hay ko thể init?

Thêm nữa, trong thư viện, đường SS =0 mỗi khi bắt đầu gửi lệnh và =1 mỗi khi gửi xong. Trong giải thuật đọc 1 sector, đến phần đợi data_token, đường SS bị nâng lên 1. VẬy đường SS này có ảnh hưởng thế nào đến việc response của thẻ.
CS phải tích cực thì mới truy xuất được thẻ.
Hàm SendMMCCmd:

// see if we are expecting data or not
if(!(sdmmc_cmdtable[cmd].moredataexpected))
SD_CS = 1;

có kiểm tra lệnh được gửi có cần thêm data theo sau hay ko, nếu có thì nó vẫn tích cực chân CS.

tahi
18-12-2009, 11:38 PM
Rút thẻ ra cắm lại, bạn có init ko? hay ko thể init?

Mạch của em làm nguồn không ổ định, nên cứ rút thẻ ra, cắm lại là bị reset. Và không thể init lại, có nghĩa là gửi lệnh CMD0 để reset thẻ thì ko thấy response nữa.


// see if we are expecting data or not
if(!(sdmmc_cmdtable[cmd].moredataexpected))
SD_CS = 1;

có kiểm tra lệnh được gửi có cần thêm data theo sau hay ko, nếu có thì nó vẫn tích cực chân CS.
Có đoạn này, nhưng em ko hiểu, nên xóa đi mất roài :D. Thay bằng hàm trong cái code của con dspic304013

Làm thế nào để đọc được file lớn trong khi buffer là có hạn...?Ý em hỏi về cơ chế đọc file, rồi nhét vào buffer rồi xử lý cái đó như thế nào . ???

tahi
23-12-2009, 10:11 AM
Giờ em dính vấn đề với lệnh write vào thẻ CMD24. Rõ ràng ko có data response mà vẫn write được vào thẻ. Em dùng win hex để kiểm tra lại .

Lệnh write các sector liên tiếp nhau có hiện tượng, 1 sector có dữ liệu 1 sector lại ko,

Hiện tượng kỳ quái hơn là: đặt delay giữa các lần write vào 1 sector thì:
ko có data_response => ko có response của lệnh CMD24 => ko có data_response =>...
cứ thế.
Nhưng kết quả của việc đặt delay hay ko delay giữa mỗi lần write sector là như nhau. Đó là :1 sector có dữ liệu 1 sector lại ko,

Em dùng hàm của nó MDD_SDSPI_SectorWrite

rhinoceros
26-12-2009, 12:41 PM
em đã đọc luồng này từ đầu,và cũng đã tham khảo nhiều luồng viết về vấn đề này.nhưng em thấy các bác cứ nói lan man,lại chẳng biết các bác nói những cái gì .hic mới bắt đầu mong mọi người giúp.
các bác cho em hỏi.giờ em muốn làm 1 chiếc MP3 thì phải làm gì ?
phần cứng có VĐK kết nối với Thẻ nhớ theo chẩn SPI có sẵn trên chip
về phần phát ra âm thanh thì vẫn chưa định hướng được phải dùng cái gì ? DAC hay PWM ?
ưu điểm và nhược điểm của mỗi loại.
nếu dùng dac thì có phải ghép thêm dac ngoài không ?nếu thế em sợ tần số đưa ra không đủ.hoặc nếu có đủ thì chất lượng âm thanh sẽ kém !!!
về phần mềm thì cần phải thao tác những gì ?
thí dụ như giao tiếp với thẻ nhớ cần khởi tạo như thế nào ?
làm thế nào để có thể hiển thị được nội dung của 1 file(tên file,kích thước , độ dài , tần số ... )
bản thân con chip khi đọc được nội dung của 1 file MP3 thì nó không thể tự phát ra nhạc được,giống như trên win vậy,muốn chơi nhạc thì phải có trình chơi nhạc.vậy cần phải làm gì để chạy được file MP3 ra nhạc. em nghĩ mình cần include 1 thư viện chơi nhạc vào thôi :-? không biết có đúng không .nếu như thế thì file để include là thế nào? em cần tìm ở đâu?


_____________________
MR : Nguyễn Thắng
Tel : 0125.432.56.00
add: HaUI.trường đại học công nghiệp HN
Email: NgThang164@Gmail.com

tahi
30-12-2009, 01:38 PM
em đã đọc luồng này từ đầu,và cũng đã tham khảo nhiều luồng viết về vấn đề này.nhưng em thấy các bác cứ nói lan man,lại chẳng biết các bác nói những cái gì .hic mới bắt đầu mong mọi người giúp.
các bác cho em hỏi.giờ em muốn làm 1 chiếc MP3 thì phải làm gì ?
phần cứng có VĐK kết nối với Thẻ nhớ theo chẩn SPI có sẵn trên chip
về phần phát ra âm thanh thì vẫn chưa định hướng được phải dùng cái gì ? DAC hay PWM ?
ưu điểm và nhược điểm của mỗi loại.
nếu dùng dac thì có phải ghép thêm dac ngoài không ?nếu thế em sợ tần số đưa ra không đủ.hoặc nếu có đủ thì chất lượng âm thanh sẽ kém !!!
về phần mềm thì cần phải thao tác những gì ?
thí dụ như giao tiếp với thẻ nhớ cần khởi tạo như thế nào ?
làm thế nào để có thể hiển thị được nội dung của 1 file(tên file,kích thước , độ dài , tần số ... )
bản thân con chip khi đọc được nội dung của 1 file MP3 thì nó không thể tự phát ra nhạc được,giống như trên win vậy,muốn chơi nhạc thì phải có trình chơi nhạc.vậy cần phải làm gì để chạy được file MP3 ra nhạc. em nghĩ mình cần include 1 thư viện chơi nhạc vào thôi :-? không biết có đúng không .nếu như thế thì file để include là thế nào? em cần tìm ở đâu?

Hi, chắc bạn chưa đọc gì rồi. Chả có cái gì ngon và dễ sơi đâu.
Để phát nhạc đơn giản nhất bạn cần làm những việc sau:
SD card ->MCU-> Amplifier
Như vậy để đơn giản nhất, bạn cần 1 con MCU có tích hợp sẵn các module để hỗ trợ giao tiếp với thẻ và để phát tín hiệu âm thanh ra bộ khuếch đại.
-Thẻ SD thì giao tiếp bằng 2 mode , SD và SPI => dùng con MCU nào có SPI là xong
-Phát ra âm thanh thì có 2 cách, dùng DAC hoặc PWM(nếu dùng thằng này phải có bộ lọc bên ngoài để biến tín hiệu PWM thành tín hiệu hình sin...) => chọn MCU có DAC hoặc PWM là xong.

Vậy nguyên tắc sẽ là: MCU đọc thẻ, tìm lấy file nhạc, tách lấy header (bao gồm các thông tin về tần số lấy mẫu, độ dài dữ liệu, số kênh, stereo hay mono..có nén ko ...) Thông tin đó dùng để cấu hình cho DAC (tần số DAC, dùng mấy kênh... hoặc cấu hình duty circle cho thằng PWM). Nếu nhạc format đơn giản WAV thì chỉ cần đọc phần data của file rồi bắn ra bộ đếm của DAC là ok....Đương nhiên nếu bị giật giật hoặc chả nghe thấy cái gì thì còn phải calibrate nhiều .

Vậy cần đọc những gì:
+ Giao tiếp với thẻ SD (bên điện tử việt nam có anh viết khá kỹ).
+ SPI, DAC, PWM, timer của thằng MCU bạn làm
+ Format của file wave (.wav)

rhinoceros
04-01-2010, 04:02 PM
Hi, chắc bạn chưa đọc gì rồi. Chả có cái gì ngon và dễ sơi đâu.
Để phát nhạc đơn giản nhất bạn cần làm những việc sau:
SD card ->MCU-> Amplifier
Như vậy để đơn giản nhất, bạn cần 1 con MCU có tích hợp sẵn các module để hỗ trợ giao tiếp với thẻ và để phát tín hiệu âm thanh ra bộ khuếch đại.
-Thẻ SD thì giao tiếp bằng 2 mode , SD và SPI => dùng con MCU nào có SPI là xong
-Phát ra âm thanh thì có 2 cách, dùng DAC hoặc PWM(nếu dùng thằng này phải có bộ lọc bên ngoài để biến tín hiệu PWM thành tín hiệu hình sin...) => chọn MCU có DAC hoặc PWM là xong.

Vậy nguyên tắc sẽ là: MCU đọc thẻ, tìm lấy file nhạc, tách lấy header (bao gồm các thông tin về tần số lấy mẫu, độ dài dữ liệu, số kênh, stereo hay mono..có nén ko ...) Thông tin đó dùng để cấu hình cho DAC (tần số DAC, dùng mấy kênh... hoặc cấu hình duty circle cho thằng PWM). Nếu nhạc format đơn giản WAV thì chỉ cần đọc phần data của file rồi bắn ra bộ đếm của DAC là ok....Đương nhiên nếu bị giật giật hoặc chả nghe thấy cái gì thì còn phải calibrate nhiều .

Vậy cần đọc những gì:
+ Giao tiếp với thẻ SD (bên điện tử việt nam có anh viết khá kỹ).
+ SPI, DAC, PWM, timer của thằng MCU bạn làm
+ Format của file wave (.wav)

không phải em chưa đọc gì mà đọc không hiểu :D
hic,giao tiếp với thẻ nhớ SD. cái này thì không khó,khó cái quản lý theo FAT32 thế nào thôi.
em đọc mãi mà chẳng hiểu ,tài liệu của nó khó tìm quá. hỏi anh Google thì anh ấy chỉ toàn nói đến cách chuyển FAT với NTFS của máy tính thôi. anh có tài liệu về thằng này ,cho em xin nhé .mà anh cho em xin luôn cả link bên ĐTVN nói về cái này nhé.

SPI ,PWM thì em thấy đa số các chip đều có hỗ trợ ,nhưng hình như dòng dsPIC33 không có thằng DAC thì phải.anh biết dòng nào có chỉ em với .tốc độ chuyển của thằng DAC onchip thường là bao nhiêu vậy. liệu có đáp ứng được với tốc độ âm thanh đưa ra không ?

Fornat wave thì hình như là không cần làm gì, chỉ cần đọc và bắn thẳng ra DAC. nhưng em đọc và tìm hiểu trên mạng thì WAV còn có cả định dạng nén.vậy để tạo ra đc 1 file WAV không nén thì dùng cái gì để tạo thế ?
nếu muốn sử dụng định dạng MP3 thì phải làm những gì nữa. có phải mình sẽ include 1 đoạn mã vào để convert dữ liệu không.

tahi
11-01-2010, 04:50 PM
không phải em chưa đọc gì mà đọc không hiểu
hic,giao tiếp với thẻ nhớ SD. cái này thì không khó,khó cái quản lý theo FAT32 thế nào thôi.
em đọc mãi mà chẳng hiểu ,tài liệu của nó khó tìm quá. hỏi anh Google thì anh ấy chỉ toàn nói đến cách chuyển FAT với NTFS của máy tính thôi. anh có tài liệu về thằng này ,cho em xin nhé .mà anh cho em xin luôn cả link bên ĐTVN nói về cái này nhé.

Link dientuvietnam
http://www.dientuvietnam.net/forums/showthread.php?p=99791
Down bộ Microchip Solution rồi vào C:\Microchip Solutions\Microchip\MDD File System\Documentation
tìm tài liệu AN1045, có nói khá base về FAT....

SPI ,PWM thì em thấy đa số các chip đều có hỗ trợ ,nhưng hình như dòng dsPIC33 không có thằng DAC thì phải.anh biết dòng nào có chỉ em với .tốc độ chuyển của thằng DAC onchip thường là bao nhiêu vậy. liệu có đáp ứng được với tốc độ âm thanh đưa ra không ?

dsPIC33 hình như thằng nào cũng có DAC hay sao ý. (toàn DAC 16 bit)
tần số vào max tầm 45 kHz
tốc độ lấy mẫu cỡ 100 KSPS
Đó là thông số của dsPIC33FJ128MCx04

Fornat wave thì hình như là không cần làm gì, chỉ cần đọc và bắn thẳng ra DAC. nhưng em đọc và tìm hiểu trên mạng thì WAV còn có cả định dạng nén.vậy để tạo ra đc 1 file WAV không nén thì dùng cái gì để tạo thế ?

Cái này vào ổ C ấn F3 để search, sau đó gõ wav, lầy file bất kỳ search được, vào property rồi summary để xem các thông số. Đa số là các file wav khá chuẩn (hoặc trong mấy trò như halflife, đế chế đều có..)

nếu muốn sử dụng định dạng MP3 thì phải làm những gì nữa. có phải mình sẽ include 1 đoạn mã vào để convert dữ liệu không.

Cái này t bất lực, chưa nghiên cứu

rhinoceros
08-02-2010, 03:28 PM
cảm ơn anh tahi nhé.em đã down được bộ thư viện của Microchip về rồi(>70MB)
cài xong rồi,nhưng mà không biết làm thế nào để làm việc với bộ thư viện đồ sộ đó được
thông thường khi viết code cho chương trình thì người ta #include các thư viện vào.vậy đối với bộ thư viện của anh Microchip thì ta phải làm thế nào vậy ah.
trên thấy anh bảo là dòng dsPIC33 hỗ trợ DAC,em tìm mãi mà không thấy
anh có thể chỉ hộ em được không (em không biết nó là cái nào :()

http://i209.photobucket.com/albums/bb11/rhinoceros164/dsPIC33FJ128MC204.jpg

bien_van_khat
08-02-2010, 04:14 PM
Dòng 80x mới có DAC
http://www.microchip.com/wwwproducts/Devices.aspx?dDocName=en532298

kokoro
29-03-2010, 01:28 PM
Link dientuvietnam
http://www.dientuvietnam.net/forums/showthread.php?p=99791
Down bộ Microchip Solution rồi vào C:\Microchip Solutions\Microchip\MDD File System\Documentation
tìm tài liệu AN1045, có nói khá base về FAT....

Ai có thể gửi cho e cái link download thằng này không? Vì em qua bên dientuvietnam nhưng tìm không thấy link download như bác nói

bien_van_khat
29-03-2010, 03:54 PM
http://www.microchip.com/stellent/idcplg?IdcService=SS_GET_PAGE&nodeId=2680&dDocName=en537044

link tải ở gần cuối trang

kokoro
02-04-2010, 12:06 PM
- Mấy anh đã làm về sd card rồi cho em hỏi, mua cái đế cắm sd card ở đâu vây? Em ra chợ Nhật Tảo kiếm nhưng không có. Thank!

greenfield
02-04-2010, 03:31 PM
Bạn qua Thiên Minh ấy muốn bao nhiêu cũng cóa.hehe

truongtam2008
29-04-2010, 09:53 AM
Các bác ơi! có bác nào biết chỗ mua con dspic33Fj256GP802 không thế! em đang cần lắm!

lybao_huy
05-05-2010, 11:10 PM
Tôi đang làm SD Card tất cả đều tốt chỉ có lúc gửi lệnh xóa CMD32=địa chỉ đầu và CMD33=địa chỉ cuối và sau đó nhận đáp ứng từ Card thì ổn cả, sau đó tiếp tục gửi lệnh ghi đơn khối CMD24 thì đáp ứng nhận được là 0x02==ERASE_RESET, tôi đọc nó nó viết như sau:(tôi không hiểu ý nghĩa của nó)
1-Erase reset—An erase sequence was cleared before executing because an out of erase sequence command was received.
2-If an out of sequence command (except SEND_STATUS) is received, the card shall set the ERASE_RESET status bit in the status register, reset the erase sequence and execute the last command.

Mong các bạn giải thích dùm.

bien_van_khat
06-05-2010, 09:24 AM
Tôi đang làm SD Card tất cả đều tốt chỉ có lúc gửi lệnh xóa CMD32=địa chỉ đầu và CMD33=địa chỉ cuối và sau đó nhận đáp ứng từ Card thì ổn cả, sau đó tiếp tục gửi lệnh ghi đơn khối CMD24 thì đáp ứng nhận được là 0x02==ERASE_RESET, tôi đọc nó nó viết như sau:(tôi không hiểu ý nghĩa của nó)
1-Erase reset—An erase sequence was cleared before executing because an out of erase sequence command was received.
2-If an out of sequence command (except SEND_STATUS) is received, the card shall set the ERASE_RESET status bit in the status register, reset the erase sequence and execute the last command.

Mong các bạn giải thích dùm.

1 - Để xóa một số sector bạn phải gửi CMD38 sau khi gửi CMD32 và CMD33
2 - Nếu bạn muốn ghi một hoặc nhiều sector bạn dùng CMD24 hoặc CMD25. Chú ý là thao tác ghi đã bao gồm thao tác xóa. Bạn ko cần phải yêu cầu xóa bằng CMD38 trước.

lybao_huy
06-05-2010, 10:33 AM
oh, cảm ơn bạn rất rất nhiều, từ lúc mình nghiên cứu Dspic với Mplab C bạn giúp mình rất nhiều, trên nền tảng giúp đỡ của bạn mình cảm thấy việc tự học thấy rất dễ dàng. Xin cảm ơn bạn rất nhiều

bien_van_khat
06-05-2010, 12:45 PM
you're welcome! :D

lybao_huy
18-05-2010, 12:36 PM
Tôi đang thắc mắc về việc Format thẻ nhớ MicroSD có hay không có Master Boot Record. Tôi có đọc thanh ghi CSD của cả 2 thẻ 512MB và 1GB và tìm được 2 trường:
-FILE_FORMAT_GROUP=0
-FILE_FORMAT=0
từ đó suy ra là "Hard disk-like file system with partition table " nguyên văn trong Spec của MicroSD.
thế nhưng khi dùng WinHex để xem thì thấy chỉ có thẻ 1GB là có MBR còn thẻ 512 thì chỉ có Boot Sector không có MBR. Vậy thì câu hỏi đặt ra là làm sao đọc thẻ trên hệ thống nhúng mà ta không hề biết là có MBR hay không, vì nếu không có MBR lúc format trong khi ta lại đọc thanh ghi CSD lại báo là có MBR thì chúng ta đọc Boot Sector lại cứ tưởng là đang đọc MBR.
Xin các bạn giải thích dùm với. Mình viết Driver với định dạng FAT16 cho thẻ SD gần xong rồi nhưng lại dính cái bệnh này thật khổ

bien_van_khat
18-05-2010, 01:02 PM
Bạn chỉ cần đọc sector 0, kiểm tra xem nó là MBR hay bootsector, vì cấu trúc của MBR và bootsector khác nhau.

lybao_huy
18-05-2010, 01:48 PM
vậy là chỉ có cách là đọc sector 0 để biết có MBR hay không?có vẻ hơi mệt đấy.
Cảm ơn bạn nhiều.

lybao_huy
18-05-2010, 07:15 PM
Tôi dùng MPLAB IDE ver 8.46. tôi có 3 file h.c, g.h, main.c:
1-h.c chứa hàm unsigned long cal1():
unsigned long cal1(){
return 125100;
}
2-g.h chứa hàm unsigned long cal2().
unsigned long cal2(){
return 125100;
}
3-có 2 trường hợp:
3a- main.c chứa lệnh cal2() và in giá trị 125100 lên màn hình.
3b-main.c chứa lệnh cal1() và in giá trị không chính xác lên màn hình nếu giá trị này lớn hơn 32767.

xin các bạn giải thích dùm

lybao_huy
01-06-2010, 10:02 PM
cho mình hỏi cái này với: READ_BL_PARTIAL=1 means that smaller blocks can be used as well. The minimum block size will be equal to minimum addressable unit (one byte) và Single Block Mode : The block length for read operations is limited by the device sector size (512 bytes) but can be as small as a single byte. vậy nếu muốn đọc 10 byte thì phải làm sao, chỗ này mình làm theo nhưng không được

dtvtb
17-06-2010, 02:46 AM
Xin hỏi mấy huynh trong Root Directory(RD) của FATcó chỗ nào phân biệt Directory nào là cha,Directory nào la con.
Em tìm hiểu cái này thì thấy specific nó ghi 32 bytes cho 1 entry trong RD,nó đề cập đến
khá nhiều khía cạnh:byte phân biệt file và folder,tên file,thời gian tạo....
Nhưng làm sao để phân biệt Directory nào là cha,Directory nào la con thì em đuối...
Mong trợ giúp !

lybao_huy
17-06-2010, 10:24 PM
Xin hỏi mấy huynh trong Root Directory(RD) của FATcó chỗ nào phân biệt Directory nào là cha,Directory nào la con.
Em tìm hiểu cái này thì thấy specific nó ghi 32 bytes cho 1 entry trong RD,nó đề cập đến
khá nhiều khía cạnh:byte phân biệt file và folder,tên file,thời gian tạo....
Nhưng làm sao để phân biệt Directory nào là cha,Directory nào la con thì em đuối...
Mong trợ giúp !

Dường như bạn chưa đọc nhiều về vấn đề này lắm. Thật ra nó cũng rất đơn giản, bạn đọc nó nhiều lần, tìm trên google ấy. Sau đó hỏi tiếp mình sẽ trả lời cho, chứ bạn hỏi chung chung quá.

somali123
18-06-2010, 01:15 AM
mấy anh ơi,em đang làm mạch giao tiếp với SD card,nhưng đang bí là trong thư viện orcad không có chân của SDcard,ai có thì post giùm nha,cả bên capture lẫn layout luôn.

tahi
18-06-2010, 04:17 PM
thư viện footprint thẻ nhớ của bọn thái
http://www.thaieasyelec.com/Free-Service-from-ThaiEasyElec/Footprint-and-symbol.html

Có ai bị dính bênh reset toàn hệ thống khi cắm nóng thẻ nhớ vào ko ạ...??

minh hai
28-10-2010, 06:13 PM
code tham khảo của bác falleaf (dùng cho chú dsPIC30F4013).Cụ thể là trong thread này:
http://www.picvietnam.com/forum/showthread.php?t=1663


#define BLOCK_SIZE 512
unsigned char SD_ReadBlock(unsigned long addr, unsigned char *buf)
{
unsigned int i;
unsigned char status;
unsigned char CMD17_READ_SINGLE_BLOCK[] = {17,0x00,0x00,0x0,0x00,0xFF};
CMD17_READ_SINGLE_BLOCK[1] = ((addr & 0xFF000000) >> 24);
CMD17_READ_SINGLE_BLOCK[2] = ((addr & 0x00FF0000) >> 16);
CMD17_READ_SINGLE_BLOCK[3] = ((addr & 0x0000FF00) >> 8);
CMD17_READ_SINGLE_BLOCK[4] = ((addr & 0x000000FF));
SD_Enable();
i=0;
do
{
status = SD_WriteCommand(CMD17_READ_SINGLE_BLOCK);
send_hex(status,"CMD17:");
if(i++ > 50)
{
putsUART1((unsigned int*)"Read sector failed\n\r");
break;
}
}
while(status != 0x00);
//Waif
Delay_Us(150);
// Send the read command
if(status != 0)
{
// ABORT: invalid response for read single command
return 1;
}
// Now wait for the "Start Block" token (0xFE)
// (see SanDisk SD Card Product Manual v1.9 section 5.2.4. Data Tokens)
do
{
status = SPIRead();
send_hex(status,"waitf token:");
} while(status != 0xFE);
// Read off all the bytes in the block
for(i = 0; i < BLOCK_SIZE; ++i)
{
status = SPIRead();
*buf = status;
buf++;
}
// Read CRC bytes
status = SPIRead();
status = SPIRead();
SD_Disable();
// Following a read transaction, the SD Card needs 8 clocks after the end
// bit of the last data block to finish up its work.
// (from SanDisk SD Card Product Manual v1.9 section 5.1.8)
SPIWrite(0xFF);
return 0;
}

trong main
status = SD_ReadBlock(0, buffer);
Hàm SD_WriteCommand vẫn giữ nguyên. Hàm read đã có write dummy data (write FF)
Còn lệnh nào có response R1 mà test đuợc không nhỉ. Tốc độ giao tiếp phụ thuộc thế nào với các loại thẻ khác nhau.
Khởi tạo thẻ nhớ với tốc độ 150k, gửi lệnh cmd0 để reset thẻ, R1 = 0x01 (ok..đã in idle state). Sau đó gửi lệnh cmd1 để vào data transfer mode. Chuyển tốc độ lên 1.25MHz. R1 = 0x00 (đã vào mode transfer)
Sau đó gửi lệnh CMD17 để đọc single block thì toàn response 0x20
Ở đây em chỉ đọc 512 byte bắt đầu từ địa chỉ 0x00, không biết đó có phải sector 0 hay ko. (em đã quét cả dải địa chỉ mà vẫn báo về như thế...)
CRC có chú ý gì ko?

Hàm read đã có write dummy data (write FF) ?? bạn ơi cho mình hỏi ghi data FF trong hàm hàm read có ý nghĩa j ? tại sao phải viết dữ liệu giả như thế ?

bien_van_khat
28-10-2010, 08:16 PM
Hàm read đã có write dummy data (write FF) ?? bạn ơi cho mình hỏi ghi data FF trong hàm hàm read có ý nghĩa j ? tại sao phải viết dữ liệu giả như thế ?

SPI muốn đọc thì phải ghi!

minh hai
01-11-2010, 11:38 AM
bác ơi em mới bắt đầu làm giao tiếp pic với SD card, có điều em muốn hỏi bác là em có thể dùng thẻ micro SD rồi cắm vào Adapter để thay cho thẻ SD card 32M mà project về SD của anh falleaf nói tới không?
(thông cảm em mới làm nên chưa có kiến thức gì về những cái này )

lybao_huy
01-11-2010, 05:30 PM
ừ, bạn có thể dùng adapter để cắp thẻ nhớ micro SD vaò, rồi cứ theo sơ đồ Pin của adapter mà kết nối

HYknight
29-11-2010, 09:13 PM
Chào các bác !!!
Em cũng đang ngâm cứu về SDCard
Nhưng hiện tại em mới chỉ khởi tạo cho thẻ mà không được
Reset thì thẻ vẫn trả về được Reponse R1 = 0x01
Đây là code và shematic
Mong các bác xem và giúp đỡ em

//Chuong trinh giao tiep voi SD card --------------------------
// ------------ main.c ------------------------------
#include <18F452.h>
#fuses hs,nowdt,nolvp
#use delay (clock = 12000000)
#include <LCD_HYknight.C>
#include <def_18f452.c>
#use rs232(baud=9600,parity=N,xmit=PIN_C6,rcv=PIN_C7,ER RORS)
#include <SDCard.c>


void main()
{
SETUP_ADC_PORTS(NO_ANALOGS);
SETUP_SPI (SPI_MASTER | SPI_SS_DISABLED |SPI_H_TO_L| SPI_CLK_DIV_4 | SPI_XMIT_L_TO_H);

TRISA = 0X00 ;
TRISC = 0X93;
TRISB = 0XF0;
TRISD = 0X0F;
TRISE = 0X00;
CS=1;


LCD_INIT();

PRINTF("\r\n**** Doc ghi SD card - HYknight - CFOC **** ");
PRINTF("\r\n");
DELAY_MS(2000);

PRINTF("\r\ Khoi tao Card..... ");
PRINTF("\r\n");
DELAY_MS(2000);


if(mmc_init()== 0)
{
printf("> Khoi tao card thanh cong...\r\n>");
DELAY_MS(2000);
}
else
{
printf("> Khong khoi tao duoc, xin moi khoi tao lai...!\r\n");
LCD_PUTCHAR("Khong kt duoc");

}



}




// --------------- SDCard.c ----------------------
// -----------------------------------------------

#DEFINE CS rc2 // chip select for MMC
#DEFINE SDO rc5
#DEFINE CLK rc3
#DEFINE SDI rc4

void send_6byte(int8 cmd, int16 argh, int16 argl, int8 crc7);
int mmc_init();

char str[600];
CHAR CH;

int8 HIGH(long data)
{
int8 modi;
modi = data>>8;
return(modi);
}

int8 LOW(long data)
{
int8 modi;
modi = data;
return(modi);
}

void send_6byte(int8 cmd, int16 argh, int16 argl, int8 crc7)
{
spi_write(cmd);
spi_write(make8(argh,1));
spi_write(make8(argh,0));
spi_write(make8(argl,1));
spi_write(make8(argh,0));
spi_write(crc7);
}

int mmc_response(unsigned char response)
{
unsigned long count = 0xFFFF; // 16bit repeat, it may be possible to shrink this to 8 bit but there is not much point

while(SPI_READ(0xFF) != response && --count > 0);

if(count==0) return 1; // loop was exited due to timeout
else return 0; // loop was exited before timeout
}

int mmc_init()
{
int i;
*0x94 |= 0x40; // set CKE = 1 - clock idle low
*0x14 &= 0xEF; // set CKP = 0 - data valid on rising edge

CS =1; // set cs = 1 (off)
SPI_WRITE(0xFF);
for(i=0;i<16;i++) // initialise the MMC card into SPI mode by sending clks on
{
SPI_WRITE(0xFF);
}

CS =0; // set cs = 0 (on) tells card to go to spi mode when it receives reset
send_6byte(0x40,0,0,0x95);

for(i= 0; i< 100; i++)
{
if(spi_read(0x00)== 0x01)
{
break;
}
}

if(i>= 100) // Check for Time-out Error
{
return(1);
}

printf("CMD40 OK (R1= 0x01)\n\r");
DELAY_MS(2000);
// ----------> Den day van duoc

send_6byte(0x55, 0, 0, 0xff);
send_6byte(0x41, 0, 0, 0xff);


for(i= 0; i<255; i++)
{
if(spi_read(0x00)== 0x00)
{
break;
}

}

if(i>=255)
{
return(1);
}


printf("CMD41 OK (R1= 0x00)\n\r");
DELAY_MS(2000);

return (0);

}

minh hai
07-12-2010, 05:35 PM
các bác đã có kinh nghiệm là thẻ SDcard cho em hỏi với, em dùng thẻ micro cắm vào adapter rồi dùng như thẻ SDcard bình thường và đã dùng hàm đọc sector để đọc được sector 0 là master boot record và đã thu được như sau hình dưới . nhưng em không biết làm cách nào để đọc cái này. có bác nào làm ơn hướng dẫn em cách để đọc cái này được không và giải thích dùm em có phải em đã đọc sector 0 được rồi phải không và card của em đã active được chưa (hình như là chưa thì phải nhưng không biết tại sao ) và bước tiếp theo em phải làm gì. em xin cảm ơn !

HYknight
11-12-2010, 11:36 AM
Hj ! Sau 1 hồi đọc lại bài viết của các anh cũng như tài liệu thì em cũng đã đọc ghi được SDCard
Nhưng em muốn hỏi 1 chút là bây giờ chip em sử dụng là 18F4523 (để dùng luôn ADC 12 bit)
Em đã sử dụng SDCard vậy h em muốn sử dụng cả DS1307 thì có cách nào không ạ ?
Em tìm thì cũng thấy có những IC Real-Time giao tiếp SPI nhưng không tự tin lắm vì thời gian hoàn thành của em là không nhiều.
Còn DS1307 thì em dùng rồi nhưng không biết làm thế nào để dùng cả 2.

Mong các anh chỉ giáo !!!!

bien_van_khat
12-12-2010, 01:02 PM
Hj ! Sau 1 hồi đọc lại bài viết của các anh cũng như tài liệu thì em cũng đã đọc ghi được SDCard
Nhưng em muốn hỏi 1 chút là bây giờ chip em sử dụng là 18F4523 (để dùng luôn ADC 12 bit)
Em đã sử dụng SDCard vậy h em muốn sử dụng cả DS1307 thì có cách nào không ạ ?
Em tìm thì cũng thấy có những IC Real-Time giao tiếp SPI nhưng không tự tin lắm vì thời gian hoàn thành của em là không nhiều.
Còn DS1307 thì em dùng rồi nhưng không biết làm thế nào để dùng cả 2.

Mong các anh chỉ giáo !!!!

Bạn có thể làm giao thức I2C = phần mềm. Nếu dùng CCS C thì đã hỗ trợ sẵn. Còn dùng C18 thì tự viết cũng nhanh, vì I2C đơn giản. Code mẫu về I2C mềm có rất nhiều trên mạng.

minh hai
13-12-2010, 04:10 PM
bác ơi bác làm ơn giúp em với, em mới làm SDcard và em chưa biết gì về nó cả, mong bác chỉ giáo em với ! em có post các địa chỉ của MBR rồi đó, bác xem và giúp em với

hoathanlq
30-12-2010, 05:21 PM
Cho mình hỏi câu hơi ngu....sao không thấy ai nói gì về SD card ở chế độ SD mode vậy...có phải nó quá dễ không....
Mình có search trên Google mà hình như chẳng có ai giao tiếp với SD card qua chế độ SD mode.....Thấy một số người trên diễn đàn khác kêu SD mode dễ hơn SPI mode..mà mình đọc mấy cái tài liệu Product Manual...thấy còn khó hơn cả SPI...

lambaotrung
06-12-2012, 09:40 PM
có bác nào làm dc 1 bài của thể về việc giao tiếp giửa PIC và SD card chưa.