Пример #1
0
u8 sd_open( void ) {
	u8 i;
	u8 resp[ R1 + 16 + 2 ];
	u24 deleteme;
	// Check for card
	if( !sd_card_present() ) return( SD_ERR_NOCARD );
	// SPI to 400kHz
	SPI_BRG_H = 0x00;
	SPI_BRG_L = 0x7D;

	// Required delays before initialization
	sd_assert();
	sd_delay( 100 );
	sd_deassert();
	sd_delay( 2 );

	// Enter idle state
	if( sd_send_command( CMD0_GO_IDLE_STATE, NULL, NULL ) != SD_ERR_OK ) return( SD_ERR_GENERIC );

	// Read OCR (for operating conditions) and verify 3.3V capability
	if( sd_send_command( CMD58_READ_OCR, NULL, resp ) != SD_ERR_OK ) return( SD_ERR_GENERIC );
	if( !( resp[ 2 ] & MSK_OCR_33 ) ) return( SD_ERR_OCR );

	// Initialize card
	i = 0;
	do {
		if( sd_send_command( ACMD41_APP_SEND_OP_COND, NULL, resp ) != SD_ERR_OK ) return( SD_ERR_GENERIC );
	} while( ( resp[ 0 ] & SD_ERR_R1_IDLE ) && ++i != SD_IDLE_TIMEOUT );

	// Set block length to 512 (compatible with SDHC)
	if( sd_set_blocklen( 512 ) != SD_ERR_OK ) return( SD_ERR_GENERIC );

	// Read CSD
	//if( sd_send_command( CMD9_SEND_CSD, NULL, resp ) != SD_ERR_OK ) return( SD_ERR_GENERIC );
	/*
	for( i = 0; i < 255; i++ ) {
		sd_readblock( i, block );
		for( deleteme = 0; deleteme < 512; deleteme++ ) {
			if( block[ deleteme ] != 0 ) {
				asm( "NOP" );
				asm( "NOP" );
				asm( "NOP" );
				asm( "NOP" );
				asm( "NOP" );
				asm( "NOP" );
				asm( "NOP" );
				asm( "NOP" );
				break;
			}
		}
	}
	*/

	// All hail the initialized SD card!
	return( SD_ERR_OK );
}	
Пример #2
0
int sd_initialize()
{
	char i, j;
	sdc->busyflag = 0;
	for (i=0; i<4; i++)
		argument[i] = 0;
	/* Delay for at least 74 clock cycles. This means to actually
	 * *clock* out at least 74 clock cycles with no data present on
	 * the clock. In SPI mode, send at least 10 idle bytes (0xFF). */
	spi_cs_assert();
	sd_delay(100);
	spi_cs_deassert();
	sd_delay(2);
	/* Put the card in the idle state */
	if (sd_send_command(sdc, CMD0, CMD0_R, response, argument) == 0)
		return 0;
	/* Now wait until the card goes idle. Retry at most SD_IDLE_WAIT_MAX times */
	j = 0;
	do
	{
		j++;
		/* Flag the next command as an application-specific command */
		if (sd_send_command(sdc, CMD55, CMD55_R, response, argument) == 1)
		{
			/* Tell the card to send its OCR */
			sd_send_command(sdc, ACMD41, ACMD41_R, response, argument);
		}
		else
		{
			/* No response, bail early */
			j = SD_IDLE_WAIT_MAX;
		}
	}
	while ((response[0] & MSK_IDLE) == MSK_IDLE && j < SD_IDLE_WAIT_MAX);
	/* As long as we didn't hit the timeout, assume we're OK. */
	if (j >= SD_IDLE_WAIT_MAX)
		return 0;
	if (sd_send_command(sdc, CMD58, CMD58_R, response, argument) == 0)
		return 0;
	/* At a very minimum, we must allow 3.3V. */
	if ((response[2] & MSK_OCR_33) != MSK_OCR_33)
		return 0;
	/* Set the block length */
	if (sd_set_blocklen (sdc, SD_BLOCKSIZE) != 1)
		return 0;
	/* If we got this far, initialization was OK. */
	return 1;
}
Пример #3
0
int32_t  SDWriteCSD(uint8_t  *buff)
{
	int8_t				response;
	uint8_t				tcrc;
	uint16_t			i;

	response = sd_send_command(SD_PROGRAM_CSD, 0);
	if (response != 0)
	{
		return  SDCARD_RWFAIL;
	}
	xchg(0xfe);							// send data token marking start of data block

	tcrc = 0;
	for (i=0; i<15; i++)				// for all 15 data bytes in CSD...
	{
    	xchg(*buff);					// send each byte via SPI
		tcrc = AddByteToCRC(tcrc, *buff);		// add byte to CRC
	}
	xchg((tcrc<<1) + 1);				// format the CRC7 value and send it

	xchg(0xff);							// ignore dummy checksum
	xchg(0xff);							// ignore dummy checksum

	i = 0xffff;							// max timeout
	while (!xchg(0xFF) && (--i))  ;		// wait until we are not busy

    sd_clock_and_release();				// cleanup  
	if (i)  return  SDCARD_OK;			// return success
	else  return  SDCARD_RWFAIL;		// nope, didn't work
}
Пример #4
0
/**
 * @brief Reads a single block from SD card, specifically for the dictionary
 *        functions
 *        Reads 512 bytes (SPI Block) from SD Card
 * @return unsigned char - 0 if no error and response byte if error
 */
