@@ -123,10 +123,11 @@ const char *REPL::IOHandlerGetHelpPrologue() {
123
123
" Valid statements, expressions, and declarations are immediately "
124
124
" compiled and executed.\n\n "
125
125
" The complete set of LLDB debugging commands are also available as "
126
- " described below. Commands "
126
+ " described below.\n\n Commands "
127
127
" must be prefixed with a colon at the REPL prompt (:quit for "
128
128
" example.) Typing just a colon "
129
- " followed by return will switch to the LLDB prompt.\n\n " ;
129
+ " followed by return will switch to the LLDB prompt.\n\n "
130
+ " Type “< path” to read in code from a text file “path”.\n\n " ;
130
131
}
131
132
132
133
bool REPL::IOHandlerIsInputComplete (IOHandler &io_handler, StringList &lines) {
@@ -179,6 +180,36 @@ int REPL::IOHandlerFixIndentation(IOHandler &io_handler,
179
180
return (int )desired_indent - actual_indent;
180
181
}
181
182
183
+ static bool ReadCode (const std::string &path, std::string &code,
184
+ lldb::StreamFileSP &error_sp) {
185
+ auto &fs = FileSystem::Instance ();
186
+ llvm::Twine pathTwine (path);
187
+ if (!fs.Exists (pathTwine)) {
188
+ error_sp->Printf (" no such file at path '%s'\n " , path.c_str ());
189
+ return false ;
190
+ }
191
+ if (!fs.Readable (pathTwine)) {
192
+ error_sp->Printf (" could not read file at path '%s'\n " , path.c_str ());
193
+ return false ;
194
+ }
195
+ const size_t file_size = fs.GetByteSize (pathTwine);
196
+ const size_t max_size = code.max_size ();
197
+ if (file_size > max_size) {
198
+ error_sp->Printf (" file at path '%s' too large: "
199
+ " file_size = %llu, max_size = %llu\n " ,
200
+ path.c_str (), file_size, max_size);
201
+ return false ;
202
+ }
203
+ auto data_sp = fs.CreateDataBuffer (pathTwine);
204
+ if (data_sp == nullptr ) {
205
+ error_sp->Printf (" could not create buffer for file at path '%s'\n " ,
206
+ path.c_str ());
207
+ return false ;
208
+ }
209
+ code.assign ((const char *)data_sp->GetBytes (), data_sp->GetByteSize ());
210
+ return true ;
211
+ }
212
+
182
213
void REPL::IOHandlerInputComplete (IOHandler &io_handler, std::string &code) {
183
214
lldb::StreamFileSP output_sp (io_handler.GetOutputStreamFileSP ());
184
215
lldb::StreamFileSP error_sp (io_handler.GetErrorStreamFileSP ());
@@ -257,6 +288,15 @@ void REPL::IOHandlerInputComplete(IOHandler &io_handler, std::string &code) {
257
288
}
258
289
}
259
290
} else {
291
+ if (code[0 ] == ' <' ) {
292
+ // User wants to read code from a file.
293
+ // Interpret rest of line as a literal path.
294
+ auto path = llvm::StringRef (code.substr (1 )).trim ().str ();
295
+ if (!ReadCode (path, code, error_sp)) {
296
+ return ;
297
+ }
298
+ }
299
+
260
300
// Unwind any expression we might have been running in case our REPL
261
301
// expression crashed and the user was looking around
262
302
if (m_dedicated_repl_mode) {
0 commit comments