mirror of
https://github.com/fish-shell/fish-shell
synced 2024-11-15 17:28:19 +00:00
Migrate get_interpreter into postfork.cpp
It's only used after fork.
This commit is contained in:
parent
8e8a3846fb
commit
29af84d733
3 changed files with 31 additions and 32 deletions
27
src/exec.cpp
27
src/exec.cpp
|
@ -66,33 +66,6 @@ void exec_close(int fd) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Returns the interpreter for the specified script. Returns NULL if file is not a script with a
|
|
||||||
/// shebang.
|
|
||||||
char *get_interpreter(const char *command, char *interpreter, size_t buff_size) {
|
|
||||||
// OK to not use CLO_EXEC here because this is only called after fork.
|
|
||||||
int fd = open(command, O_RDONLY);
|
|
||||||
if (fd >= 0) {
|
|
||||||
size_t idx = 0;
|
|
||||||
while (idx + 1 < buff_size) {
|
|
||||||
char ch;
|
|
||||||
ssize_t amt = read(fd, &ch, sizeof ch);
|
|
||||||
if (amt <= 0) break;
|
|
||||||
if (ch == '\n') break;
|
|
||||||
interpreter[idx++] = ch;
|
|
||||||
}
|
|
||||||
interpreter[idx++] = '\0';
|
|
||||||
close(fd);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (std::strncmp(interpreter, "#! /", 4) == 0) {
|
|
||||||
return interpreter + 3;
|
|
||||||
} else if (std::strncmp(interpreter, "#!/", 3) == 0) {
|
|
||||||
return interpreter + 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// This function is executed by the child process created by a call to fork(). It should be called
|
/// This function is executed by the child process created by a call to fork(). It should be called
|
||||||
/// after \c child_setup_process. It calls execve to replace the fish process image with the command
|
/// after \c child_setup_process. It calls execve to replace the fish process image with the command
|
||||||
/// specified in \c p. It never returns. Called in a forked child! Do not allocate memory, etc.
|
/// specified in \c p. It never returns. Called in a forked child! Do not allocate memory, etc.
|
||||||
|
|
|
@ -37,7 +37,4 @@ int exec_subshell_for_expand(const wcstring &cmd, parser_t &parser, wcstring_lis
|
||||||
/// Loops over close until the syscall was run without being interrupted.
|
/// Loops over close until the syscall was run without being interrupted.
|
||||||
void exec_close(int fd);
|
void exec_close(int fd);
|
||||||
|
|
||||||
/// Gets the interpreter for a given command.
|
|
||||||
char *get_interpreter(const char *command, char *interpreter, size_t buff_size);
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -38,6 +38,8 @@
|
||||||
/// Fork error message.
|
/// Fork error message.
|
||||||
#define FORK_ERROR "Could not create child process - exiting"
|
#define FORK_ERROR "Could not create child process - exiting"
|
||||||
|
|
||||||
|
static char *get_interpreter(const char *command, char *buffer, size_t buff_size);
|
||||||
|
|
||||||
/// Called only by the child to set its own process group (possibly creating a new group in the
|
/// Called only by the child to set its own process group (possibly creating a new group in the
|
||||||
/// process if it is the first in a JOB_CONTROL job.
|
/// process if it is the first in a JOB_CONTROL job.
|
||||||
/// Returns true on success, false on failure.
|
/// Returns true on success, false on failure.
|
||||||
|
@ -353,8 +355,9 @@ void safe_report_exec_error(int err, const char *actual_cmd, const char *const *
|
||||||
// an open file action fails. These cases appear to be impossible to distinguish. We
|
// an open file action fails. These cases appear to be impossible to distinguish. We
|
||||||
// address this by not using posix_spawn for file redirections, so all the ENOENTs we
|
// address this by not using posix_spawn for file redirections, so all the ENOENTs we
|
||||||
// find must be errors from exec().
|
// find must be errors from exec().
|
||||||
char interpreter_buff[128] = {}, *interpreter;
|
char interpreter_buff[128] = {};
|
||||||
interpreter = get_interpreter(actual_cmd, interpreter_buff, sizeof interpreter_buff);
|
const char *interpreter =
|
||||||
|
get_interpreter(actual_cmd, interpreter_buff, sizeof interpreter_buff);
|
||||||
if (interpreter && 0 != access(interpreter, X_OK)) {
|
if (interpreter && 0 != access(interpreter, X_OK)) {
|
||||||
debug_safe(0,
|
debug_safe(0,
|
||||||
"The file '%s' specified the interpreter '%s', which is not an "
|
"The file '%s' specified the interpreter '%s', which is not an "
|
||||||
|
@ -378,3 +381,29 @@ void safe_report_exec_error(int err, const char *actual_cmd, const char *const *
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Returns the interpreter for the specified script. Returns NULL if file is not a script with a
|
||||||
|
/// shebang.
|
||||||
|
static char *get_interpreter(const char *command, char *buffer, size_t buff_size) {
|
||||||
|
// OK to not use CLO_EXEC here because this is only called after fork.
|
||||||
|
int fd = open(command, O_RDONLY);
|
||||||
|
if (fd >= 0) {
|
||||||
|
size_t idx = 0;
|
||||||
|
while (idx + 1 < buff_size) {
|
||||||
|
char ch;
|
||||||
|
ssize_t amt = read(fd, &ch, sizeof ch);
|
||||||
|
if (amt <= 0) break;
|
||||||
|
if (ch == '\n') break;
|
||||||
|
buffer[idx++] = ch;
|
||||||
|
}
|
||||||
|
buffer[idx++] = '\0';
|
||||||
|
close(fd);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (std::strncmp(buffer, "#! /", 4) == 0) {
|
||||||
|
return buffer + 3;
|
||||||
|
} else if (std::strncmp(buffer, "#!/", 3) == 0) {
|
||||||
|
return buffer + 2;
|
||||||
|
}
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in a new issue