unsigned char sd_read_single_dict_block(unsigned long start_block)
{
  unsigned char response;
  unsigned int i, retry = 0;

  response = sd_send_command(READ_SINGLE_BLOCK, start_block); //read a Block command

  if(response != 0x00) return response; //check for SD status: 0x00 - OK (No flags set)

  SD_CS_ASSERT;

  retry = 0;
  while(spi_receive() != 0xfe) //wait for start block token 0xfe (0x11111110)
    if(retry++ > 0xfffe)
    {
      SD_CS_DEASSERT; 
      return 1;
    } //return if time-out

  for(i = 0; i < 512; i++) //read 512 bytes
    dict_buffer[i] = spi_receive();

  spi_receive(); //receive incoming CRC (16-bit), CRC is ignored here
  spi_receive();

  spi_receive(); //extra 8 clock pulses
  SD_CS_DEASSERT;

  return 0;
}
Пример #5
0
/*
	This function writes a single block to the SD card at block
	blockaddr. Returns 1 if the command was successful, zero
	otherwise.

	This is an ASYNCHRONOUS call. The transfer will not be complete
	when the function returns. If you want to explicitly wait until
	any pending transfers are finished, use the command
	sd_wait_notbusy(sdc).

	sd_context_t *sdc
	 -- a pointer to an sd device context structure,
		populated by the function sd_initialize()

	u32 blockaddr
	 -- The block address to read from the card.
		This is a block address, not a linear address.

	uint8_t *data
	 -- The data, a pointer to an array of unsigned
		chars.
*/
int sd_write_block(sd_context_t *sdc, uint32_t blockaddr,
				   uint8_t *data)
{
	/* Adjust the block address to a linear address */
	blockaddr <<= SD_BLOCKSIZE_NBITS;

	/* Wait until any old transfers are finished */
	sd_wait_notbusy(sdc);

	/* Pack the address */
	sd_packarg(argument, blockaddr);

	if (sd_send_command(sdc, CMD24, CMD24_R, response, argument) == 0)
		return 0;

	/* Check for an error, like a misaligned write */
	if (response[0] != 0)
		return 0;

	/* Re-assert CS to continue the transfer */
	spi_cs_assert();

	/* The write command needs an additional 8 clock cycles before
	* the block write is started. */
	spi_rcv_byte();

	/* Clear any pending flags */
	IFG1 &= ~(URXIFG0 | UTXIFG0);

	/* Get the block */
	/* Source DMA address: the data buffer. */
	DMA0SA = (unsigned short)data;

	/* Destination DMA address: the UART send register. */
	DMA0DA = U0TXBUF_;

	/* The size of the block to be transferred */
	DMA0SZ = SD_BLOCKSIZE;

	/* Configure the DMA transfer*/
	DMA0CTL =
		DMADT_0 |    /* Single transfer mode */
		DMASBDB |    /* Byte mode */
		DMAEN |      /* Enable DMA */
		DMASRCINCR1 | DMASRCINCR0; /* Increment the source address */

	/* DMA trigger is UART send */
	DMACTL0 = DMA0TSEL_3;

	/* Kick off the transfer by sending the first byte, the "start block"
	* token */
	U0TXBUF = SD_TOK_WRITE_STARTBLOCK;

	/* Signal that the card may be busy, so any subsequent commands
	should wait for the busy signalling to end (indicated by a
	nonzero response). */
	sdc->busyflag = 1;

	return 1;
}
Пример #6
0
int sd_write_block (sd_context_t *sdc, u32 blockaddr, unsigned char *data){
blockaddr <<= SD_BLOCKSIZE_NBITS;			//Adjust the block address to a linear address.
sd_wait_notbusy (sdc);						// Wait until any old transfers are finished.

sd_packarg(argument, blockaddr);			//Pack the address.
if (sd_send_command(sdc, CMD24, CMD24_R, response, argument) == 0){		//Check for an error, like a misaligned write.
	return 0;
}
if (response[0] != 0){
	return 0;
}
spi_cs_assert();	//Re-assert CS to continue the transfer.
		/* The write command needs an additional 8 clock cycles before
		the block write is started. */
spi_rcv_byte();		//Clear any pending flags.
IFG1 &= ~(URXIFG0 | UTXIFG0);		//Get the block.
DMA0SA = (unsigned short)data;		//Source DMA address: the data buffer.
DMA0DA = U0TXBUF_;					//Destination DMA address: the UART send register.
DMA0SZ = SD_BLOCKSIZE;				//The size of the block to be transferred.
DMA0CTL =							//Configure the DMA transfer.
	DMADT_0 |					//Single transfer mode.
	DMASBDB |					//Byte mode.
	DMAEN |						//Enable DMA.
	DMASRCINCR1 | DMASRCINCR0;	// Increment the source address.
DMACTL0 = DMA0TSEL_3;				//DMA trigger is UART send.
//-------------------------Kick off the transfer by sending the first byte, the "start block" token---------------------------
U0TXBUF = SD_TOK_WRITE_STARTBLOCK;		//Signal that the card may be busy, so any subsequent commands should wait for the busy signalling to end (indicated by a nonzero response).
sdc->busyflag = 1;
return 1;
}
Пример #7
0
static u8 sd_set_blocklen( u32 len ) {
	u8 resp;
	if( sd_send_command( CMD16_SET_BLOCKLEN, &len, &resp ) != SD_ERR_OK ) return( SD_ERR_GENERIC );
	if( resp ) return( SD_ERR_R1_MASK | resp );
	blocklen = len;
	return( SD_ERR_OK );
}
Пример #8
0
Файл: sd.c Проект: Pikrass/pios
// For now, start and len are a number of 512-byte blocks
int sd_read(struct sd_card *card, int start, int len, void *dest) {
	int bl_addr;
	struct dma_cb ctrl __attribute__ ((__aligned__(32)));

	if(card->type == 0)
		start *= 512;

	dmb();
	*BLKSIZECNT = BLKSIZE(512) | BLKCNT(len);

	sd_send_command(CMD_READ_MULTIPLE_BLOCK,
			TM_BLKCNT_EN | TM_AUTO_CMD_12 | TM_DAT_CARD_TO_HOST |
			TM_MULTI_BLOCK | CMD_RSPNS_48 | CMD_ISDATA, start);

	ctrl.ti = DMA_TI_INTEN | DMA_TI_WAIT_RESP |
		DMA_TI_DEST_INC | DMA_TI_DEST_WIDTH |
		DMA_TI_SRC_DREQ | DMA_TI_PERMAP_EMMC;
	ctrl.source_ad = IO_TO_BUS(DATA);
	ctrl.dest_ad = virt_to_phy(dest);
	ctrl.txfr_len = 512 * len;
	ctrl.stride = 0;
	ctrl.nextconbk = 0;

	return dma_initiate(DMA_CHAN_EMMC, &ctrl);
}
Пример #9
0
/**
 * @brief Reads multiple blocks from the SD card and send every block to UART
 * @return unsigned char - 0 if no error and response byte if error
 */
