32
32
33
33
#if MICROPY_VFS
34
34
35
- // Block device functions are expected to return 0 on success
36
- // and negative integer on errors. Check for positive integer
37
- // results as some callers (i.e. littlefs) will produce corrupt
38
- // results from these.
39
- static int mp_vfs_check_result (mp_obj_t ret ) {
40
- if (ret == mp_const_none ) {
41
- return 0 ;
42
- } else {
43
- int i = MP_OBJ_SMALL_INT_VALUE (ret );
44
- return i > 0 ? (- MP_EINVAL ) : i ;
45
- }
46
- }
47
-
48
35
void mp_vfs_blockdev_init (mp_vfs_blockdev_t * self , mp_obj_t bdev ) {
49
36
mp_load_method (bdev , MP_QSTR_readblocks , self -> readblocks );
50
37
mp_load_method_maybe (bdev , MP_QSTR_writeblocks , self -> writeblocks );
@@ -59,27 +46,37 @@ void mp_vfs_blockdev_init(mp_vfs_blockdev_t *self, mp_obj_t bdev) {
59
46
}
60
47
}
61
48
49
+ // Helper function to minimise code size of read/write functions
50
+ static int mp_vfs_blockdev_call_rw (mp_obj_t * args , bool ext_fn , size_t block_num , size_t block_off , size_t len , void * buf ) {
51
+ mp_obj_array_t ar = {{& mp_type_bytearray }, BYTEARRAY_TYPECODE , 0 , len , buf };
52
+ args [2 ] = MP_OBJ_NEW_SMALL_INT (block_num );
53
+ args [3 ] = MP_OBJ_FROM_PTR (& ar );
54
+ args [4 ] = MP_OBJ_NEW_SMALL_INT (block_off ); // ignored for !ext_fn
55
+ mp_obj_t ret = mp_call_method_n_kw (ext_fn ? 3 : 2 , 0 , args );
56
+
57
+ if (ret == mp_const_none ) {
58
+ return 0 ;
59
+ } else {
60
+ // Block device functions are expected to return 0 on success
61
+ // and negative integer on errors. Check for positive integer
62
+ // results as some callers (i.e. littlefs) will produce corrupt
63
+ // results from these.
64
+ int i = MP_OBJ_SMALL_INT_VALUE (ret );
65
+ return i > 0 ? (- MP_EINVAL ) : i ;
66
+ }
67
+ }
68
+
62
69
int mp_vfs_blockdev_read (mp_vfs_blockdev_t * self , size_t block_num , size_t num_blocks , uint8_t * buf ) {
63
70
if (self -> flags & MP_BLOCKDEV_FLAG_NATIVE ) {
64
71
mp_uint_t (* f )(uint8_t * , uint32_t , uint32_t ) = (void * )(uintptr_t )self -> readblocks [2 ];
65
72
return f (buf , block_num , num_blocks );
66
73
} else {
67
- mp_obj_array_t ar = {{& mp_type_bytearray }, BYTEARRAY_TYPECODE , 0 , num_blocks * self -> block_size , buf };
68
- self -> readblocks [2 ] = MP_OBJ_NEW_SMALL_INT (block_num );
69
- self -> readblocks [3 ] = MP_OBJ_FROM_PTR (& ar );
70
- mp_call_method_n_kw (2 , 0 , self -> readblocks );
71
- // TODO handle error return
72
- return 0 ;
74
+ return mp_vfs_blockdev_call_rw (self -> readblocks , false, block_num , 0 , num_blocks * self -> block_size , buf );
73
75
}
74
76
}
75
77
76
78
int mp_vfs_blockdev_read_ext (mp_vfs_blockdev_t * self , size_t block_num , size_t block_off , size_t len , uint8_t * buf ) {
77
- mp_obj_array_t ar = {{& mp_type_bytearray }, BYTEARRAY_TYPECODE , 0 , len , buf };
78
- self -> readblocks [2 ] = MP_OBJ_NEW_SMALL_INT (block_num );
79
- self -> readblocks [3 ] = MP_OBJ_FROM_PTR (& ar );
80
- self -> readblocks [4 ] = MP_OBJ_NEW_SMALL_INT (block_off );
81
- mp_obj_t ret = mp_call_method_n_kw (3 , 0 , self -> readblocks );
82
- return mp_vfs_check_result (ret );
79
+ return mp_vfs_blockdev_call_rw (self -> readblocks , true, block_num , block_off , len , buf );
83
80
}
84
81
85
82
int mp_vfs_blockdev_write (mp_vfs_blockdev_t * self , size_t block_num , size_t num_blocks , const uint8_t * buf ) {
@@ -92,12 +89,7 @@ int mp_vfs_blockdev_write(mp_vfs_blockdev_t *self, size_t block_num, size_t num_
92
89
mp_uint_t (* f )(const uint8_t * , uint32_t , uint32_t ) = (void * )(uintptr_t )self -> writeblocks [2 ];
93
90
return f (buf , block_num , num_blocks );
94
91
} else {
95
- mp_obj_array_t ar = {{& mp_type_bytearray }, BYTEARRAY_TYPECODE , 0 , num_blocks * self -> block_size , (void * )buf };
96
- self -> writeblocks [2 ] = MP_OBJ_NEW_SMALL_INT (block_num );
97
- self -> writeblocks [3 ] = MP_OBJ_FROM_PTR (& ar );
98
- mp_call_method_n_kw (2 , 0 , self -> writeblocks );
99
- // TODO handle error return
100
- return 0 ;
92
+ return mp_vfs_blockdev_call_rw (self -> writeblocks , false, block_num , 0 , num_blocks * self -> block_size , (void * )buf );
101
93
}
102
94
}
103
95
@@ -106,13 +98,7 @@ int mp_vfs_blockdev_write_ext(mp_vfs_blockdev_t *self, size_t block_num, size_t
106
98
// read-only block device
107
99
return - MP_EROFS ;
108
100
}
109
-
110
- mp_obj_array_t ar = {{& mp_type_bytearray }, BYTEARRAY_TYPECODE , 0 , len , (void * )buf };
111
- self -> writeblocks [2 ] = MP_OBJ_NEW_SMALL_INT (block_num );
112
- self -> writeblocks [3 ] = MP_OBJ_FROM_PTR (& ar );
113
- self -> writeblocks [4 ] = MP_OBJ_NEW_SMALL_INT (block_off );
114
- mp_obj_t ret = mp_call_method_n_kw (3 , 0 , self -> writeblocks );
115
- return mp_vfs_check_result (ret );
101
+ return mp_vfs_blockdev_call_rw (self -> writeblocks , true, block_num , block_off , len , (void * )buf );
116
102
}
117
103
118
104
mp_obj_t mp_vfs_blockdev_ioctl (mp_vfs_blockdev_t * self , uintptr_t cmd , uintptr_t arg ) {
0 commit comments