@@ -24,6 +24,8 @@ use std::sync::atomic::Ordering;
24
24
25
25
use std:: fs;
26
26
use std:: io;
27
+ use std:: io:: BorrowedBuf ;
28
+ use std:: io:: Read ;
27
29
28
30
#[ cfg( test) ]
29
31
mod tests;
@@ -101,10 +103,13 @@ pub trait FileLoader {
101
103
fn file_exists ( & self , path : & Path ) -> bool ;
102
104
103
105
/// Read the contents of a UTF-8 file into memory.
106
+ /// This function must return a String because we normalize
107
+ /// source files, which may require resizing.
104
108
fn read_file ( & self , path : & Path ) -> io:: Result < String > ;
105
109
106
110
/// Read the contents of a potentially non-UTF-8 file into memory.
107
- fn read_binary_file ( & self , path : & Path ) -> io:: Result < Vec < u8 > > ;
111
+ /// We don't normalize binary files, so we can start in an Lrc.
112
+ fn read_binary_file ( & self , path : & Path ) -> io:: Result < Lrc < [ u8 ] > > ;
108
113
}
109
114
110
115
/// A FileLoader that uses std::fs to load real files.
@@ -119,8 +124,16 @@ impl FileLoader for RealFileLoader {
119
124
fs:: read_to_string ( path)
120
125
}
121
126
122
- fn read_binary_file ( & self , path : & Path ) -> io:: Result < Vec < u8 > > {
123
- fs:: read ( path)
127
+ fn read_binary_file ( & self , path : & Path ) -> io:: Result < Lrc < [ u8 ] > > {
128
+ let mut file = fs:: File :: open ( path) ?;
129
+ let len = file. metadata ( ) ?. len ( ) ;
130
+
131
+ let mut bytes = Lrc :: new_uninit_slice ( len as usize ) ;
132
+ let mut buf = BorrowedBuf :: from ( Lrc :: get_mut ( & mut bytes) . unwrap ( ) ) ;
133
+ file. read_buf_exact ( buf. unfilled ( ) ) ?;
134
+ // SAFETY: If the read_buf_exact call returns Ok(()), then we have
135
+ // read len bytes and initialized the buffer.
136
+ Ok ( unsafe { bytes. assume_init ( ) } )
124
137
}
125
138
}
126
139
@@ -228,7 +241,7 @@ impl SourceMap {
228
241
///
229
242
/// Unlike `load_file`, guarantees that no normalization like BOM-removal
230
243
/// takes place.
231
- pub fn load_binary_file ( & self , path : & Path ) -> io:: Result < Vec < u8 > > {
244
+ pub fn load_binary_file ( & self , path : & Path ) -> io:: Result < Lrc < [ u8 ] > > {
232
245
let bytes = self . file_loader . read_binary_file ( path) ?;
233
246
234
247
// We need to add file to the `SourceMap`, so that it is present
0 commit comments