unsigned char sd_read_multiple_blocks (unsigned long start_block, 
    unsigned long total_blocks)
{
  unsigned char response;
  unsigned int i, retry = 0;

  retry = 0;

  response = sd_send_command(READ_MULTIPLE_BLOCKS, start_block); //write a Block command

  if(response != 0x00) return response; //check for SD status: 0x00 - OK (No flags set)

  SD_CS_ASSERT;

  while(total_blocks)
  {
    retry = 0;
    while(spi_receive() != 0xfe) //wait for start block token 0xfe (0x11111110)
      if(retry++ > 0xfffe)
      {
        SD_CS_DEASSERT; 
        return 1;
      } //return if time-out

    for(i = 0; i < 512; i++) //read 512 bytes
      buffer[i] = spi_receive();

    spi_receive(); //receive incoming CRC (16-bit), CRC is ignored here
    spi_receive();

    spi_receive(); //extra 8 cycles

    for(i = 0; i < 512; i++) //send the block to UART
    {
      if(buffer[i] == '~') break;
      transmit_byte(buffer[i]);
    }

    total_blocks--;
  }

  sd_send_command(STOP_TRANSMISSION, 0); //command to stop transmission
  SD_CS_DEASSERT;
  spi_receive(); //extra 8 clock pulses

  return 0;
}
Пример #10
0
static int8_t  ReadCardStatus(void)
{
	cardstatus[0] = sd_send_command(SD_SEND_STATUS, 0);
	cardstatus[1] = xchg(0xff);
//	printf_P(PSTR("\r\nReadCardStatus = %02x %02x"), cardstatus[0], cardstatus[1]);
	xchg(0xff);
	return  SDCARD_OK;
}
Пример #11
0
/*
 *  ==========================================================================
 *
 *  sd_send_command      send raw command to SD card, return response
 *
 *  This routine accepts a single SD command and a 4-byte argument.  It sends
 *  the command plus argument, adding the appropriate CRC.  It then returns
 *  the one-byte response from the SD card.
 *
 *  For advanced commands (those with a command byte having bit 7 set), this
 *  routine automatically sends the required preface command (CMD55) before
 *  sending the requested command.
 *
 *  Upon exit, this routine returns the response byte from the SD card.
 *  Possible responses are:
 *    0xff	No response from card; card might actually be missing
 *    0x01  SD card returned 0x01, which is OK for most commands
 *    0x?? 	other responses are command-specific
 */
static  int8_t  sd_send_command(uint8_t  command, uint32_t  arg)
{
	uint8_t				response;
	uint8_t				i;
	uint8_t				crc;

	if (command & 0x80)					// special case, ACMD(n) is sent as CMD55 and CMDn
	{
		command = command & 0x7f;		// strip high bit for later
		response = sd_send_command(CMD55, 0);	// send first part (recursion)
		if (response > 1)  return response;
	}

	sd_clock_and_release();
	select();							// enable CS
	xchg(0xff);

    xchg(command | 0x40);				// command always has bit 6 set!
	xchg((unsigned char)(arg>>24));		// send data, starting with top byte
	xchg((unsigned char)(arg>>16));
	xchg((unsigned char)(arg>>8));
	xchg((unsigned char)(arg&0xff));
	crc = 0x01;							// good for most cases
	if (command == SD_GO_IDLE)  crc = 0x95;			// this will be good enough for most commands
	if (command == SD_SEND_IF_COND)  crc = 0x87;	// special case, have to use different CRC
    xchg(crc);         					// send final byte                          

	for (i=0; i<10; i++)				// loop until timeout or response
	{
		response = xchg(0xff);
		if ((response & 0x80) == 0)  break;	// high bit cleared means we got a response
	}

/*
 *  We have issued the command but the SD card is still selected.  We
 *  only deselect the card if the command we just sent is NOT a command
 *  that requires additional data exchange, such as reading or writing
 *  a block.
 */
	if ((command != SD_READ_BLK) &&
		(command != SD_WRITE_BLK) &&
		(command != SD_READ_OCR) &&
		(command != SD_SEND_CSD) &&
		(command != SD_SEND_STATUS) &&
		(command != SD_SEND_CID) &&
		(command != SD_SEND_IF_COND) &&
		(command != SD_LOCK_UNLOCK) &&
		(command != SD_PROGRAM_CSD))
	{
		sd_clock_and_release();
	}

	return  response;					// let the caller sort it out
}
Пример #12
0
							//initialization was successful, 0 otherwise.
							//sd_context_t *sdc -- pointer to a data structure containing
							//information about the card. For now, the
							//timeouts MUST be specified in advance. This
							//function does not yet calculate them from the
							//card data.
int sd_initialize(sd_context_t *sdc){
	char i, j;						//SPI SD initialization sequence: CMD0->CMD55->ACMD41->CMD58.
	j = 0;							//Note there is no CMD2 or CMD3 in SPI mode. These instructions are devoted to addressing on the SD bus.
	sdc->busyflag = 0;				//SD memory card SD initialization sequence: CMD0->CMD55->ACMD41->CMD2->CMD3.
	
	for (i=0; i<4; i++){
	argument[i] = 0;
	}								//Delay for at least 74 clock cycles. This means to actually
	spi_cs_assert();				//*clock* out at least 74 clock cycles with no data present on
	sd_delay(100);					//the clock. In SPI mode, send at least 10 idle bytes (0xFF).
	spi_cs_deassert();
	sd_delay(2);
	if (sd_send_command(sdc, CMD0, CMD0_R, response, argument) == 0){	 //Put the card in the idle state
	return 0;
	}
//-------------------------------------Now wait until the card goes idle. Retry at most SD_IDLE_WAIT_MAX times.-------------------------------------- 
	do{
	j++;
									//Flag the next command as an application-specific command.
	if (sd_send_command(sdc, CMD55, CMD55_R, response, argument) == 1){
		sd_send_command(sdc, ACMD41, ACMD41_R, response, argument);		//Tell the card to send its OCR
	}
	else{							// No response, bail early.
		j = SD_IDLE_WAIT_MAX;
	}
	}
	while ((response[0] & MSK_IDLE) == MSK_IDLE && j < SD_IDLE_WAIT_MAX);	//As long as we didn’t hit the timeout, assume we’re OK.
	if (j >= SD_IDLE_WAIT_MAX){
	return 0;
	}
	if (sd_send_command(sdc, CMD58, CMD58_R, response, argument) == 0){
	return 0;
	}
	if ((response[2] & MSK_OCR_33) != MSK_OCR_33){		//At a very minimum, we must allow 3.3V.
	return 0;
	}
	if (sd_set_blocklen (sdc, SD_BLOCKSIZE) != 1){		//Set the block length
	return 0;
	}
	return 1;	//If we got this far, initialization was OK.
}
Пример #13
0
/**
 * @brief Erases the specified no. of blocks of SD card
 * @return unsigned char - 0 if no error and response byte if error
 */
