/* 注意:從函數的代碼上來看,所謂的drv這個參數,是用一個數字來代表文件硬件的類型,從其switch語句看 drv = ATA = 0:表示是IDE硬盤的一種接口 drv = MMC = 1: 表示的是MMC卡的接口,也就是SD卡 drv = USB = 2: 表示的是USB存儲設備的接口 從這裡看來,我們應該要選擇的是MMC接口,輸入參數必須為1*/ DSTATUS disk_initialize ( BYTE drv /* Physical drive nmuber (0..) */ ) { SD_Error Status; Status = SD_Init(); if (Status == SD_OK) { /*----------------- Read CSD/CID MSD registers ------------------*/ Status = SD_GetCardInfo(&SDCardInfo); } if (Status == SD_OK) { /*----------------- Select Card --------------------------------*/ Status = SD_SelectDeselect((u32) (SDCardInfo.RCA << 16)); } if (Status == SD_OK) { Status = SD_EnableWideBusOperation(SDIO_BusWide_1b); } /* Set Device Transfer Mode to DMA [設置傳輸模式為DMA方式]*/ if (Status == SD_OK) { Status = SD_SetDeviceMode(SD_INTERRUPT_MODE); } if(Status == SD_OK)return 0; else return STA_NOINIT; }
/******************************************************************************* * Function Name : MAL_Init * Description : Initializes the Media on the STM32 * Input : None * Output : None * Return : None *******************************************************************************/ uint16_t MAL_Init(uint8_t lun) { uint16_t status = MAL_OK; switch (lun) { case 0: #ifdef USE_STM3210E_EVAL Status = SD_Init(); Status = SD_GetCardInfo(&SDCardInfo); Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); Status = SD_SetDeviceMode(SD_DMA_MODE); #else MSD_Init(); #endif break; #ifdef USE_FSMC_NAND case 1: status = NAND_Init(); break; #endif default: return MAL_FAIL; } return status; }
DSTATUS disk_status ( BYTE pdrv /* Physical drive nmuber (0..) */ ) { switch (pdrv) { case SD_CARD: status = SD_GetCardInfo(&SDCardInfo); if(status != SD_OK) return STA_NOINIT; else return RES_OK; // case ATA : // result = ATA_disk_status(); // // // translate the reslut code here // // return stat; // // case MMC : // result = MMC_disk_status(); // // // translate the reslut code here // // return stat; // // case USB : // result = USB_disk_status(); // // // translate the reslut code here // // return stat; } return STA_NOINIT; }
void SDCard_Configuration(void) { int i; for( i=0;i<109500;i++);//延时等待电容充电5760,21900//为保证多一点的板子同时脸上的时候有效就设定的大一点21900*5 /*-------------------------- SD Init ----------------------------- */ Status = SD_Init(); //disk_initialize(0);//选择磁盘,这句包括上面的SD_Init();所以只需要这一次 if (Status == SD_OK) { /*----------------- Read CSD/CID MSD registers ------------------*/ Status = SD_GetCardInfo(&SDCardInfo); /*----------------- Select Card --------------------------------*/ Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); /* Set Device Transfer Mode to 4b */ Status = SD_EnableWideBusOperation(SDIO_BusWide_1b); /* Set Device Transfer Mode to DMA */ Status = SD_SetDeviceMode(SD_DMA_MODE); //Status = SD_SetDeviceMode(SD_POLLING_MODE); //Status = SD_SetDeviceMode(SD_INTERRUPT_MODE); } res = f_mount(0,&fs); if(res==FR_OK) printf("\n\rFile system mounted.\n\r"); else printf("Error mounting file system.\n\r"); }
/******************************************************************************* * Function Name : MAL_Init * Description : Initializes the Media on the STM32 * 功能 : 储存介质初始化 * Input : None * Output : None * Return : None *******************************************************************************/ uint16_t MAL_Init(uint8_t lun) { uint16_t status = MAL_OK; switch (lun) { case 0: Status = SD_Init(); Status = SD_GetCardInfo(&SDCardInfo); Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); Status = SD_SetDeviceMode(SD_DMA_MODE); if (Status == SD_OK) { // 从地址0开始读取512字节 Status = SD_ReadBlock(Buffer_Block_Rx, 0x00, BlockSize); } if (Status == SD_OK) { // 返回成功的话,串口输出SD卡测试成功信息 DbgPrintf(" \n SD SDIO-4bit模式 TF OK"); } break; default: return MAL_FAIL; } return status; }
/******************************************************************************* * Function Name : MAL_Init * Description : Initializes the Media on the STM32 * Input : None * Output : None * Return : None *******************************************************************************/ uint16_t MAL_Init(uint8_t lun) { uint16_t status = MAL_OK; switch (lun) { case 0: #ifdef USE_STM3210E_EVAL Status = SD_Init(); Status = SD_GetCardInfo(&SDCardInfo); Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); Status = SD_SetDeviceMode(SD_DMA_MODE); if (Status == SD_OK) { //Status = SD_ReadMultiBlocks(0x00, Buffer_MultiBlock_Rx, BlockSize, NumberOfBlocks1); // printf("\r\nSD SDIO-4bit模式 测试TF卡读写成功! \n "); } if (Status == SD_OK) { // Read block of 512 bytes from address 0 Status = SD_ReadBlock(0x00, Buffer_Block_Rx, BlockSize); } if (Status == SD_OK) { // Check the corectness of written dada printf("\r\nSD SDIO-4bit模式 测试TF卡读写成功! \n "); } #else MSD_Init(); #endif break; #ifdef USE_STM3210E_EVAL case 1: status = NAND_Init(); break; #endif default: return MAL_FAIL; } return status; }
DRESULT disk_ioctl ( BYTE drv, /* Physical drive number (0) */ BYTE ctrl, /* Control code */ void *buff /* Buffer to send/receive control data */ ) { DRESULT res; SD_CardInfo SDCardInfo; if (drv) return RES_PARERR; res = RES_ERROR; if (Stat & STA_NOINIT) return RES_NOTRDY; switch (ctrl) { case CTRL_SYNC : /* Make sure that no pending write process */ res = RES_OK; break; case GET_SECTOR_COUNT : /* Get number of sectors on the disk (DWORD) */ if(drv == 0) { SD_GetCardInfo(&SDCardInfo); *(DWORD*)buff = SDCardInfo.CardCapacity / 512; } res = RES_OK; break; case GET_SECTOR_SIZE : /* Get R/W sector size (WORD) */ *(WORD*)buff = 512; res = RES_OK; break; case GET_BLOCK_SIZE : /* Get erase block size in unit of sector (DWORD) */ if(drv == 0) *(DWORD*)buff = 512; else *(DWORD*)buff = 32; break; default: res = RES_PARERR; } return res; }
// Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); // Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); // if ( Status != SD_OK ) // return MAL_FAIL; // Status = SD_SetDeviceMode(SD_DMA_MODE); // if ( Status != SD_OK ) // return MAL_FAIL; // Mass_Memory_Size[0] = Mass_Block_Count[0] * Mass_Block_Size[0]; // LED1 = 0; // if (dis_mem == 0) //显示TF卡的容量 由于是周期性更新状态,所以,加了条件,只显示一次容量值 // { // printf("\r\n Micro SD卡的容量是 %d MBytes\n" ,SDCardInfo.CardCapacity); // dis_mem = 1; // } // return MAL_OK; // } // } // LED1 = 0; // return MAL_FAIL; //} u16 MAL_GetStatus (u8 lun) { uint32_t DeviceSizeMul = 0, NumberOfBlocks = 0; switch (lun) { case 0: if (dis_mem == 0) //显示TF卡的容量 由于是周期性更新状态,所以,加了条件,只显示一次容量值 { if (SD_Init() == SD_OK) { SD_GetCardInfo(&SDCardInfo); SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); DeviceSizeMul = (SDCardInfo.SD_csd.DeviceSizeMul + 2); if (SDCardInfo.CardType == SDIO_HIGH_CAPACITY_SD_CARD) { Mass_Block_Count[0] = (SDCardInfo.SD_csd.DeviceSize + 1) * 1024; } else { NumberOfBlocks = ((1 << (SDCardInfo.SD_csd.RdBlockLen)) / 512); Mass_Block_Count[0] = ((SDCardInfo.SD_csd.DeviceSize + 1) * (1 << DeviceSizeMul) << (NumberOfBlocks / 2)); } Mass_Block_Size[0] = 512; Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); if ( Status != SD_OK ) return MAL_FAIL; Status = SD_SetDeviceMode(SD_DMA_MODE); if ( Status != SD_OK ) return MAL_FAIL; Mass_Memory_Size[0] = Mass_Block_Count[0] * Mass_Block_Size[0]; LED1 = 0; // if (dis_mem == 0) //显示TF卡的容量 由于是周期性更新状态,所以,加了条件,只显示一次容量值 // { printf("\r\n Micro SD卡的容量是 %lld MBytes\n" , SDCardInfo.CardCapacity >> 20); dis_mem = 1; // } return MAL_OK; } dis_mem = 1; } return MAL_OK; case 1: return MAL_OK; case 2: return MAL_FAIL; default: return MAL_FAIL; }
/******************************************************************************* * Function Name : MAL_GetStatus * Description : Get status * Input : None * Output : None * Return : None *******************************************************************************/ uint16_t MAL_GetStatus (uint8_t lun) { // NAND_IDTypeDef NAND_ID; uint32_t DeviceSizeMul = 0, NumberOfBlocks = 0; if (lun == 0) { if (SD_Init() == SD_OK) { SD_GetCardInfo(&SDCardInfo); SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); DeviceSizeMul = (SDCardInfo.SD_csd.DeviceSizeMul + 2); if(SDCardInfo.CardType == SDIO_HIGH_CAPACITY_SD_CARD) { Mass_Block_Count[0] = (SDCardInfo.SD_csd.DeviceSize + 1) * 1024; } else { NumberOfBlocks = ((1 << (SDCardInfo.SD_csd.RdBlockLen)) / 512); Mass_Block_Count[0] = ((SDCardInfo.SD_csd.DeviceSize + 1) * (1 << DeviceSizeMul) << (NumberOfBlocks/2)); } Mass_Block_Size[0] = 512; Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); if ( Status != SD_OK ) { return MAL_FAIL; } Mass_Memory_Size[0] = Mass_Block_Count[0] * Mass_Block_Size[0]; return MAL_OK; } } // else // { // FSMC_NAND_ReadID(&NAND_ID); // if (NAND_ID.Device_ID != 0 ) // { // /* only one zone is used */ // Mass_Block_Count[1] = NAND_ZONE_SIZE * NAND_BLOCK_SIZE * NAND_MAX_ZONE ; // Mass_Block_Size[1] = NAND_PAGE_SIZE; // Mass_Memory_Size[1] = (Mass_Block_Count[1] * Mass_Block_Size[1]); // return MAL_OK; // } // } return MAL_FAIL; }
SD_Error SD_PrintInfo( void ) { SD_Error SDError; const char *CardTypes[] = { "STD_CAPACITY_SD_CARD_V1_1", "STD_CAPACITY_SD_CARD_V2_0", "HIGH_CAPACITY_SD_CARD", "MULTIMEDIA_CARD", "SECURE_DIGITAL_IO_CARD", "HIGH_SPEED_MULTIMEDIA_CARD", "SECURE_DIGITAL_IO_COMBO_CARD", "HIGH_CAPACITY_MMC_CARD" }; printf("Card info:\n\r"); if ((SDError = SD_GetCardInfo(&SDCardInfo)) != SD_OK) { printf("\tConfigure SD card - FAILED. SD_GetCardInfo()\n\r"); SD_print_error(SDError); return SDError; } if(SDError == SD_OK) { SD_PrintState(SD_GetState()); printf("\tBlockSize: %d\n\r", SDCardInfo.CardBlockSize); printf("\tCapacity: %"PRIu64" Byte", SDCardInfo.CardCapacity); printf(" (%i MiB)\n\r", (uint32_t)( SDCardInfo.CardCapacity/1024/1024)); printf("\tType: %s\n\r", CardTypes[SDCardInfo.CardType]); printf("\tRCA: %d\n\r", SDCardInfo.RCA); printf("\tCSD.MaxBusClkFrec: %d\n\r", SDCardInfo.SD_csd.MaxBusClkFrec); printf("\tCSD.DeviceSize: %d\n\r", SDCardInfo.SD_csd.DeviceSize); printf("\tCSD.DeviceSizeMul: %d\n\r", SDCardInfo.SD_csd.DeviceSizeMul); printf("\tCSD.RdBlockLen: %d\n\r", SDCardInfo.SD_csd.RdBlockLen); printf("\tCSD.MaxWrBlockLen: %d\n\r", SDCardInfo.SD_csd.MaxWrBlockLen); printf("\tCID:\n\r"); printf("\t\tManufacturerID: %u\n\r", SDCardInfo.SD_cid.ManufacturerID); printf("\t\tProdName1: %u\n\r", SDCardInfo.SD_cid.ProdName1); printf("\t\tProdName2: %u\n\r", SDCardInfo.SD_cid.ProdName2); printf("\t\tProdRev: %u\n\r", SDCardInfo.SD_cid.ProdRev); printf("\t\tProdSN: %u\n\r", SDCardInfo.SD_cid.ProdSN); printf("\t\tManufactDate: %u\n\r", SDCardInfo.SD_cid.ManufactDate); printf("\t\tCID_CRC: %u\n\r", SDCardInfo.SD_cid.CID_CRC); SD_PrintState(SD_GetState()); } return SD_OK; }
/******************************************************************************* * Function Name : MAL_GetStatus * Description : Get status * Input : None * Output : None * Return : None *******************************************************************************/ uint16_t MAL_GetStatus (uint8_t lun) { ; uint32_t DeviceSizeMul = 0, NumberOfBlocks = 0; if (lun == 0) { if (SD_Init() == SD_OK) { SD_GetCardInfo(&SDCardInfo); SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); DeviceSizeMul = (SDCardInfo.SD_csd.DeviceSizeMul + 2); if(SDCardInfo.CardType == SDIO_HIGH_CAPACITY_SD_CARD) { Mass_Block_Count[0] = (SDCardInfo.SD_csd.DeviceSize + 1) * 1024; } else { NumberOfBlocks = ((1 << (SDCardInfo.SD_csd.RdBlockLen)) / 512); Mass_Block_Count[0] = ((SDCardInfo.SD_csd.DeviceSize + 1) * (1 << DeviceSizeMul) << (NumberOfBlocks/2)); } Mass_Block_Size[0] = 512; Mass_Memory_Size[0] = Mass_Block_Count[0] * Mass_Block_Size[0]; GPIO_SetBits(USB_LED_PORT, GPIO_Pin_7); Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); if ( Status != SD_OK ) { return MAL_FAIL; } Status = SD_SetDeviceMode(SD_DMA_MODE); if ( Status != SD_OK ) { return MAL_FAIL; } return MAL_OK; } } else { return MAL_OK; } GPIO_ResetBits(USB_LED_PORT, GPIO_Pin_7); return MAL_FAIL; }
//初始化SD卡 //返回值:错误代码;(0,无错误) SD_Error SD_Init(void) { SD_Error errorstatus=SD_OK; u8 clkdiv=0; //SDIO IO口初始化 RCC->AHB1ENR|=1<<2; //使能PORTC时钟 RCC->AHB1ENR|=1<<3; //使能PORTD时钟 RCC->AHB1ENR|=1<<22; //DMA2时钟使能 RCC->APB2ENR|=1<<11; //SDIO时钟使能 RCC->APB2RSTR|=1<<11; //SDIO复位 GPIO_Set(GPIOC,0X1F<<8,GPIO_MODE_AF,GPIO_OTYPE_PP,GPIO_SPEED_50M,GPIO_PUPD_PU); //PC8,9,10,11,12复用功能输出 GPIO_Set(GPIOD,1<<2,GPIO_MODE_AF,GPIO_OTYPE_PP,GPIO_SPEED_50M,GPIO_PUPD_PU); //PD2复用功能输出 GPIO_AF_Set(GPIOC,8,12); //PC8,AF12 GPIO_AF_Set(GPIOC,9,12); //PC9,AF12 GPIO_AF_Set(GPIOC,10,12); //PC10,AF12 GPIO_AF_Set(GPIOC,11,12); //PC11,AF12 GPIO_AF_Set(GPIOC,12,12); //PC12,AF12 GPIO_AF_Set(GPIOD,2,12); //PD2,AF12 RCC->APB2RSTR&=~(1<<11); //SDIO结束复位 //SDIO外设寄存器设置为默认值 SDIO->POWER=0x00000000; SDIO->CLKCR=0x00000000; SDIO->ARG=0x00000000; SDIO->CMD=0x00000000; SDIO->DTIMER=0x00000000; SDIO->DLEN=0x00000000; SDIO->DCTRL=0x00000000; SDIO->ICR=0x00C007FF; SDIO->MASK=0x00000000; MY_NVIC_Init(0,0,SDIO_IRQn,2); //SDIO中断配置 errorstatus=SD_PowerON(); //SD卡上电 if(errorstatus==SD_OK)errorstatus=SD_InitializeCards(); //初始化SD卡 if(errorstatus==SD_OK)errorstatus=SD_GetCardInfo(&SDCardInfo); //获取卡信息 if(errorstatus==SD_OK)errorstatus=SD_SelectDeselect((u32)(SDCardInfo.RCA<<16));//选中SD卡 if(errorstatus==SD_OK)errorstatus=SD_EnableWideBusOperation(1); //4位宽度,如果是MMC卡,则不能用4位模式 if((errorstatus==SD_OK)||(SDIO_MULTIMEDIA_CARD==CardType)) { if(SDCardInfo.CardType==SDIO_STD_CAPACITY_SD_CARD_V1_1||SDCardInfo.CardType==SDIO_STD_CAPACITY_SD_CARD_V2_0) { clkdiv=SDIO_TRANSFER_CLK_DIV+2; //V1.1/V2.0卡,设置最高48/4=12Mhz }else clkdiv=SDIO_TRANSFER_CLK_DIV; //SDHC等其他卡,设置最高48/2=24Mhz SDIO_Clock_Set(clkdiv); //设置时钟频率,SDIO时钟计算公式:SDIO_CK时钟=SDIOCLK/[clkdiv+2];其中,SDIOCLK固定为48Mhz //errorstatus=SD_SetDeviceMode(SD_DMA_MODE); //设置为DMA模式 errorstatus=SD_SetDeviceMode(SD_POLLING_MODE);//设置为查询模式 } return errorstatus; }
/**************************************************************************** * 名 称:void SD_TEST(void) * 功 能:SD卡测试函数 * 入口参数:无 * 出口参数:无 * 说 明: * 调用方法:无 ****************************************************************************/ void SD_TEST(void){ Status = SD_Init(); Status = SD_GetCardInfo(&SDCardInfo); Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); Status = SD_SetDeviceMode(SD_DMA_MODE); if (Status == SD_OK) { // 从地址0开始读取512字节 Status = SD_ReadBlock(Buffer_Block_Rx, 0x00, 512); } if (Status == SD_OK) { // 返回成功的话,串口输出SD卡测试成功信息 USART_OUT(USART1,"\r\nSD SDIO-4bit模式 测试TF卡成功! \n "); } }
static int check_sdcard(void) { unsigned int DeviceSizeMul = 0, NumberOfBlocks = 0; SD_Error Status; if (SD_Init() == SD_OK) { SD_GetCardInfo(&SDIO_Info); SD_SelectDeselect((unsigned int) (SDIO_Info.RCA << 16)); DeviceSizeMul = (SDIO_Info.SD_csd.DeviceSizeMul + 2); if(SDIO_Info.CardType == SDIO_HIGH_CAPACITY_SD_CARD) { SDIO_Block_Count = (SDIO_Info.SD_csd.DeviceSize + 1) * 1024; SDIO_Block_Size = 1; } else { NumberOfBlocks = ((1 << (SDIO_Info.SD_csd.RdBlockLen)) / 512); SDIO_Block_Count = ((SDIO_Info.SD_csd.DeviceSize + 1) * (1 << DeviceSizeMul) << (NumberOfBlocks/2)); SDIO_Block_Size = 512; } Status = SD_SelectDeselect((unsigned int) (SDIO_Info.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); if ( Status != SD_OK ) { return -1; } Status = SD_SetDeviceMode(SD_DMA_MODE); if ( Status != SD_OK ) { return -1; } SDIO_Memory_Size = SDIO_Block_Count * SDIO_Block_Size; if( SDIO_Memory_Size >= (2*1024 * 1024 * 1024)) // * 512)) { return 0; // 卡大于2G } else return -1; } return -1; }
DRESULT disk_ioctl ( BYTE pdrv, /* Physical drive nmuber (0..) */ BYTE cmd, /* Control code */ void *buff /* Buffer to send/receive control data */ ) { DRESULT res; if (pdrv) { return RES_PARERR; } //FATFS目前版本仅需处理CTRL_SYNC,GET_SECTOR_COUNT,GET_BLOCK_SIZ三个命令 switch(cmd) { case CTRL_SYNC: SPI_CS_Assert(); if(SD_ResetSD() == SD_NO_ERR) { res = RES_OK; } else { res = RES_ERROR; } SPI_CS_Deassert(); break; case GET_BLOCK_SIZE: *(WORD*)buff = 512; res = RES_OK; break; case GET_SECTOR_COUNT: *(DWORD*)buff = SD_GetCardInfo(); res = RES_OK; break; default: res = RES_PARERR; break; } return res; }
static bool InitMemoryInfo() { SD_CardInfo card_info; if (SD_Init() != SD_OK) { ERR_MSG("Failed to init card.", 0); return false; } if (SD_GetCardInfo( &card_info ) != SD_OK){ ERR_MSG("Failed to get card info.", 0); return false; } Mass_Block_Count = card_info.CardCapacity / card_info.CardBlockSize; Mass_Block_Size = card_info.CardBlockSize; Mass_Memory_Size = card_info.CardCapacity; }
uint16_t MAL_GetStatus (uint8_t lun) { uint32_t DeviceSizeMul = 0, NumberOfBlocks = 0; uint64_t dwDevSize; /* nemui */ if (lun == 0) { if (SD_Init() == SD_OK) { SD_GetCardInfo(&SDCardInfo); SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); DeviceSizeMul = (SDCardInfo.SD_csd.DeviceSizeMul + 2); if(SDCardInfo.CardType == SDIO_HIGH_CAPACITY_SD_CARD) { /* nemui */ dwDevSize = (uint64_t)(SDCardInfo.SD_csd.DeviceSize + 1) * 512 * 1024; /* nemui calculate highest LBA */ Mass_Block_Count[0] = (dwDevSize - 1) / 512; } else { NumberOfBlocks = ((1 << (SDCardInfo.SD_csd.RdBlockLen)) / 512); Mass_Block_Count[0] = ((SDCardInfo.SD_csd.DeviceSize + 1) * (1 << DeviceSizeMul) << (NumberOfBlocks/2)); } Mass_Block_Size[0] = 512; Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); if ( Status != SD_OK ) { return MAL_FAIL; } Mass_Memory_Size[0] = Mass_Block_Count[0] * Mass_Block_Size[0]; return MAL_OK; } } return MAL_FAIL; }
/* Inidialize a Drive */ DSTATUS disk_initialize ( BYTE drv /* Physical drive nmuber (0..) */ ) { //printf("Disk init: %x\r\n", drv); SD_Error Status; if(drv==0) { //FIXME: DMA stuff - fix later... // NVIC_InitTypeDef NVIC_InitStructure; // NVIC_InitStructure.NVIC_IRQChannel = SDIO_IRQn; // NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0; // NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; // NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; // NVIC_Init(&NVIC_InitStructure); // NVIC_InitStructure.NVIC_IRQChannel = SD_SDIO_DMA_IRQn; // NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1; // NVIC_Init(&NVIC_InitStructure); Status = SD_Init(); if(Status != SD_OK) return STA_NODISK; //assume no disk if initialization failed else { Status = SD_GetCardInfo(&SDCardInfo); if(Status != SD_OK) return STA_NOINIT; Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); if(Status != SD_OK) return STA_NOINIT; return 0; } } else return STA_NOINIT; }
/* Miscellaneous Functions */ DRESULT disk_ioctl ( BYTE drv, /* Physical drive nmuber (0..) */ BYTE ctrl, /* Control code */ void *buff /* Buffer to send/receive control data */ ) { //printf("Disk ioctl: %x, Disk: %x\r\n", ctrl, drv); u32 x, y, z; DRESULT res; if (drv==0) { switch(ctrl) { case CTRL_SYNC: res = RES_OK; break; case GET_BLOCK_SIZE: *(WORD*)buff = BlockSize; res = RES_OK; break; case GET_SECTOR_COUNT: if (SD_GetCardInfo(&SDCardInfo)==SD_OK) { *(DWORD*)buff = SDCardInfo.CardCapacity / 512; res = RES_OK; } else res = RES_ERROR ; break; default: res = RES_PARERR; } return res; } else return RES_ERROR; }
/******************************************************************************* * Function Name : MAL_Init * Description : Initializes the Media on the STM32 * Input : None * Output : None * Return : None *******************************************************************************/ uint16_t MAL_Init(uint8_t lun) { uint16_t status = MAL_OK; switch (lun) { case 0: Status = SD_Init(); Status = SD_GetCardInfo(&SDCardInfo); Status = SD_SelectDeselect((u32) (SDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); Status = SD_SetDeviceMode(SD_DMA_MODE); break; case 1: status = NAND_Init(); break; default: return MAL_FAIL; } return status; }
DRESULT disk_ioctl ( BYTE drv, /* Physical drive number (0..) */ BYTE ctrl, /* Control code */ void *buff /* Buffer to send/receive control data */ ) { SD_CardInfo cardinfo; DRESULT res; if ( drv ) return RES_PARERR; switch( ctrl ) { case CTRL_SYNC: // res = ( SD_WaitReady() == SD_RESPONSE_NO_ERROR ) ? RES_OK : RES_ERROR res = RES_OK; break; case GET_BLOCK_SIZE: *(WORD*)buff = _MAX_SS; res = RES_OK; break; case GET_SECTOR_COUNT: if ( SD_GetCardInfo( &cardinfo ) != SD_RESPONSE_NO_ERROR ) res = RES_ERROR; else { *(DWORD*)buff = cardinfo.CardCapacity; res = ( *(DWORD*)buff > 0 ) ? RES_OK : RES_PARERR; } break; case CTRL_ERASE_SECTOR: res = ( SD_SectorsErase( ((DWORD*)buff)[ 0 ], ((DWORD*)buff)[ 1 ] ) == SD_RESPONSE_NO_ERROR ) ? RES_OK : RES_PARERR; break; default: res = RES_PARERR; break; } return res; }
/** * @brief return medium capacity and block size * @param lun : logical unit number * @param block_num : number of physical block * @param block_size : size of a physical block * @retval Status */ int8_t STORAGE_GetCapacity (uint8_t lun, uint32_t *block_num, uint32_t *block_size) { #ifdef USE_STM3210C_EVAL SD_CardInfo SDCardInfo; SD_GetCardInfo(&SDCardInfo); #else if(SD_GetStatus() != 0 ) { return (-1); } #endif *block_size = 512; *block_num = SDCardInfo.CardCapacity / 512; return (0); }
/******************************************************************************* * Function Name : MAL_GetStatus * Description : Get status * Input : None * Output : None * Return : None *******************************************************************************/ uint16_t MAL_GetStatus (uint8_t lun) { NAND_IDTypeDef NAND_ID; u32 DeviceSizeMul = 0, NumberOfBlocks = 0; if (lun == 0) { if (SD_Init() == SD_OK) { SD_GetCardInfo(&SDCardInfo); SD_SelectDeselect((u32) (SDCardInfo.RCA << 16)); DeviceSizeMul = (SDCardInfo.SD_csd.DeviceSizeMul + 2); if(SDCardInfo.CardType == SDIO_HIGH_CAPACITY_SD_CARD) { Mass_Block_Count[0] = (SDCardInfo.SD_csd.DeviceSize + 1) * 1024; } else { NumberOfBlocks = ((1 << (SDCardInfo.SD_csd.RdBlockLen)) / 512); Mass_Block_Count[0] = ((SDCardInfo.SD_csd.DeviceSize + 1) * (1 << DeviceSizeMul) << (NumberOfBlocks/2)); } Mass_Block_Size[0] = 512; Status = SD_SelectDeselect((u32) (SDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); if ( Status != SD_OK ) return MAL_FAIL; Status = SD_SetDeviceMode(SD_DMA_MODE); if ( Status != SD_OK ) return MAL_FAIL; } } else { FSMC_NAND_ReadID(&NAND_ID); if (NAND_ID.Device_ID != 0 ) { //printf("\r\n Device ID : %02X %02X" ,NAND_ID.Maker_ID,NAND_ID.Device_ID ); /* only one zone is used */ Mass_Block_Count[1] = NAND_ZONE_SIZE * NAND_BLOCK_SIZE * NAND_MAX_ZONE ; Mass_Block_Size[1] = NAND_PAGE_SIZE; Mass_Memory_Size[1] = (Mass_Block_Count[1] * Mass_Block_Size[1]); return MAL_OK; } } return MAL_FAIL; }
//========================================================================================= DRESULT FATFS_SD_SDIO_disk_ioctl(BYTE cmd, void *buff) { DRESULT res = RES_ERROR; HAL_SD_CardInfoTypedef CardInfo; /* Check if init OK */ if (Stat & STA_NOINIT) return RES_NOTRDY; switch (cmd) { /* Make sure that no pending write process */ case CTRL_SYNC : res = RES_OK; break; /* Get number of sectors on the disk (DWORD) */ case GET_SECTOR_COUNT : SD_GetCardInfo(&CardInfo); *(DWORD *)buff = CardInfo.CardCapacity / BLOCK_SIZE; res = RES_OK; break; /* Get R/W sector size (WORD) */ case GET_SECTOR_SIZE : *(WORD *)buff = BLOCK_SIZE; res = RES_OK; break; /* Get erase block size in unit of sector (DWORD) */ case GET_BLOCK_SIZE : *(DWORD*)buff = BLOCK_SIZE; break; default: res = RES_PARERR; } return res; }
static void FileSystem_Init(void) { static FATFS fileSystem; SD_Error Status = SD_OK; SD_CardInfo SDCardInfo; Delay_ms(1000); for(int i=0;i<3;i++) { if((Status = SD_Init()) != SD_OK){ DBG_MSG("SD Card Init Failed! Retrying...", 0); } else { break; } } if(Status != SD_OK) { ERR_MSG("No SD card found!", 0); return; } Status = SD_GetCardInfo( &SDCardInfo ); if(Status != SD_OK) return; DBG_MSG("CardCapacity: %dM, Block Size %d", (int)(SDCardInfo.CardCapacity/1024/1024), (int)SDCardInfo.CardBlockSize); DBG_MSG("CardType: %d", (int)SDCardInfo.CardType); if(f_mount(0, &fileSystem) != FR_OK){ ERR_MSG("Failed to mount SD card!", 0); return; } DBG_MSG("SD Card Init OK!", 0); }
void SD_test( void ) { static uint32_t sdioclk = ((HSE_VALUE/8)*336)/7; SD_Error SDError; printf("Configure SD card...\n\r"); print_RCC_Clocks(); printf("SDIOCLK = ((HSE_VALUE / PLL_M) * PLL_N) / PLLQ = %u\n\r", sdioclk); printf("For init: SDIO_CK = SDIOCLK / (SDIO_INIT_CLK_DIV + 2) = %i\n",(sdioclk/(SDIO_INIT_CLK_DIV + 2))); printf("For transfer: SDIO_CK = SDIOCLK / (SDIO_TRANSFER_CLK_DIV + 2) = %i\n",(sdioclk/(SDIO_TRANSFER_CLK_DIV + 2))); #ifdef SD_DMA_MODE printf("SD_DMA_MODE\n\r"); #endif #ifdef SD_POLLING_MODE printf("SD_POLLING_MODE\n\r"); #endif if ((SDError = SD_Init()) != SD_OK) { printf("\tConfigure SD card - FAILED. SD_Init()\n\r"); SD_print_error(SDError); } SD_PrintInfo(); SD_PrintCardStatus(); printf("Configure SD card - OK.\n\r"); if ((SDError = SD_GetCardInfo(&SDCardInfo)) != SD_OK) { printf("\tConfigure SD card - FAILED. SD_GetCardInfo()\n\r"); SD_print_error(SDError); } printf("Run print all SD in Hex. %u bloks.\n\r",SDCardInfo.SD_csd.DeviceSize); //print_all_SD(SDCardInfo.SD_csd.DeviceSize); }
uint8_t BSP_TEST_SDIO(void) { uint8_t t_status = 0; /*-------------------------- SD Init ----------------------------- */ BSP_SDCARD_ENABLE(); Status = SD_Init(); if (Status == SD_OK) { /*----------------- Read CSD/CID MSD registers ------------------*/ Status = SD_GetCardInfo(&SDCardInfo); } if (Status == SD_OK) { /*----------------- Select Card --------------------------------*/ Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); } if (Status == SD_OK) { Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); } /*------------------- Block Erase -------------------------------*/ if (Status == SD_OK) { /* Erase NumberOfBlocks Blocks of WRITE_BL_LEN(512 Bytes) */ Status = SD_Erase(0x00, (SDIO_BLOCK_SIZE * SDIO_NB_BLOCK)); } /* Set Device Transfer Mode to DMA */ if (Status == SD_OK) { Status = SD_SetDeviceMode(SD_DMA_MODE); } if (Status == SD_OK) { Status = SD_ReadMultiBlocks(0x00, Buffer_MultiBlock_Rx, SDIO_BLOCK_SIZE, SDIO_NB_BLOCK); } if (Status == SD_OK) { t_status = eBuffercmp(Buffer_MultiBlock_Rx, SDIO_MULTIWSIZE); } /*------------------- Block Read/Write --------------------------*/ /* Fill the buffer to send */ Fill_Buffer(Buffer_Block_Tx, SDIO_BUFFERW_SIZE, 0xFFFF); if (Status == SD_OK) { /* Write block of 512 bytes on address 0 */ Status = SD_WriteBlock(0x00, Buffer_Block_Tx, SDIO_BLOCK_SIZE); } if (Status == SD_OK) { /* Read block of 512 bytes from address 0 */ Status = SD_ReadBlock(0x00, Buffer_Block_Rx, SDIO_BLOCK_SIZE); } if (Status == SD_OK) { /* Check the corectness of written dada */ t_status &= Buffercmp(Buffer_Block_Tx, Buffer_Block_Rx, SDIO_BUFFERW_SIZE); } BSP_SDCARD_DISABLE(); return t_status; }
/******************************************************************************* * Function Name : MAL_GetStatus * Description : Get status * Input : None * Output : None * Return : None *******************************************************************************/ uint16_t MAL_GetStatus (uint8_t lun) { #ifdef USE_STM3210E_EVAL NAND_IDTypeDef NAND_ID; uint32_t DeviceSizeMul = 0, NumberOfBlocks = 0; #else SD_CSD SD_csd; uint32_t DeviceSizeMul = 0; #endif /* USE_STM3210E_EVAL */ #ifdef USE_STM32L152D_EVAL uint32_t NumberOfBlocks = 0; #endif if (lun == 0) { #if defined (USE_STM3210E_EVAL) || defined(USE_STM32L152D_EVAL) if (SD_Init() == SD_OK) { SD_GetCardInfo(&mSDCardInfo); SD_SelectDeselect((uint32_t) (mSDCardInfo.RCA << 16)); DeviceSizeMul = (mSDCardInfo.SD_csd.DeviceSizeMul + 2); if(mSDCardInfo.CardType == SDIO_HIGH_CAPACITY_SD_CARD) { Mass_Block_Count[0] = (mSDCardInfo.SD_csd.DeviceSize + 1) * 1024; } else { NumberOfBlocks = ((1 << (mSDCardInfo.SD_csd.RdBlockLen)) / 512); Mass_Block_Count[0] = ((mSDCardInfo.SD_csd.DeviceSize + 1) * (1 << DeviceSizeMul) << (NumberOfBlocks/2)); } Mass_Block_Size[0] = 512; Status = SD_SelectDeselect((uint32_t) (mSDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); if ( Status != SD_OK ) { return MAL_FAIL; } #else uint32_t temp_block_mul = 0; SD_GetCSDRegister(&SD_csd); DeviceSizeMul = SD_csd.DeviceSizeMul + 2; temp_block_mul = (1 << SD_csd.RdBlockLen)/ 512; Mass_Block_Count[0] = ((SD_csd.DeviceSize + 1) * (1 << (DeviceSizeMul))) * temp_block_mul; Mass_Block_Size[0] = 512; Mass_Memory_Size[0] = (Mass_Block_Count[0] * Mass_Block_Size[0]); #endif /* USE_STM3210E_EVAL */ Mass_Memory_Size[0] = Mass_Block_Count[0] * Mass_Block_Size[0]; LED_On1(); return MAL_OK; #if defined (USE_STM3210E_EVAL) || defined(USE_STM32L152D_EVAL) } #endif /* USE_STM3210E_EVAL */ } #ifdef USE_STM3210E_EVAL else { FSMC_NAND_ReadID(&NAND_ID); if (NAND_ID.Device_ID != 0 ) { /* only one zone is used */ Mass_Block_Count[1] = NAND_ZONE_SIZE * NAND_BLOCK_SIZE * NAND_MAX_ZONE ; Mass_Block_Size[1] = NAND_PAGE_SIZE; Mass_Memory_Size[1] = (Mass_Block_Count[1] * Mass_Block_Size[1]); return MAL_OK; } } #endif /* USE_STM3210E_EVAL */ LED_On1(); return MAL_FAIL; }
/******************************************************************************* * Function Name : MAL_GetStatus * Description : Get status * Input : None * Output : None * Return : None *******************************************************************************/ uint16_t MAL_GetStatus (uint8_t lun) { #ifdef USE_STM3210E_EVAL uint32_t DeviceSizeMul = 0, NumberOfBlocks = 0; #else uint32_t temp_block_mul = 0; sMSD_CSD MSD_csd; uint32_t DeviceSizeMul = 0; #endif #ifdef USE_FSMC_NAND NAND_IDTypeDef NAND_ID; #endif if (lun == 0) { #ifdef USE_STM3210E_EVAL if (SD_Init() == SD_OK) { SD_GetCardInfo(&SDCardInfo); SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); DeviceSizeMul = (SDCardInfo.SD_csd.DeviceSizeMul + 2); if(SDCardInfo.CardType == SDIO_HIGH_CAPACITY_SD_CARD) { Mass_Block_Count[0] = (SDCardInfo.SD_csd.DeviceSize + 1) * 1024; } else { NumberOfBlocks = ((1 << (SDCardInfo.SD_csd.RdBlockLen)) / 512); Mass_Block_Count[0] = ((SDCardInfo.SD_csd.DeviceSize + 1) * (1 << DeviceSizeMul) << (NumberOfBlocks/2)); } Mass_Block_Size[0] = 512; Status = SD_SelectDeselect((uint32_t) (SDCardInfo.RCA << 16)); Status = SD_EnableWideBusOperation(SDIO_BusWide_4b); if ( Status != SD_OK ) { return MAL_FAIL; } Status = SD_SetDeviceMode(SD_DMA_MODE); if ( Status != SD_OK ) { return MAL_FAIL; } #else MSD_GetCSDRegister(&MSD_csd); DeviceSizeMul = MSD_csd.DeviceSizeMul + 2; temp_block_mul = (1 << MSD_csd.RdBlockLen)/ 512; Mass_Block_Count[0] = ((MSD_csd.DeviceSize + 1) * (1 << (DeviceSizeMul))) * temp_block_mul; Mass_Block_Size[0] = 512; Mass_Memory_Size[0] = (Mass_Block_Count[0] * Mass_Block_Size[0]); #endif Mass_Memory_Size[0] = Mass_Block_Count[0] * Mass_Block_Size[0]; GPIO_SetBits(USB_LED_PORT, GPIO_Pin_7); return MAL_OK; #ifdef USE_STM3210E_EVAL } #endif } #ifdef USE_FSMC_NAND else { FSMC_NAND_ReadID(&NAND_ID); if (NAND_ID.Device_ID != 0 ) { //only one zone is used Mass_Block_Count[1] = NAND_ZONE_SIZE * NAND_BLOCK_SIZE * NAND_MAX_ZONE ; Mass_Block_Size[1] = NAND_PAGE_SIZE; Mass_Memory_Size[1] = (Mass_Block_Count[1] * Mass_Block_Size[1]); return MAL_OK; } } #endif GPIO_ResetBits(USB_LED_PORT, GPIO_Pin_7); return MAL_FAIL; }
DRESULT disk_ioctl ( BYTE drv, /* Physical drive nmuber (0..) */ BYTE ctrl, /* Control code */ void *buff /* Buffer to send/receive control data */ ) { //return RES_OK; // 0 DRESULT res ; SD_CardInfo card; if(drv) return RES_PARERR; switch(ctrl) { case CTRL_SYNC: SD_WaitWriteOperation(); while(SD_GetStatus() != SD_TRANSFER_OK); res = RES_OK; break; case GET_SECTOR_SIZE: *(WORD*)buff = 512; res = RES_OK; break; case GET_SECTOR_COUNT: SD_GetCardInfo(&card); *(DWORD*)buff=(uint32_t)((card.CardCapacity)>>9); // *(DWORD*)buff= (uint32_t)(GetCapacity()>>9); res = RES_OK; break; default: break; } return res; /* 下面注释掉的部分为FATFS自带的 */ // DRESULT res; // int result; // // switch (drv) { // case ATA : // // pre-process here // // //result = ATA_disk_ioctl(ctrl, buff); // // post-process here // // return res; // // case MMC : // // pre-process here // // result = MMC_disk_ioctl(ctrl, buff); // // post-process here // // return res; // // case USB : // // pre-process here // // result = USB_disk_ioctl(ctrl, buff); // // post-process here // // return res; // } // return RES_PARERR; }