@@ -141,54 +141,46 @@ uint64_t sdcard_get_capacity_in_bytes(void) {
141141 return cardinfo .CardCapacity ;
142142}
143143
144- bool sdcard_read_blocks (uint8_t * dest , uint32_t block_num , uint32_t num_blocks ) {
144+ mp_uint_t sdcard_read_blocks (uint8_t * dest , uint32_t block_num , uint32_t num_blocks ) {
145145 // check that dest pointer is aligned on a 4-byte boundary
146146 if (((uint32_t )dest & 3 ) != 0 ) {
147- return false ;
147+ return SD_ERROR ;
148148 }
149149
150150 // check that SD card is initialised
151151 if (sd_handle .Instance == NULL ) {
152- return false ;
152+ return SD_ERROR ;
153153 }
154154
155155 // We must disable IRQs because the SDIO peripheral has a small FIFO
156156 // buffer and we can't let it fill up in the middle of a read.
157157 // This will not be needed when SD uses DMA for transfer.
158- __disable_irq ();
159- HAL_SD_ErrorTypedef err = HAL_SD_ReadBlocks (& sd_handle , (uint32_t * )dest , ( uint64_t ) block_num * SDCARD_BLOCK_SIZE , SDCARD_BLOCK_SIZE , num_blocks );
160- __enable_irq ( );
158+ mp_uint_t atomic_state = MICROPY_BEGIN_ATOMIC_SECTION ();
159+ HAL_SD_ErrorTypedef err = HAL_SD_ReadBlocks_BlockNumber (& sd_handle , (uint32_t * )dest , block_num , SDCARD_BLOCK_SIZE , num_blocks );
160+ MICROPY_END_ATOMIC_SECTION ( atomic_state );
161161
162- if (err != SD_OK ) {
163- return false;
164- }
165-
166- return true;
162+ return err ;
167163}
168164
169- bool sdcard_write_blocks (const uint8_t * src , uint32_t block_num , uint32_t num_blocks ) {
165+ mp_uint_t sdcard_write_blocks (const uint8_t * src , uint32_t block_num , uint32_t num_blocks ) {
170166 // check that src pointer is aligned on a 4-byte boundary
171167 if (((uint32_t )src & 3 ) != 0 ) {
172- return false ;
168+ return SD_ERROR ;
173169 }
174170
175171 // check that SD card is initialised
176172 if (sd_handle .Instance == NULL ) {
177- return false ;
173+ return SD_ERROR ;
178174 }
179175
180176 // We must disable IRQs because the SDIO peripheral has a small FIFO
181177 // buffer and we can't let it drain to empty in the middle of a write.
182178 // This will not be needed when SD uses DMA for transfer.
183- __disable_irq ();
184- HAL_SD_ErrorTypedef err = HAL_SD_WriteBlocks (& sd_handle , (uint32_t * )src , (uint64_t )block_num * SDCARD_BLOCK_SIZE , SDCARD_BLOCK_SIZE , num_blocks );
185- __enable_irq ();
186-
187- if (err != SD_OK ) {
188- return false;
189- }
179+ mp_uint_t atomic_state = MICROPY_BEGIN_ATOMIC_SECTION ();
180+ HAL_SD_ErrorTypedef err = HAL_SD_WriteBlocks_BlockNumber (& sd_handle , (uint32_t * )src , block_num , SDCARD_BLOCK_SIZE , num_blocks );
181+ MICROPY_END_ATOMIC_SECTION (atomic_state );
190182
191- return true ;
183+ return err ;
192184}
193185
194186#if 0
@@ -205,7 +197,7 @@ bool sdcard_read_blocks_dma(uint8_t *dest, uint32_t block_num, uint32_t num_bloc
205197 }
206198
207199 // do the read
208- if (HAL_SD_ReadBlocks_DMA (& sd_handle , (uint32_t * )dest , ( uint64_t ) block_num * SDCARD_BLOCK_SIZE , SDCARD_BLOCK_SIZE ) != SD_OK ) {
200+ if (HAL_SD_ReadBlocks_BlockNumber_DMA (& sd_handle , (uint32_t * )dest , block_num , SDCARD_BLOCK_SIZE ) != SD_OK ) {
209201 return false;
210202 }
211203
@@ -230,7 +222,7 @@ bool sdcard_write_blocks_dma(const uint8_t *src, uint32_t block_num, uint32_t nu
230222
231223 SD_Error status ;
232224
233- status = HAL_SD_WriteBlock_DMA (& sd_handle , (uint32_t * )src , ( uint64_t ) block_num * SDCARD_BLOCK_SIZE , SDCARD_BLOCK_SIZE , num_blocks );
225+ status = HAL_SD_WriteBlocks_BlockNumber_DMA (& sd_handle , (uint32_t * )src , block_num , SDCARD_BLOCK_SIZE , num_blocks );
234226 if (status != SD_OK ) {
235227 return false;
236228 }
@@ -247,14 +239,17 @@ bool sdcard_write_blocks_dma(const uint8_t *src, uint32_t block_num, uint32_t nu
247239
248240/******************************************************************************/
249241// Micro Python bindings
242+ //
243+ // Note: these function are a bit ad-hoc at the moment and are mainly intended
244+ // for testing purposes. In the future SD should be a proper class with a
245+ // consistent interface and methods to mount/unmount it.
250246
251- static mp_obj_t sd_present (mp_obj_t self ) {
247+ STATIC mp_obj_t sd_present (mp_obj_t self ) {
252248 return MP_BOOL (sdcard_is_present ());
253249}
250+ STATIC MP_DEFINE_CONST_FUN_OBJ_1 (sd_present_obj , sd_present );
254251
255- static MP_DEFINE_CONST_FUN_OBJ_1 (sd_present_obj , sd_present ) ;
256-
257- static mp_obj_t sd_power (mp_obj_t self , mp_obj_t state ) {
252+ STATIC mp_obj_t sd_power (mp_obj_t self , mp_obj_t state ) {
258253 bool result ;
259254 if (mp_obj_is_true (state )) {
260255 result = sdcard_power_on ();
@@ -264,40 +259,59 @@ static mp_obj_t sd_power(mp_obj_t self, mp_obj_t state) {
264259 }
265260 return MP_BOOL (result );
266261}
262+ STATIC MP_DEFINE_CONST_FUN_OBJ_2 (sd_power_obj , sd_power );
267263
268- static MP_DEFINE_CONST_FUN_OBJ_2 (sd_power_obj , sd_power ) ;
264+ STATIC mp_obj_t sd_info (mp_obj_t self ) {
265+ HAL_SD_ErrorTypedef HAL_SD_Init (SD_HandleTypeDef * hsd , HAL_SD_CardInfoTypedef * SDCardInfo );
266+ if (sd_handle .Instance == NULL ) {
267+ return mp_const_none ;
268+ }
269+ HAL_SD_CardInfoTypedef cardinfo ;
270+ HAL_SD_Get_CardInfo (& sd_handle , & cardinfo );
271+ // cardinfo.SD_csd and cardinfo.SD_cid have lots of info but we don't use them
272+ mp_obj_t tuple [3 ] = {
273+ mp_obj_new_int_from_ull (cardinfo .CardCapacity ),
274+ mp_obj_new_int_from_uint (cardinfo .CardBlockSize ),
275+ mp_obj_new_int (cardinfo .CardType ),
276+ };
277+ return mp_obj_new_tuple (3 , tuple );
278+ }
279+ STATIC MP_DEFINE_CONST_FUN_OBJ_1 (sd_info_obj , sd_info );
269280
270- static mp_obj_t sd_read (mp_obj_t self , mp_obj_t block_num ) {
281+ STATIC mp_obj_t sd_read (mp_obj_t self , mp_obj_t block_num ) {
271282 uint8_t * dest = m_new (uint8_t , SDCARD_BLOCK_SIZE );
272- if (!sdcard_read_blocks (dest , mp_obj_get_int (block_num ), 1 )) {
283+ mp_uint_t ret = sdcard_read_blocks (dest , mp_obj_get_int (block_num ), 1 );
284+
285+ if (ret != 0 ) {
273286 m_free (dest , SDCARD_BLOCK_SIZE );
274- return mp_const_none ;
287+ nlr_raise ( mp_obj_new_exception_msg_varg ( & mp_type_Exception , "sdcard_read_blocks failed [%u]" , ret )) ;
275288 }
289+
276290 return mp_obj_new_bytearray_by_ref (SDCARD_BLOCK_SIZE , dest );
277291}
292+ STATIC MP_DEFINE_CONST_FUN_OBJ_2 (sd_read_obj , sd_read );
278293
279- static MP_DEFINE_CONST_FUN_OBJ_2 (sd_read_obj , sd_read ) ;
280-
281- static mp_obj_t sd_write (mp_obj_t self , mp_obj_t block_num , mp_obj_t source ) {
294+ STATIC mp_obj_t sd_write (mp_obj_t self , mp_obj_t block_num , mp_obj_t data ) {
282295 mp_buffer_info_t bufinfo ;
283- uint8_t tmp [1 ];
284-
285- pyb_buf_get_for_send (source , & bufinfo , tmp );
296+ mp_get_buffer_raise (data , & bufinfo , MP_BUFFER_READ );
286297 if (bufinfo .len % SDCARD_BLOCK_SIZE != 0 ) {
287- nlr_raise (mp_obj_new_exception_msg_varg (& mp_type_ValueError , "writes must be aligned to SDCARD_BLOCK_SIZE (%d) bytes" , SDCARD_BLOCK_SIZE ));
298+ nlr_raise (mp_obj_new_exception_msg_varg (& mp_type_ValueError , "writes must be a multiple of %d bytes" , SDCARD_BLOCK_SIZE ));
288299 }
289300
290- if (!sdcard_write_blocks (bufinfo .buf , mp_obj_get_int (block_num ), bufinfo .len / SDCARD_BLOCK_SIZE )) {
291- nlr_raise (mp_obj_new_exception_msg_varg (& mp_type_Exception , "sdcard_write_blocks failed" ));
301+ mp_uint_t ret = sdcard_write_blocks (bufinfo .buf , mp_obj_get_int (block_num ), bufinfo .len / SDCARD_BLOCK_SIZE );
302+
303+ if (ret != 0 ) {
304+ nlr_raise (mp_obj_new_exception_msg_varg (& mp_type_Exception , "sdcard_write_blocks failed [%u]" , ret ));
292305 }
306+
293307 return mp_const_none ;
294308}
295-
296- static MP_DEFINE_CONST_FUN_OBJ_3 (sd_write_obj , sd_write ) ;
309+ STATIC MP_DEFINE_CONST_FUN_OBJ_3 (sd_write_obj , sd_write );
297310
298311STATIC const mp_map_elem_t sdcard_locals_dict_table [] = {
299312 { MP_OBJ_NEW_QSTR (MP_QSTR_present ), (mp_obj_t )& sd_present_obj },
300313 { MP_OBJ_NEW_QSTR (MP_QSTR_power ), (mp_obj_t )& sd_power_obj },
314+ { MP_OBJ_NEW_QSTR (MP_QSTR_info ), (mp_obj_t )& sd_info_obj },
301315 { MP_OBJ_NEW_QSTR (MP_QSTR_read ), (mp_obj_t )& sd_read_obj },
302316 { MP_OBJ_NEW_QSTR (MP_QSTR_write ), (mp_obj_t )& sd_write_obj },
303317};
0 commit comments