unsigned char sd_erase (unsigned long start_block, unsigned long total_blocks) {
    unsigned char response;

    // Send starting block address
    response = sd_send_command(ERASE_BLOCK_START_ADDR, start_block); 

    if (response != 0x00) //check for SD status: 0x00 - OK (No flags set)
        return response;

    // Send end block address
    response = sd_send_command(ERASE_BLOCK_END_ADDR, (start_block + total_blocks - 1));

    if (response != 0x00)
        return response;

    // Erase all selected blocks
    response = sd_send_command(ERASE_SELECTED_BLOCKS, 0); 
    if (response != 0x00)
        return response;

    return 0;
}
Пример #14
0
int32_t  SDReadOCR(uint8_t  *buff)
{
	uint8_t				i;
	int8_t				response;

	for (i=0; i<4;  i++)  buff[i] = 0;

	if (SDType == SDTYPE_SDHC)
	{
		response = sd_send_command(SD_SEND_IF_COND, 0x1aa);
		if (response != 0)
		{
			sd_clock_and_release();			// cleanup  
			return  SDCARD_RWFAIL;
		}
		for (i=0; i<4; i++)
		{
			buff[i] = xchg(0xff);
		}
		xchg(0xff);							// burn the CRC
	}
	else
	{
		response = sd_send_command(SD_READ_OCR, 0);
		if (response != 0x00)
		{
			sd_clock_and_release();			// cleanup  
			return  SDCARD_RWFAIL;
		}
		for (i=0; i<4; i++)					// OCR is 4 bytes
		{
			buff[i] = xchg(0xff);
		}
		xchg(0xff);
	}
    sd_clock_and_release();				// cleanup  
	return  SDCARD_OK;
}
Пример #15
0
/**
 * @brief Writes a single block of SD Card. Data that is written is put into the
 *        buffer variables and writes out the 512 charachters.  
 * @param start_block - unsigned long, describes which block you want to right 
 * @return unsigned char - 0 if no error
 *                         response byte will be sent if an error
 */
unsigned char sd_write_single_block(unsigned long start_block)
{
  unsigned char response;
  unsigned int i, retry = 0;

  response = sd_send_command(WRITE_SINGLE_BLOCK, start_block); //write a Block command

  if(response != 0x00) return response; //check for SD status: 0x00 - OK (No flags set)
  SD_CS_ASSERT;

  spi_transmit(0xfe);     //Send start block token 0xfe (0x11111110)

  for(i = 0; i < 512; i++)    //send 512 bytes data
    spi_transmit(buffer[i]);

  spi_transmit(0xff);     //transmit dummy CRC (16-bit), CRC is ignored here
  spi_transmit(0xff);

  response = spi_receive();

  if((response & 0x1f) != 0x05) //response= 0xXXX0AAA1 ; AAA='010' - data accepted
  {                              //AAA='101'-data rejected due to CRC error
    SD_CS_DEASSERT;              //AAA='110'-data rejected due to write error
    return response;
  }

  while(!spi_receive()) //wait for SD card to complete writing and get idle
    if(retry++ > 0xfffe)
    {
      SD_CS_DEASSERT; 
      return 1;
    }

  SD_CS_DEASSERT;
  spi_transmit(0xff);   //just spend 8 clock cycle delay before reasserting the CS line
  SD_CS_ASSERT;         //re-asserting the CS line to verify if card is still busy

  while(!spi_receive()) //wait for SD card to complete writing and get idle
    if(retry++ > 0xfffe)
    {
      SD_CS_DEASSERT; 
      return 1;
    }

  SD_CS_DEASSERT;

  return 0;
}
Пример #16
0
int sd_send_command(unsigned char cmd, uint32_t arg)
{
    unsigned char n, res, *p;

    if (cmd & 0x80) {   /* ACMD<n> is the command sequense of CMD55-CMD<n> */
        cmd &= 0x7F;
        res = sd_send_command(CMD55, 0);
        if (res > 1)
            return res;
    }

    /* Select the card and wait for ready */
    sd_spi_release(); /* raise CS, then sends 8 clocks (some cards require this) */
    sd_spi_lower_cs();
    if(sd_spi_wait(true) != 0xFF)
        return 0xFF;

    /* Send command packet */
    sd_spi_transmit_byte(cmd);                        /* Start + Command index */
#if 0
    sd_spi_transmit_byte((unsigned char)(arg >> 24)); /* Argument[31..24] */
    sd_spi_transmit_byte((unsigned char)(arg >> 16)); /* Argument[23..16] */
    sd_spi_transmit_byte((unsigned char)(arg >> 8));  /* Argument[15..8] */
    sd_spi_transmit_byte((unsigned char)arg);         /* Argument[7..0] */
#else
    /* sdcc sadly unable to figure this out for itself yet */
    p = ((unsigned char *)&arg)+3;
    sd_spi_transmit_byte(*(p--));                     /* Argument[31..24] */
    sd_spi_transmit_byte(*(p--));                     /* Argument[23..16] */
    sd_spi_transmit_byte(*(p--));                     /* Argument[15..8] */
    sd_spi_transmit_byte(*p);                         /* Argument[7..0] */
#endif
    /* there's only a few commands (in native mode) that need correct CRCs */
    n = 0x01;                                                /* Dummy CRC + Stop */
    if (cmd == CMD0) n = 0x95;                               /* Valid CRC for CMD0(0) */
    if (cmd == CMD8) n = 0x87;                               /* Valid CRC for CMD8(0x1AA) */
    sd_spi_transmit_byte(n);

    /* Receive command response */
    if (cmd == CMD12)
        sd_spi_receive_byte();     /* Skip a stuff byte when stop reading */
    n = 20;                             /* Wait for a valid response */
    do {
        res = sd_spi_receive_byte();
    } while ((res & 0x80) && --n);

    return res;         /* Return with the response value */
}
Пример #17
0
/*
 *  SDWriteBlock      write buffer of data to SD card
 *
 *  I've lost track of who created the original code for this
 *  routine; I found it somewhere on the web.
 *
 *	Write a single 512 byte sector to the MMC/SD card
 *  blocknum holds the number of the 512-byte block to write,
 *  buffer points to the 512-byte buffer of data to write.
 *
 *  Note that for SD (not SDHC) cards, blocknum will be converted
 *  into a byte address.
 */
