@@ -54,11 +54,12 @@ void check_fd_is_open(const mp_obj_fdfile_t *o) {
5454#define check_fd_is_open (o )
5555#endif
5656
57- STATIC const mp_obj_type_t rawfile_type ;
57+ extern const mp_obj_type_t mp_type_fileio ;
58+ extern const mp_obj_type_t mp_type_textio ;
5859
5960STATIC void fdfile_print (void (* print )(void * env , const char * fmt , ...), void * env , mp_obj_t self_in , mp_print_kind_t kind ) {
6061 mp_obj_fdfile_t * self = self_in ;
61- print (env , "<io.FileIO %d>" , self -> fd );
62+ print (env , "<io.%s %d>" , mp_obj_get_type_str ( self ) , self -> fd );
6263}
6364
6465STATIC machine_int_t fdfile_read (mp_obj_t o_in , void * buf , machine_uint_t size , int * errcode ) {
@@ -103,23 +104,10 @@ STATIC mp_obj_t fdfile_fileno(mp_obj_t self_in) {
103104}
104105STATIC MP_DEFINE_CONST_FUN_OBJ_1 (fdfile_fileno_obj , fdfile_fileno );
105106
106- STATIC mp_obj_fdfile_t * fdfile_new (int fd ) {
107- mp_obj_fdfile_t * o = m_new_obj (mp_obj_fdfile_t );
108- o -> base .type = & rawfile_type ;
109- o -> fd = fd ;
110- return o ;
111- }
112-
113107STATIC mp_obj_t fdfile_make_new (mp_obj_t type_in , uint n_args , uint n_kw , const mp_obj_t * args ) {
114108 mp_obj_fdfile_t * o = m_new_obj (mp_obj_fdfile_t );
115- o -> base .type = type_in ;
116-
117- if (MP_OBJ_IS_SMALL_INT (args [0 ])) {
118- o -> fd = MP_OBJ_SMALL_INT_VALUE (args [0 ]);
119- return o ;
120- }
109+ mp_const_obj_t type = type_in ;
121110
122- const char * fname = mp_obj_str_get_str (args [0 ]);
123111 const char * mode_s ;
124112 if (n_args > 1 ) {
125113 mode_s = mp_obj_str_get_str (args [1 ]);
@@ -143,14 +131,32 @@ STATIC mp_obj_t fdfile_make_new(mp_obj_t type_in, uint n_args, uint n_kw, const
143131 case '+' :
144132 mode |= O_RDWR ;
145133 break ;
134+ #if MICROPY_MOD_IO_FILEIO
135+ // If we don't have io.FileIO, then files are in text mode implicitly
136+ case 'b' :
137+ type = & mp_type_fileio ;
138+ break ;
139+ case 't' :
140+ type = & mp_type_textio ;
141+ break ;
142+ #endif
146143 }
147144 }
148145
146+ o -> base .type = type ;
147+
148+ if (MP_OBJ_IS_SMALL_INT (args [0 ])) {
149+ o -> fd = MP_OBJ_SMALL_INT_VALUE (args [0 ]);
150+ return o ;
151+ }
152+
153+ const char * fname = mp_obj_str_get_str (args [0 ]);
149154 int fd = open (fname , mode , 0644 );
150155 if (fd == -1 ) {
151156 nlr_raise (mp_obj_new_exception_arg1 (& mp_type_OSError , MP_OBJ_NEW_SMALL_INT ((machine_int_t )errno )));
152157 }
153- return fdfile_new (fd );
158+ o -> fd = fd ;
159+ return o ;
154160}
155161
156162STATIC const mp_map_elem_t rawfile_locals_dict_table [] = {
@@ -167,29 +173,48 @@ STATIC const mp_map_elem_t rawfile_locals_dict_table[] = {
167173
168174STATIC MP_DEFINE_CONST_DICT (rawfile_locals_dict , rawfile_locals_dict_table );
169175
170- STATIC const mp_stream_p_t rawfile_stream_p = {
176+ #if MICROPY_MOD_IO_FILEIO
177+ STATIC const mp_stream_p_t fileio_stream_p = {
171178 .read = fdfile_read ,
172179 .write = fdfile_write ,
180+ .is_bytes = true,
173181};
174182
175- STATIC const mp_obj_type_t rawfile_type = {
183+ const mp_obj_type_t mp_type_fileio = {
176184 { & mp_type_type },
177185 .name = MP_QSTR_FileIO ,
178186 .print = fdfile_print ,
179187 .make_new = fdfile_make_new ,
180188 .getiter = mp_identity ,
181189 .iternext = mp_stream_unbuffered_iter ,
182- .stream_p = & rawfile_stream_p ,
190+ .stream_p = & fileio_stream_p ,
191+ .locals_dict = (mp_obj_t )& rawfile_locals_dict ,
192+ };
193+ #endif
194+
195+ STATIC const mp_stream_p_t textio_stream_p = {
196+ .read = fdfile_read ,
197+ .write = fdfile_write ,
198+ };
199+
200+ const mp_obj_type_t mp_type_textio = {
201+ { & mp_type_type },
202+ .name = MP_QSTR_TextIOWrapper ,
203+ .print = fdfile_print ,
204+ .make_new = fdfile_make_new ,
205+ .getiter = mp_identity ,
206+ .iternext = mp_stream_unbuffered_iter ,
207+ .stream_p = & textio_stream_p ,
183208 .locals_dict = (mp_obj_t )& rawfile_locals_dict ,
184209};
185210
186211// Factory function for I/O stream classes
187212mp_obj_t mp_builtin_open (uint n_args , const mp_obj_t * args ) {
188213 // TODO: analyze mode and buffering args and instantiate appropriate type
189- return fdfile_make_new ((mp_obj_t )& rawfile_type , n_args , 0 , args );
214+ return fdfile_make_new ((mp_obj_t )& mp_type_textio , n_args , 0 , args );
190215}
191216MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN (mp_builtin_open_obj , 1 , 2 , mp_builtin_open );
192217
193- const mp_obj_fdfile_t mp_sys_stdin_obj = { .base = {& rawfile_type }, .fd = STDIN_FILENO };
194- const mp_obj_fdfile_t mp_sys_stdout_obj = { .base = {& rawfile_type }, .fd = STDOUT_FILENO };
195- const mp_obj_fdfile_t mp_sys_stderr_obj = { .base = {& rawfile_type }, .fd = STDERR_FILENO };
218+ const mp_obj_fdfile_t mp_sys_stdin_obj = { .base = {& mp_type_textio }, .fd = STDIN_FILENO };
219+ const mp_obj_fdfile_t mp_sys_stdout_obj = { .base = {& mp_type_textio }, .fd = STDOUT_FILENO };
220+ const mp_obj_fdfile_t mp_sys_stderr_obj = { .base = {& mp_type_textio }, .fd = STDERR_FILENO };
0 commit comments