CLEON  Version 1
Cloud-Offloaded GPS Receiver
diskio.c File Reference
#include "hal_define.h"
#include "sys_define.h"
#include "fs_define.h"
Include dependency graph for diskio.c:

Go to the source code of this file.

Macros

#define INIT_PORT()   HAL_SPI_Init() /* Initialize MMC control port */
 
#define FAST_MODE()   SYS_MMC_FastMode() /* Maximize SD Card transfer speed */
 
#define DLY_US(n)   __delay_cycles(n * 12)
 
#define CS_H()   SYS_MMC_DeselectCard() /* Set MMC CS "high" */
 
#define CS_L()   SYS_MMC_SelectCard() /* Set MMC CS "low" */
 
#define WP   (0) /* Card is write protected (yes:true, no:false, default:false) */
 
#define CMD0   (0) /* GO_IDLE_STATE */
 
#define CMD1   (1) /* SEND_OP_COND */
 
#define ACMD41   (0x80 + 41) /* SEND_OP_COND (SDC) */
 
#define CMD8   (8) /* SEND_IF_COND */
 
#define CMD9   (9) /* SEND_CSD */
 
#define CMD10   (10) /* SEND_CID */
 
#define CMD12   (12) /* STOP_TRANSMISSION */
 
#define ACMD13   (0x80 + 13) /* SD_STATUS (SDC) */
 
#define CMD16   (16) /* SET_BLOCKLEN */
 
#define CMD17   (17) /* READ_SINGLE_BLOCK */
 
#define CMD18   (18) /* READ_MULTIPLE_BLOCK */
 
#define CMD23   (23) /* SET_BLOCK_COUNT */
 
#define ACMD23   (0x80 + 23) /* SET_WR_BLK_ERASE_COUNT (SDC) */
 
#define CMD24   (24) /* WRITE_BLOCK */
 
#define CMD25   (25) /* WRITE_MULTIPLE_BLOCK */
 
#define CMD41   (41) /* SEND_OP_COND (ACMD) */
 
#define CMD55   (55) /* APP_CMD */
 
#define CMD58   (58) /* READ_OCR */
 

Functions

DWORD get_fattime (void)
 
DSTATUS disk_status (BYTE drv)
 
uint8_t validateCSD (void)
 
unsigned char detectCard (void)
 
DSTATUS disk_initialize (BYTE drv)
 
DRESULT disk_read (BYTE drv, BYTE *buff, DWORD sector, BYTE count)
 

Variables

BYTE INS = 1
 

Macro Definition Documentation

#define ACMD13   (0x80 + 13) /* SD_STATUS (SDC) */

Definition at line 61 of file diskio.c.

#define ACMD23   (0x80 + 23) /* SET_WR_BLK_ERASE_COUNT (SDC) */

Definition at line 66 of file diskio.c.

#define ACMD41   (0x80 + 41) /* SEND_OP_COND (SDC) */

Definition at line 56 of file diskio.c.

#define CMD0   (0) /* GO_IDLE_STATE */

Definition at line 54 of file diskio.c.

#define CMD1   (1) /* SEND_OP_COND */

Definition at line 55 of file diskio.c.

#define CMD10   (10) /* SEND_CID */

Definition at line 59 of file diskio.c.

#define CMD12   (12) /* STOP_TRANSMISSION */

Definition at line 60 of file diskio.c.

#define CMD16   (16) /* SET_BLOCKLEN */

Definition at line 62 of file diskio.c.

#define CMD17   (17) /* READ_SINGLE_BLOCK */

Definition at line 63 of file diskio.c.

#define CMD18   (18) /* READ_MULTIPLE_BLOCK */

Definition at line 64 of file diskio.c.

#define CMD23   (23) /* SET_BLOCK_COUNT */

Definition at line 65 of file diskio.c.

#define CMD24   (24) /* WRITE_BLOCK */

Definition at line 67 of file diskio.c.