int32_t  SDWriteBlock(uint32_t  blocknum, uint8_t  *buff)
{
	uint16_t				i;
	uint8_t					status;
	uint32_t				addr;

	if (!registered)  return  SDCARD_NOT_REG;

/*
 *  Compute byte address of start of desired sector.
 *
 *  For SD cards, the argument to CMD17 must be a byte address.
 *  For SDHC cards, the argument to CMD17 must be a block (512 bytes) number.
 */
	if (SDType == SDTYPE_SD)  addr = blocknum << 9;	// SD card; convert block number to byte addr
	else					  addr = blocknum;		// SDHC card; just use blocknum as is

	status = sd_send_command(SD_WRITE_BLK, addr);

	if (status != SDCARD_OK)			// if card does not send back 0...
	{
		sd_clock_and_release();			// cleanup
		return  SDCARD_RWFAIL;
	}

	xchg(0xfe);							// send data token marking start of data block

	for (i=0; i<512; i++)				// for all bytes in a sector...
	{
    	xchg(*buff++);					// send each byte via SPI
	}

	xchg(0xff);							// ignore dummy checksum
	xchg(0xff);							// ignore dummy checksum

	if ((xchg(0xFF) & 0x0F) != 0x05)
	{
		sd_clock_and_release();			// cleanup
		return  SDCARD_RWFAIL;
	}
	
	i = 0xffff;							// max timeout  (nasty timing-critical loop!)
	while (!xchg(0xFF) && (--i))  ;		// wait until we are not busy
	sd_clock_and_release();				// cleanup
	return  SDCARD_OK;					// return success		
}
Пример #18
0
static u8 sd_readblock( u32 addr, u8 *data ) {
	u8 tmp, i, resp[ R2 ];
	u24 count;
	u16 crc;

	addr <<= 9;

	//sd_waitidle();

	if( sd_send_command( CMD17_READ_SINGLE_BLOCK, &addr, resp ) != SD_ERR_OK ) return( SD_ERR_GENERIC );

	if( resp[ 0 ] ) return( SD_ERR_READ );

	sd_assert();

	// Wait (with timeout) for data token
	i = 0;
	do {
		tmp = spi_txrx( CMD_IDLE );
	} while( ++i != SD_READ_TIMEOUT && tmp == 0xFF );

	// Bail on error
	if( !( tmp & MSK_TOK_DATAERROR ) ) {
		spi_txrx( CMD_IDLE );
		sd_deassert();
		return( SD_ERR_READ );
	}

	// Read data
	count = 512;
	while( count-- ) {
		*data++ = spi_txrx( CMD_IDLE );
	}

	// Read CRC
	high8( crc ) = spi_txrx( CMD_IDLE );
	low8( crc ) = spi_txrx( CMD_IDLE );

	tmp = spi_txrx( CMD_IDLE );

	sd_deassert();

	return( SD_ERR_OK );
}
Пример #19
0
uint8_t devsd_transfer_sector1(void)
{
    uint8_t attempt;
    bool success;

    sd_drive = blk_op.blkdev->driver_data & DRIVE_NR_MASK;

    for(attempt=0; attempt<8; attempt++){
	if(sd_send_command(blk_op.is_read ? CMD17 : CMD24, 
                    /* for byte addressed cards, shift LBA to convert to byte address */
                    (blk_op.blkdev->driver_data & CT_BLOCK) ? blk_op.lba : (blk_op.lba << 9)
                    ) == 0){
	    if(blk_op.is_read){
                success = (sd_spi_wait(false) == 0xFE);
                if(success){
                    sd_spi_receive_sector();
					//sd_spi_wait(false);
				}
            }else{
                success = false;
                if(sd_spi_wait(true) == 0xFF){
                    sd_spi_transmit_byte(0xFE);
                    sd_spi_transmit_sector();
                    sd_spi_transmit_byte(0xFF); /* dummy CRC */
                    sd_spi_transmit_byte(0xFF);
                    success = ((sd_spi_wait(false) & 0x1F) == 0x05);
                }
            }
	}else
	    success = false;

	sd_spi_release();

	if(success)
	    return 1;

	kputs("sd: failed, retrying.\n");
    }

    udata.u_error = EIO;
    return 0;
}
Пример #20
0
int32_t  SDReadCID(uint8_t  *buff)
{
	uint8_t			i;
	int8_t			response;

	for (i=0; i<16; i++)  buff[i] = 0;

	response = sd_send_command(SD_SEND_CID, 0);
	response = sd_wait_for_data();
	if (response != (int8_t)0xfe)
	{
		return  SDCARD_RWFAIL;
	}

	for (i=0; i<16; i++)
	{
		buff[i] = xchg(0xff);
	}
	xchg(0xff);							// burn the CRC
    sd_clock_and_release();				// cleanup  
	return  SDCARD_OK;
}
Пример #21
0
static int8_t  ModifyPWD(uint8_t  mask)
{
	int8_t						r;
	uint16_t					i;

	mask = mask & 0x07;					// top five bits MUST be 0, do not allow forced-erase!
	r = sd_send_command(SD_LOCK_UNLOCK, 0);
	if (r != 0)
	{
		return  SDCARD_RWFAIL;
	}
	xchg(0xfe);							// send data token marking start of data block

	xchg(mask);							// always start with required command
	xchg(pwd_len);						// then send the password length
	for (i=0; i<512; i++)				// need to send one full block for CMD42
	{
		if (i < pwd_len)
		{
    		xchg(pwd[i]);					// send each byte via SPI
		}
		else
		{
			xchg(0xff);
		}
	}

	xchg(0xff);							// ignore dummy checksum
	xchg(0xff);							// ignore dummy checksum

	i = 0xffff;							// max timeout
	while (!xchg(0xFF) && (--i))  ;		// wait until we are not busy

	if (i)  return  SDCARD_OK;			// return success
	else  return  SDCARD_RWFAIL;		// nope, didn't work
}
Пример #22
0
int32_t  SDReadBlock(uint32_t  blocknum, uint8_t  *buff)
{
    uint16_t					i;
	uint8_t						status;
	uint32_t					addr;

	if (!registered)  return  SDCARD_NOT_REG;		// if no SPI functions, leave now
	if (SDType == SDTYPE_UNKNOWN)  return  SDCARD_UNKNOWN;	// card type not yet known

/*
 *  Compute byte address of start of desired sector.
 *
 *  For SD cards, the argument to CMD17 must be a byte address.
 *  For SDHC cards, the argument to CMD17 must be a block (512 bytes) number.
 */
	if (SDType == SDTYPE_SD) 	addr = blocknum << 9;	// SD card; convert block number to byte addr
	else						addr = blocknum;	// SDHC card; use the requested block number

    sd_send_command(SD_READ_BLK, addr); // send read command and logical sector address
	status = sd_wait_for_data();		// wait for valid data token from card
	if (status != 0xfe)					// card must return 0xfe for CMD17
    {
		xprintf("\n\rSDReadBlock: sd_wait_for_data returned %d", status);
        sd_clock_and_release();			// cleanup 
        return  SDCARD_RWFAIL;			// return error code
    }

    for (i=0; i<512; i++)           	// read sector data
        buff[i] = xchg(0xff);

    xchg(0xff);                		 	// ignore CRC
    xchg(0xff);                		 	// ignore CRC

    sd_clock_and_release();				// cleanup  
    return  SDCARD_OK;					// return success       
}
Пример #23
0
int sd_read_block (sd_context_t *sdc, u32 blockaddr, unsigned char *data){
unsigned long int i = 0;
unsigned char tmp;
unsigned char blank = 0xFF;

blockaddr <<= SD_BLOCKSIZE_NBITS;			//Adjust the block address to a linear address. 
sd_wait_notbusy (sdc);						//Wait until any old transfers are finished.
sd_packarg(argument, blockaddr);			//Pack the address.
	
	if (sd_send_command(sdc, CMD17, CMD17_R, response, argument) == 0){			//Need to add size checking.
	return 0;
	}
	if (response[0] != 0){		// Check for an error, like a misaligned read.
	return 0;
	}
spi_cs_assert();				//Re-assert CS to continue the transfer.
i=0;							//Wait for the token.		
	do{
	tmp = spi_rcv_byte();
	i++;
	}
	while ((tmp == 0xFF) && i < sdc->timeout_read );
	if ((tmp & MSK_TOK_DATAERROR) == 0){				//Clock out a byte before returning.
	spi_send_byte(0xFF);						//The card returned an error response. Bail and return 0
	return 0;
	}
//----------------------------------Prime the interrupt flags so things happen in the correct order.------------------------------------

IFG1 &= ~URXIFG0;
IFG1 &= ~UTXIFG0;
/* Get the block */
/* Source DMA address: receive register. */
DMA0SA = U0RXBUF_;
/* Destination DMA address: the user data buffer. */
DMA0DA = (unsigned short)data;
/* The size of the block to be transferred */
DMA0SZ = SD_BLOCKSIZE;
/* Configure the DMA transfer*/
DMA0CTL =	
	DMADT_0 |		/* Single transfer mode */
	DMASBDB |		/* Byte mode */
	DMAEN |			/* Enable DMA */
	DMADSTINCR1 | DMADSTINCR0; 		/* Increment the destination address */

/* We depend on the DMA priorities here. Both triggers occur at
the same time, since the source is identical. DMA0 is handled
first, and retrieves the byte. DMA1 is triggered next, and
sends the next byte. */

/* Source DMA address: constant 0xFF (don’t increment)*/
DMA1SA = (unsigned short)&blank;			/* Destination DMA address: the transmit buffer. */
DMA1DA = U0TXBUF_;							/* Increment the destination address */
DMA1SZ = SD_BLOCKSIZE-1;					/* The size of the block to be transferred */
DMA1CTL =									/* Configure the DMA transfer*/
	DMADT_0 |								/* Single transfer mode */
	DMASBDB |								/* Byte mode */
	DMAEN;									/* Enable DMA */
DMACTL0 = DMA0TSEL_3 | DMA1TSEL_3;				/* DMA trigger is UART receive for both DMA0 and DMA1 */
U0TXBUF = 0xFF;									/* Kick off the transfer by sending the first byte */
return 1;
}
Пример #24
0
static u8 sd_send_command( u16 cmd, void *arg, void* resp ) {
	u8 i, tmp;
	// Prefix with an ACMD?
	if( cmd & 0x0100 ) {
		tmp = sd_send_command( CMD55_APP_CMD, NULL, NULL );
		if( tmp != SD_ERR_OK ) return( tmp );
	}
	// Select SD card
	sd_assert();
	// Send command
	spi_txrx( ( ( ( u8 )cmd ) & 0x3F ) | 0x40 );
	// Send arguments
	if( arg ) {
		spi_txrx( *( ( ( u8* )arg ) + 3 ) );
		spi_txrx( *( ( ( u8* )arg ) + 2 ) );
		spi_txrx( *( ( ( u8* )arg ) + 1 ) );
		spi_txrx( *( ( ( u8* )arg ) + 0 ) );
	} else {
		spi_txrx( 0 );
		spi_txrx( 0 );
		spi_txrx( 0 );
		spi_txrx( 0 );
	}
	// CRC, ignored for all commands except reset - where it is always 0x95
	spi_txrx( 0x95 );
	// Read first response byte with timeout
	i = 0;
	do {
		tmp = spi_txrx( CMD_IDLE );
		i++;
	} while( ( tmp & 0x80 ) != 0 && i < SD_CMD_TIMEOUT );
	// Bail if timed out
	if( ( tmp & 0x80 ) != 0 ) {
		sd_deassert();
		return( SD_ERR_TIMEOUT );
	}
	switch( cmd ) {
		case CMD12_STOP_TRANSMISSION:
			i = R1b;
			break;
		case CMD8_SEND_IF_COND:
			i = R7;
			break;
		case CMD58_READ_OCR:
			i = R3;
			break;
		case CMD9_SEND_CSD:
		case CMD10_SEND_CID:
			i = R1 + 16 + 2;
			break;
		default:
			i = R1;
	}
	// Read remaining response data
	while( i-- ) {
		if( resp ) ( ( u8* )resp )[ i ] = tmp;
		tmp = spi_txrx( CMD_IDLE );
	}
	// Deselect card
	sd_deassert();
	// All seems to be in order
	return( SD_ERR_OK );
}
Пример #25
0
DSTATUS disk_initialize (BYTE pdrv)
{
    DSTATUS status;

    status = 0;

    if (pdrv < N_PDRV)
    {
        uint8_t r1;
        uint32_t arg_hcs;
        int tries;

        sd_init();
        tries = 4;
        do {
            r1 = sd_send_command_r1(0, 0);
            tries--;
        } while ((r1 != SD_STATE_IDLE) && (tries > 0));
        if (r1 != SD_STATE_IDLE)
        {
            status = STA_NODISK;
        }
        if (status == 0)
        {
            uint8_t r7[5];

            sd_send_command(8, 0x1AA, r7, sizeof(r7));
            if (
                    (r7[0] != SD_STATE_IDLE) /* state not idle */
                    ||
                    ((r7[3]&0x0F) != 0x01) /* not supported voltage range */
                    ||
                    (r7[4] != 0xAA) /* check pattern error */
               )
            {
                /* TODO: SD V1 */
                status = STA_NODISK;
            }
        }
        if (status == 0)
        {
            arg_hcs = 0x40000000;
            /* timeout should be around 1s.
             * SPI clk is 125kHz.
             * a command is around 8 bytes -> 64 SPI clk cycles.
             * a loop is around 128 SPI clk cycles -> ~1ms
             * tries = 1000 so it's ~1000ms.
             */
            tries = 1000;
            do
            {
                r1 = sd_send_command_r1(55, 0);
                r1 = sd_send_command_r1(41, arg_hcs);
                tries--;
            } while ((r1 & SD_STATE_IDLE) && (tries > 0));
            if (r1 & SD_STATE_IDLE)
            {
                status = STA_NODISK;
            }
        }
        if (status == 0)
        {
            uint8_t r3[5];
            
            sd_send_command(58, 0, r3, sizeof(r3));
            if (r3[1] & 0x40)
            {
                /* high capacity */
                pdrv_data[pdrv].byte_addressable = 0;
            }
            else
            {
                /* std capacity */
                pdrv_data[pdrv].byte_addressable = 1;
                r1 = sd_send_command_r1(16, SD_SECTOR_SIZE);
                if (r1 != 0)
                {
                    status = STA_NODISK;
                }
            }
        }
        if (status == 0)
        {
            sd_full_speed();
            pdrv_data[pdrv].initialized = 1;
            pdrv_data[pdrv].present = 1;
#ifndef SD_SPI_DISKIO_READONLY
            pdrv_data[pdrv].write_protected = 0;
            status = 0;
#else
            pdrv_data[pdrv].write_protected = 1;
            status = STA_PROTECT;
#endif
        }
    }
    else
    {
        status = STA_NODISK;
    }

    return status;
}
Пример #26
0
Файл: sd.c Проект: Pikrass/pios
int sd_init(struct sd_card *card) {
	int resp, powerup;
	int raw_csd[4];

	// Reset
	*CONTROL0 = 0;
	*CONTROL1 = SRST_HC;
	*CONTROL2 = 0;
	while(*CONTROL1 & SRST_HC);

	// Clock config
	*CONTROL1 = CLK_INTLEN | CLK_GENSEL | CLK_FREQ8(7) | DATA_TOUNIT_DISABLE;
	// Wait for internal clock to stabilize
	while((*CONTROL1 & CLK_STABLE) == 0);

	// Activate SD clock
	*CONTROL1 |= CLK_EN,

	// Enable interrupts
	*IRPT_MASK = IR_ALL;

	// Send CMD0
	if(sd_send_command(CMD_GO_IDLE_STATE, 0, 0))
		return 1;

	// Send CMD8
	if(sd_send_command(CMD_SEND_IF_COND, CMD_RSPNS_48BUSY, 0x1aa))
		return 2;
	if(*RESP0 != 0x1aa) {
		return 2;
	}

	// Send ACMD41 until powerup bit is received
	powerup = 0;
	while(!powerup) {
		*INTERRUPT = IR_ALL;
		*ARG1 = 0;
		*CMDTM = CMD_INDEX(CMD_APP) | TM_DAT_CARD_TO_HOST;
		while((*INTERRUPT & IR_CMD_DONE) == 0);

		idle(500);
		if(sd_send_command(CMD_SEND_OP_COND, CMD_RSPNS_48, 0x40ff0000))
			return 3;

		powerup = (*RESP0 & 0x80000000);
	}
	card->type = *RESP0 & 0x40000000;

	// Send CMD2 to get the CID
	if(sd_send_command(CMD_ALL_SEND_CID, CMD_RSPNS_136, 0))
		return 4;

	// Send CMD3 to get the RCA
	if(sd_send_command(CMD_SEND_RELATIVE_ADDR, CMD_RSPNS_48, 0))
		return 5;

	resp = *RESP0;
	card->rca = resp & 0xffff0000;

	// Send CMD9 to get the CSD
	if(sd_send_command(CMD_SEND_CSD, CMD_RSPNS_136, card->rca))
		return 6;

	raw_csd[0] = *RESP0;
	raw_csd[1] = *RESP1;
	raw_csd[2] = *RESP2;
	raw_csd[3] = *RESP3;
	sd_parse_csd(raw_csd, &card->csd);

	// Send CMD7 to select the card
	*INTERRUPT = IR_ALL;
	*ARG1 = card->rca;
	*CMDTM = CMD_INDEX(CMD_SELECT_CARD) | CMD_RSPNS_48;
	while(*INTERRUPT == 0);
	if(*INTERRUPT & IR_ERR) {
		return 7;
	}

	return 0;
}
Пример #27
0
/*
 * This function initializes the SD card. It returns 1 if
 * initialization was successful, 0 otherwise.
 *
 * sd_context_t *sdc -- Pointer to a data structure containing
 *                      information about the card. For now, the
 *                      timeouts must be specified in advance. It
 *                      is not yet calculated from the card data.
 */
