5

Недавно я использовал vim для программирования на C. Я создал ярлыки для компиляции и запуска программ из самого vim, но недавно процесс vim остановился после выполнения программы.

foo.c:

#include <stdio.h>

int main() {
    printf("Hello World!\n");
    return 0;
}

.vimrc:

set shellcmdflag=-ic

syntax on

autocmd FileType c map <F6> :!gcc -o "%:p:r.out" "%:." <bar> more<CR>
autocmd FileType c map <F7> :!%:p:r.out<CR>

Если я нажму F6, программа прекрасно скомпилируется. Но если я нажму F7, я получу следующее:

Hello World!
[1]+  Stopped                 vim test.c

Я могу использовать fg чтобы снова запустить процесс, но это немного раздражает. Кто-нибудь знает, как это исправить?

2 ответа2

7

Не используйте интерактивную оболочку для выполнения команд. (Это i в -ic .)

По умолчанию shellcmdflag (-c) должен работать нормально.

Если вы указываете -i для того, чтобы заставить bash прочитать ваш файл .bashrc (что является побочным эффектом запуска интерактивной оболочки), тогда вам лучше просто сказать bash прочитать сценарий среды запуска. Цитирую man-страницу bash:

Когда bash запускается неинтерактивно, например, для запуска сценария оболочки он ищет переменную BASH_ENV в среде, расширяет ее значение, если оно там появляется, и использует расширенное значение в качестве имени файла для чтения и выполнения. , Bash ведет себя так, как будто была выполнена следующая команда:

          if [ -n "$BASH_ENV" ]; then . "$BASH_ENV"; fi

но значение PATH не используется для поиска имени файла.

Вы можете установить переменные окружения внутри vim с помощью :let

0

Я согласен, что не следует использовать интерактивную подоболочку, как указывает Ричи в своем ответе. (Я особенно высоко оценил анализ проблемы в его комментарии.)

Однако установка BASH_ENV опасна: если вы делаете это, вы должны убедиться, что Bash никогда не вызывается из этого файла, прямо или косвенно, иначе вы попадете в бесконечный цикл порождающих процессов Bash. Это может быть сложно, если у вас достаточно сложные настройки, поскольку легко не понять, что вызываемая вами программа на самом деле является скриптом Bash.

Мое решение состоит в том, чтобы просто set shell=bash-rcc , который является следующим скриптом:

#!/usr/bin/env bash
#
#   bash-rcc - source ~/.bashrc and run bash -c command
#
#   This is used as the shell by programs such as vim where we want
#   `:!` commands to be able to use shell functions and aliases
#   defined in `~/.bashrc` but do not want the shell started in
#   interactive mode. Interactive mode does various things, such as
#   setting up its own process group, that can cause problems when
#   used to run a single command from another program.

[[ $1 = -c ]] && shift
. ~/.bashrc
eval "$1"

Всё ещё ищете ответ? Посмотрите другие вопросы с метками .