#define CMD25   (25) /* WRITE_MULTIPLE_BLOCK */

Definition at line 68 of file diskio.c.

#define CMD41   (41) /* SEND_OP_COND (ACMD) */

Definition at line 69 of file diskio.c.

#define CMD55   (55) /* APP_CMD */

Definition at line 70 of file diskio.c.

#define CMD58   (58) /* READ_OCR */

Definition at line 71 of file diskio.c.

#define CMD8   (8) /* SEND_IF_COND */

Definition at line 57 of file diskio.c.

#define CMD9   (9) /* SEND_CSD */

Definition at line 58 of file diskio.c.

#define CS_H ( )    SYS_MMC_DeselectCard() /* Set MMC CS "high" */

Definition at line 24 of file diskio.c.

#define CS_L ( )    SYS_MMC_SelectCard() /* Set MMC CS "low" */

Definition at line 25 of file diskio.c.

#define DLY_US (   n)    __delay_cycles(n * 12)

Definition at line 22 of file diskio.c.

#define FAST_MODE ( )    SYS_MMC_FastMode() /* Maximize SD Card transfer speed */

Definition at line 21 of file diskio.c.

#define INIT_PORT ( )    HAL_SPI_Init() /* Initialize MMC control port */

Definition at line 20 of file diskio.c.

#define WP   (0) /* Card is write protected (yes:true, no:false, default:false) */

Definition at line 28 of file diskio.c.

Function Documentation

unsigned char detectCard ( void  )

Definition at line 360 of file diskio.c.

{
//Check for a valid CSD response
if (validateCSD()){
disk_status(0); //Update the INS variable
return ( 1) ; //Card is present
}
//We didn't get a valid response. So we now know the status is one of two things:
//a) The card isn't there at all;
//b) or, it was just inserted recently, and needs to be initialized
INS = 0x01; //Trick disk_initialize into thinking it's inserted...
disk_initialize(0); //Attempt to initialize it
INS = validateCSD(); //Try again
disk_status(0); //Update the INS variable
return ( INS) ; //1 = card is present; 0 = not present
}

Here is the call graph for this function:

DSTATUS disk_initialize ( BYTE  drv)

Definition at line 386 of file diskio.c.

{
#pragma diag_suppress=Pe550
BYTE n, ty, cmd, buf[4];
UINT tmr;
INIT_PORT(); /* Initialize control port */
s = disk_status(drv); /* Check if card is in the socket */
if (s & STA_NODISK){
return ( s) ;
}
CS_H();
for (n = 10; n; n--){rcvr_mmc(buf, 1); /* 80 dummy clocks */
}
ty = 0;
if (send_cmd(CMD0, 0) == 1){ /* Enter Idle state */
if (send_cmd(CMD8, 0x1AA) == 1){ /* SDv2? */
rcvr_mmc(buf, 4); /* Get trailing return value of R7 resp */
if (buf[2] == 0x01 && buf[3] == 0xAA){ /* The card can work at vdd range of 2.7-3.6V */
for (tmr = 1000; tmr; tmr--)
{ /* Wait for leaving idle state (ACMD41 with HCS bit) */
if (send_cmd(ACMD41, 1UL << 30) == 0){
break;
}
DLY_US(1000);
}
if (tmr && send_cmd(CMD58, 0) == 0){ /* Check CCS bit in the OCR */
rcvr_mmc(buf, 4);
ty = (buf[0] & 0x40) ? CT_SD2 | CT_BLOCK : CT_SD2; /* SDv2 */
}
}
} else { /* SDv1 or MMCv3 */
if (send_cmd(ACMD41, 0) <= 1){
ty = CT_SD1; cmd = ACMD41; /* SDv1 */
} else {
ty = CT_MMC; cmd = CMD1; /* MMCv3 */
}
for (tmr = 1000; tmr; tmr--)
{ /* Wait for leaving idle state */
if (send_cmd(ACMD41, 0) == 0){
break;
}
DLY_US(1000);
}
if (!tmr || send_cmd(CMD16, 512) != 0){ /* Set R/W block length to 512 */
ty = 0;
}
}
}
CardType = ty;
deselect();
if (ty){ /* Initialization succeded */
s &= ~STA_NOINIT;
} else { /* Initialization failed */
s |= STA_NOINIT;
}
Stat = s;
return (s);
}