int sd_initialize(sd_context_t *sdc)
{
	u16 i;

	/*
	 * SPI SDv2 initialization sequence:
	 *   CMD0
	 *   CMD8
	 *   CMD55+ACMD41
	 *   CMD58
	 *     (There is no CMD2 or CMD3 in SPI mode. These
	 *      instructions are devoted to addressing on the SD bus)
	 */

	sdc->busyflag = 0;

	/*
	 * Delay for at least 74 clock cycles. This means to actually
	 * *clock* out at least 74 clock cycles with no data present on
	 * the clock. In SPI mode, send at least 10 idle bytes (0xFF)
	 */
	spi_cs_deassert();
	sd_delay(100);
	spi_cs_assert();
	sd_delay(2);

	/* Put the card in thee idle state */
	if (sd_send_command(sdc, CMD0, CMD0_R, response, NULL) == 0)
		return 0;

	sd_packarg(argument, 0x000001AA);
	if (sd_send_command(sdc, CMD8, CMD8_R, response, argument) == 0) {
		return 0;
	}

	if (response[0] & MSK_ILL_CMD) {
		/* Illegal command, try SDv1 init */
		sd_packarg(argument, 0x00000000);
	} else {
		/* Check if the voltage range is appropiate */
		if (response[3] == 0x01 && response[4] == 0xAA) {
			sd_packarg(argument, 0x40000000);
		} else {
			return 0;
		}
	}

	/* Now wait until the card goes idle. Retry at most SD_IDLE_WAIT_MAX */
	i = 0;
	do {
		i++;
		/* Flag the next command as an application-specific command */
		if (sd_send_command(sdc, CMD55, CMD55_R, response, NULL) == 1) {
			/* Tell the card to send its OCR */
			sd_send_command(sdc, ACMD41, ACMD41_R, response, argument);
		} else {
			/* No response, bail early */
			i = SD_IDLE_WAIT_MAX;
		}
	} while ((response[0] & MSK_IDLE) == MSK_IDLE && i < SD_IDLE_WAIT_MAX);

	/* As long as we didn't hit the timeout, assume we're OK */
	if (i >= SD_IDLE_WAIT_MAX)
		return 0;

	if (sd_send_command(sdc, CMD58, CMD58_R, response, NULL) == 0)
		return 0;

	/* At the very minimum, we must allow 3.3V */
	if ((response[2] & MSK_OCR_33) != MSK_OCR_33)
		return 0;

	/* Set the block length */
	if (sd_set_blocklen(sdc, SD_BLOCKSIZE) != 1)
		return 0;

	/* If we got this far, initialization was OK */
	return 1;
}
Пример #28
0
/**
 * @brief Recieves data from UART and writes to multiple blocks of SD card
 * @return unsigned char - response byte
 */
