OLD | NEW |
1 // Copyright 2009 the V8 project authors. All rights reserved. | 1 // Copyright 2009 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
177 private: | 177 private: |
178 int fd_; | 178 int fd_; |
179 }; | 179 }; |
180 | 180 |
181 | 181 |
182 // A utility class that takes the array of command arguments and puts then in an | 182 // A utility class that takes the array of command arguments and puts then in an |
183 // array of new[]ed UTF-8 C strings. Deallocates them again when it goes out of | 183 // array of new[]ed UTF-8 C strings. Deallocates them again when it goes out of |
184 // scope. | 184 // scope. |
185 class ExecArgs { | 185 class ExecArgs { |
186 public: | 186 public: |
187 ExecArgs(Handle<Value> arg0, Handle<Array> command_args) { | 187 ExecArgs() { |
| 188 exec_args_[0] = NULL; |
| 189 } |
| 190 bool Init(Handle<Value> arg0, Handle<Array> command_args) { |
188 String::Utf8Value prog(arg0); | 191 String::Utf8Value prog(arg0); |
189 int len = prog.length() + 1; | 192 if (*prog == NULL) { |
| 193 const char* message = |
| 194 "os.system(): String conversion of program name failed"; |
| 195 ThrowException(String::New(message)); |
| 196 return false; |
| 197 } |
| 198 int len = prog.length() + 3; |
190 char* c_arg = new char[len]; | 199 char* c_arg = new char[len]; |
191 snprintf(c_arg, len, "%s", *prog); | 200 snprintf(c_arg, len, "%s", *prog); |
192 exec_args_[0] = c_arg; | 201 exec_args_[0] = c_arg; |
193 int i = 1; | 202 int i = 1; |
194 for (unsigned j = 0; j < command_args->Length(); i++, j++) { | 203 for (unsigned j = 0; j < command_args->Length(); i++, j++) { |
195 Handle<Value> arg(command_args->Get(Integer::New(j))); | 204 Handle<Value> arg(command_args->Get(Integer::New(j))); |
196 String::Utf8Value utf8_arg(arg); | 205 String::Utf8Value utf8_arg(arg); |
| 206 if (*utf8_arg == NULL) { |
| 207 exec_args_[i] = NULL; // Consistent state for destructor. |
| 208 const char* message = |
| 209 "os.system(): String conversion of argument failed."; |
| 210 ThrowException(String::New(message)); |
| 211 return false; |
| 212 } |
197 int len = utf8_arg.length() + 1; | 213 int len = utf8_arg.length() + 1; |
198 char* c_arg = new char[len]; | 214 char* c_arg = new char[len]; |
199 snprintf(c_arg, len, "%s", *utf8_arg); | 215 snprintf(c_arg, len, "%s", *utf8_arg); |
200 exec_args_[i] = c_arg; | 216 exec_args_[i] = c_arg; |
201 } | 217 } |
202 exec_args_[i] = NULL; | 218 exec_args_[i] = NULL; |
| 219 return true; |
203 } | 220 } |
204 ~ExecArgs() { | 221 ~ExecArgs() { |
205 for (unsigned i = 0; i < kMaxArgs; i++) { | 222 for (unsigned i = 0; i < kMaxArgs; i++) { |
206 if (exec_args_[i] == NULL) { | 223 if (exec_args_[i] == NULL) { |
207 return; | 224 return; |
208 } | 225 } |
209 delete [] exec_args_[i]; | 226 delete [] exec_args_[i]; |
210 exec_args_[i] = 0; | 227 exec_args_[i] = 0; |
211 } | 228 } |
212 } | 229 } |
(...skipping 234 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
447 if (command_args->Length() > ExecArgs::kMaxArgs) { | 464 if (command_args->Length() > ExecArgs::kMaxArgs) { |
448 return ThrowException(String::New("Too many arguments to system()")); | 465 return ThrowException(String::New("Too many arguments to system()")); |
449 } | 466 } |
450 if (args.Length() < 1) { | 467 if (args.Length() < 1) { |
451 return ThrowException(String::New("Too few arguments to system()")); | 468 return ThrowException(String::New("Too few arguments to system()")); |
452 } | 469 } |
453 | 470 |
454 struct timeval start_time; | 471 struct timeval start_time; |
455 gettimeofday(&start_time, NULL); | 472 gettimeofday(&start_time, NULL); |
456 | 473 |
457 ExecArgs exec_args(args[0], command_args); | 474 ExecArgs exec_args; |
| 475 if (!exec_args.Init(args[0], command_args)) { |
| 476 return v8::Undefined(); |
| 477 } |
458 int exec_error_fds[2]; | 478 int exec_error_fds[2]; |
459 int stdout_fds[2]; | 479 int stdout_fds[2]; |
460 | 480 |
461 if (pipe(exec_error_fds) != 0) { | 481 if (pipe(exec_error_fds) != 0) { |
462 return ThrowException(String::New("pipe syscall failed.")); | 482 return ThrowException(String::New("pipe syscall failed.")); |
463 } | 483 } |
464 if (pipe(stdout_fds) != 0) { | 484 if (pipe(stdout_fds) != 0) { |
465 return ThrowException(String::New("pipe syscall failed.")); | 485 return ThrowException(String::New("pipe syscall failed.")); |
466 } | 486 } |
467 | 487 |
(...skipping 26 matching lines...) Expand all Loading... |
494 start_time, | 514 start_time, |
495 read_timeout, | 515 read_timeout, |
496 total_timeout)) { | 516 total_timeout)) { |
497 return v8::Undefined(); | 517 return v8::Undefined(); |
498 } | 518 } |
499 | 519 |
500 return scope.Close(accumulator); | 520 return scope.Close(accumulator); |
501 } | 521 } |
502 | 522 |
503 | 523 |
| 524 Handle<Value> Shell::ChangeDirectory(const Arguments& args) { |
| 525 if (args.Length() != 1) { |
| 526 const char* message = "chdir() takes one argument"; |
| 527 return ThrowException(String::New(message)); |
| 528 } |
| 529 String::Utf8Value directory(args[0]); |
| 530 if (*directory == NULL) { |
| 531 const char* message = "os.chdir(): String conversion of argument failed."; |
| 532 return ThrowException(String::New(message)); |
| 533 } |
| 534 if (chdir(*directory) != 0) { |
| 535 return ThrowException(String::New(strerror(errno))); |
| 536 } |
| 537 return v8::Undefined(); |
| 538 } |
| 539 |
| 540 |
504 } // namespace v8 | 541 } // namespace v8 |
OLD | NEW |