Here is the call graph for this function:

Here is the caller graph for this function:

DRESULT disk_read ( BYTE  drv,
BYTE buff,
DWORD  sector,
BYTE  count 
)

Definition at line 461 of file diskio.c.

{
DSTATUS s;
s = disk_status(drv);
if (s & STA_NOINIT){
return ( RES_NOTRDY) ;
}
if (!count){
return ( RES_PARERR) ;
}
if (!(CardType & CT_BLOCK)){
sector *= 512; /* Convert LBA to byte address if needed */
}
if (count == 1){ /* Single block read */
if ((send_cmd(CMD17, sector) == 0) /* READ_SINGLE_BLOCK */
&& rcvr_datablock(buff, 512)){
count = 0;
}
} else { /* Multiple block read */
if (send_cmd(CMD18, sector) == 0){ /* READ_MULTIPLE_BLOCK */
do {
if (!rcvr_datablock(buff, 512)){
break;
}
buff += 512;
} while (--count);
send_cmd(CMD12, 0); /* STOP_TRANSMISSION */
}
}
deselect();
return (count ? RES_ERROR : RES_OK);
}

Here is the call graph for this function:

Here is the caller graph for this function:

DSTATUS disk_status ( BYTE  drv)

Definition at line 301 of file diskio.c.

{
DSTATUS s = Stat;
if (drv || !INS){
} else {
s &= ~STA_NODISK;
if (WP){
} else {
s &= ~STA_PROTECT;
}
}
Stat = s;
return (s);
}

Here is the caller graph for this function:

DWORD get_fattime ( void  )

Definition at line 35 of file diskio.c.

{
DWORD tmr;
/* Pack date and time into a DWORD variable */
tmr = (((DWORD)(HAL_GetRTCYear()-1980)) << 25)
| ((DWORD)HAL_GetRTCMon() << 21)
| ((DWORD)HAL_GetRTCDay() << 16)
| (WORD)(((unsigned char) HAL_GetRTCHour()) << 11)
| (WORD)(((unsigned char) HAL_GetRTCMin()) << 5)
| (WORD)(((unsigned char) HAL_GetRTCSec()) >> 1);
return (tmr);
}

Here is the call graph for this function:

Here is the caller graph for this function:

uint8_t validateCSD ( void  )

Definition at line 323 of file diskio.c.

{
BYTE csd0[16], csd1[16], i;
WORD sum = 0;
//Pull the CSD -- twice. If the response codes are invalid, then we know the card isn't there or initialized.
if ((send_cmd(CMD9, 0) == 0) && rcvr_datablock(csd0, 16)){
if ((send_cmd(CMD9, 0) == 0) && rcvr_datablock(csd1, 16)){
//The response codes were good -- but maybe the SPI input was just floating low. Let's evaluate the CSD data.
//First, look for all zero or all ones. If the SPI input is floating, these are the most likely outcomes.
for (i = 0; i <= 15; i++){
sum += csd0[i];
}
if (!((sum == 0) || (sum == 4096))){
//The response was a mix of 0's and 1's. Floating inputs could still do that -- but it's unlikely they'd
//produce the same pattern twice. Compare to ensure the two are identical.
i = 0;
while (i <= 15)
{
if (csd0[i] != csd1[i]){
break;
}
i++;
}
if (i > 15){
return ( 1) ;
}
}
}
}
return ( 0) ;
}

Here is the caller graph for this function:

Variable Documentation

BYTE INS = 1

Definition at line 27 of file diskio.c.