unsigned char sd_write_multiple_blocks(unsigned long start_block, 
    unsigned long total_blocks)
{
  unsigned char response, data;
  unsigned int i, retry = 0;
  unsigned long block_counter = 0, size;

  response = sd_send_command(WRITE_MULTIPLE_BLOCKS, start_block); //write a Block command

  if(response != 0x00) return response; //check for SD status: 0x00 - OK (No flags set)

  SD_CS_ASSERT;

  while( block_counter < total_blocks )
  {
    i = 0;
    do
    {
      data = receive_byte();
      if(data == 0x08)  //'Back Space' key pressed
      { 
        if(i != 0)
        { 
          transmit_byte(data);
          transmit_byte(' '); 
          transmit_byte(data); 
          i--; 
          size--;
        } 
        continue;     
      }
      transmit_byte(data);
      buffer[i++] = data;
      if(data == 0x0d)
      {
        transmit_byte(0x0a);
        buffer[i++] = 0x0a;
      }
      if(i == 512) break;
    }
    while (data != '~');

    spi_transmit(0xfc); //Send start block token 0xfc (0x11111100)

    for(i = 0; i < 512; i++) //send 512 bytes data
      spi_transmit(buffer[i]);

    spi_transmit(0xff); //transmit dummy CRC (16-bit), CRC is ignored here
    spi_transmit(0xff);

    response = spi_receive();
    if((response & 0x1f) != 0x05) //response= 0xXXX0AAA1 ; AAA='010' - data accepted
    {                              //AAA='101'-data rejected due to CRC error
      SD_CS_DEASSERT;             //AAA='110'-data rejected due to write error
      return response;
    }

    while(!spi_receive()) //wait for SD card to complete writing and get idle
      if(retry++ > 0xfffe)
      {
        SD_CS_DEASSERT; 
        return 1;
      }

    spi_receive(); //extra 8 bits
    block_counter++;
  }

  spi_transmit(0xfd); //send 'stop transmission token'
  retry = 0;

  while(!spi_receive()) //wait for SD card to complete writing and get idle
    if(retry++ > 0xfffe)
    {
      SD_CS_DEASSERT; 
      return 1;
    }

  SD_CS_DEASSERT;
  spi_transmit(0xff); //just spend 8 clock cycle delay before reasserting the CS signal

  // re assertion of the CS signal is required to verify if card is still busy
  SD_CS_ASSERT; 

  while(!spi_receive()) //wait for SD card to complete writing and get idle
    if(retry++ > 0xfffe)
    {
      SD_CS_DEASSERT; 
      return 1;
    }

  SD_CS_DEASSERT;

  return 0;
}
Пример #29
0
int32_t  SDInit(void)
{
	int					i;
	int8_t				response;
//	volatile uint32_t	dly;


	if (registered == FALSE)  return  SDCARD_NOT_REG;

	SDType = SDTYPE_UNKNOWN;			// assume this fails
/*
 *  Begin initialization by sending CMD0 and waiting until SD card
 *  responds with In Idle Mode (0x01).  If the response is not 0x01
 *  within a reasonable amount of time, there is no SD card on the bus.
 */
	deselect();							// always make sure
	for (i=0; i<10; i++)				// send several clocks while card power stabilizes
		xchg(0xff);

	for (i=0; i<0x10; i++)
	{
		response = sd_send_command(SD_GO_IDLE, 0);	// send CMD0 - go to idle state
		if (response == 1)  break;
	}
	if (response != 1)
	{
		return  SDCARD_NO_DETECT;
	}

	sd_send_command(SD_SET_BLK_LEN, 512);		// always set block length (CMD6) to 512 bytes

	response = sd_send_command(SD_SEND_IF_COND, 0x1aa);	// probe to see if card is SDv2 (SDHC)
	if (response == 0x01)						// if card is SDHC...
	{
		for (i=0; i<4; i++)						// burn the 4-byte response (OCR)
		{
			xchg(0xff);
		}
		for (i=20000; i>0; i--)
		{
			response = sd_send_command(SD_ADV_INIT, 1UL<<30);
			if (response == 0)  break;
		}
		SDType = SDTYPE_SDHC;
	}
	else
	{
		response = sd_send_command(SD_READ_OCR, 0);
		if (response == 0x01)
		{
			for (i=0; i<4; i++)					// OCR is 4 bytes
			{
				xchg(0xff);					// burn the 4-byte response (OCR)
			}
			for (i=20000; i>0; i--)
			{
				response = sd_send_command(SD_INIT, 0);
				if (response == 0)  break;
//				for (dly=0; dly<1000; dly++)  ;		// spin-loop delay
			}
			sd_send_command(SD_SET_BLK_LEN, 512);
			SDType = SDTYPE_SD;
		}
	}

	sd_clock_and_release();					// always deselect and send final 8 clocks

/*
 *  At this point, the SD card has completed initialization.  The calling routine
 *  can now increase the SPI clock rate for the SD card to the maximum allowed by
 *  the SD card (typically, 20 MHz).
 */
	return  SDCARD_OK;					// if no power routine or turning off the card, call it good
}
Пример #30
0
/**
 * @brief initializes the SD/SDHC card in SPI mode
 * @return unsigned char - return 0 if no error and response byte otherwise
 */
unsigned char sd_init(void)
{
  unsigned char i, response, sd_version;
  unsigned int retry = 0;

  for(i = 0; i < 10; i++) {
    spi_transmit(0xff);   //80 clock pulses spent before sending the first command
  }
  SD_CS_ASSERT;
  
  do
  {
    response = sd_send_command(GO_IDLE_STATE, 0); //send 'reset & go idle' command
    retry++;
    if(retry > 0x20)
      return 1;   //time out, card not detected
  } while(response != 0x01);

  SD_CS_DEASSERT;

  spi_transmit (0xff);
  spi_transmit (0xff);

  retry = 0;

  sd_version = 2; //default set to SD compliance with ver2.x; 
  //this may change after checking the next command
  do
  {
    // Check power supply status, mendatory for SDHC card
    response = sd_send_command(SEND_IF_COND, 0x000001AA); 
    retry++;
    if(retry > 0xfe) 
    {
      sd_version = 1;
      card_type = 1;
      break;
    }
  }
  while(response != 0x01);

  retry = 0;

  do
  {
    // CMD55, must be sent before sending any ACMD command
    response = sd_send_command(APP_CMD,0); 
    response = sd_send_command(SD_SEND_OP_COND,0x40000000); // ACMD41
    PRINTF(dbgstr);
    retry++;
    if(retry > 0xfe)
    {
      return 2;  //time out, card initialization failed
    }
  }
  while(response != 0x00);


  retry = 0;
  sdhc_flag = 0;

  if (sd_version == 2)
  {
    do
    {
      response = sd_send_command(READ_OCR,0);
      retry++;
      if(retry > 0xfe)
      {
        card_type = 0;
        break;
      } //time out
    }
    while(response != 0x00);

    if(sdhc_flag == 1) card_type = 2;
    else card_type = 3;
  }

  return 0; //successful return
}