Đặt một quá trình bắt đầu với! trong nền


8

Nếu tôi làm điều này từ vỏ:

$ sleep 100

Tôi có thể làm cho nó đi đến nền bằng cách làm:

^Z
$ bg

Và sau đó tiếp tục sử dụng vỏ của tôi. Bạn có thể có được hiệu ứng tương tự bằng cách thêm a &vào cuối lệnh, nhưng tôi thường quên điều này.

Trong Vim, tôi thường làm:

:!sleep 100

Và ở đây cũng vậy, tôi thường quên thêm &. Tôi có thể đặt quá trình này trong nền và tiếp tục sử dụng Vim như trong trình bao không?


1
Để tránh quên lần nữa, bạn có thể yêu cầu Vim nối thêm &mỗi lần: :nnoremap :! :!&<Left>... Nhưng tất nhiên, đôi khi bạn sẽ không muốn &và sẽ phải nhấn <Del> để xóa nó.
joeytwiddle

@joeytwiddle Đó là một ý tưởng hay và nghe có vẻ như là một câu trả lời mà bạn có thể viết như một câu trả lời, thay vì chỉ là một nhận xét :-)
Martin Tournoij 24/2/2015

Câu trả lời:


5

Như <C-z>sẽ đình chỉ Vim, không chỉ lệnh shell được khởi chạy, sẽ không hoạt động.

Những gì tôi sẽ làm là hủy bỏ lệnh chạy dài với <C-c>, sau đó khởi chạy lại cùng một lệnh trong nền thông qua

:!! &

( :!!Lệnh này có ích để gọi lại lệnh bên ngoài trước đó tại đây; bạn cũng có thể sử dụng lịch sử lệnh Ex thông qua <Up>.)


1
Đây chính xác là quy trình công việc tôi hy vọng sẽ cải thiện. Vấn đề là bạn cần đóng bất cứ thứ gì bạn bắt đầu ...
Martin Tournoij 24/2/2015

1

Bạn có thể đặt lệnh trong một kịch bản shell mà chính nó. Nội dung, ví dụ, có thể là:

#!/bin/sh
sleep 100 &

3
Sẽ không được sử dụng nhiều khi lệnh đã bắt đầu.
muru

Ý tôi là người ta có thể chạy script shell thay vì lệnh chậm. Có nền tảng chính nó làm giảm nhu cầu phải nhớ để làm điều đó trong thời gian chạy. Tôi đoán tôi không hiểu rõ trường hợp sử dụng. Nếu đó là cùng một lệnh mà tôi cứ quên làm nền, tôi sẽ sử dụng tập lệnh shell. Nếu điều này xảy ra với các lệnh tùy ý, tôi sẽ cân nhắc tạo thói quen chuyển sang hệ vỏ thực tế để làm như vậy.
Jon Carter

Tôi sử dụng tmuxtheo mặc định, nhưng vấn đề là phiên Vim của tôi (với các tệp đang mở và như vậy) vẫn vô dụng. Tôi có thể chuyển sang một khung khác và chạy tập lệnh của mình ở đó, nhưng đó là nhiều hành động hơn là :!gitk %ví dụ ... Điều sử dụng tập lệnh là tôi sẽ phải tạo trước nhiều tập lệnh này cho mỗi lệnh có thể. Có lẽ đó không phải là ý tưởng tồi đối với một số lệnh được sử dụng nhiều nhất (chẳng hạn như gitk& mupdf).
Martin Tournoij 24/2/2015

1

Thông thường khi một quá trình được bắt đầu, bạn không có nhiều quyền kiểm soát đối với nó ngoài việc chấm dứt nó ( Ctrl+ c) hoặc tạm dừng nó ( Ctrl+ z, nhưng bao gồm cả quá trình cha).

Tuy nhiên tùy thuộc vào loại quy trình và hệ điều hành, đây là một vài thủ thuật mà bạn có thể thử:

  • Gửi SIGTSTPhoặc SIGSTOPsẽ dừng quá trình (tín hiệu tương tự được gửi bởi Ctrl+ z) và SIGCONTsẽ tiếp tục (tiếp tục) quá trình. Kiểm tra với sleepkhông hoạt động, vì vậy bạn sẽ kiểm tra nó với phần mềm cụ thể cách nó xử lý các tín hiệu. Ví dụ

    killall -SIGSTOP sleep
    killall -SIGTSTP sleep
    kill -SIGTSTP PID
    

    SIGSTOP dừng quá trình dừng (không thể bị bắt hoặc bỏ qua)

    Tín hiệu dừng quá trình dừng SIGTSTP được tạo từ bàn phím

  • Gửi SIGHUPđến quá trình. Theo mặc định, tín hiệu này chấm dứt quá trình, tuy nhiên nếu quá trình thực hiện tín hiệu SIGHUP, nó sẽ tách khỏi việc kiểm soát tty và chạy lại trong nền với id tiến trình mới (thường được sử dụng với trình nền). Thật không may, nhiều ứng dụng không xử lý chính xác và đơn giản là chết (bao gồm sleep). Ví dụ

    killall -SIGHUP sleep
    

    SIGHUP chấm dứt quá trình treo thiết bị đầu cuối dòng

  • Giải pháp khác có thể sử dụng các công cụ như retty(reattach thành pseudo-tty), detach(tách một quy trình khỏi thiết bị đầu cuối), nohup( ngắt kết nối quy trình khỏi thiết bị đầu cuối ) hoặc gdb(đính kèm quy trình hiện có -pvà đóng mô tả tệp của nó như tty, ví dụ tương tự ).

Để biết thêm thông tin, hãy kiểm tra: Kiểm soát công việc (Unix) - Triển khai tại Wikipedia.

Xem thêm: man killhoặc man sigaction.


Thật kỳ lạ khi điều này hiệu quả với bạn. STOP / CONT chỉ nên tạm dừng và tiếp tục quá trình, không có gì hơn. Nó không hoạt động ở đây, trong cả console vim hoặc gvim.
derobert

1

Lưu ý : Câu trả lời này dường như chỉ hoạt động với tcshfishshell. Tôi cũng đã cố gắng bash, dash, mksh, và zsh, và nó không làm việc ở đó; Tôi không chắc chắn lý do tại sao, vì nếu tôi làm những hành động tương tự từ những vỏ mà không Vim, nó không làm việc như mong đợi ... ( :!lệnh được thực hiện mặc dù vỏ).

Tôi tình cờ sử dụng tcsh, vì vậy nó hoạt động với tôi ...

Bạn có thể sử dụng :set shell=/bin/tcshđể thiết lập vỏ của bạn; đây là toàn cầu, mặc dù. Vì vậy, chỉ sử dụng nó nếu bạn nghĩ rằng đây là một tính năng rất quan trọng :-)


^Zgửi SIGTSTPtín hiệu, bạn có thể gửi tín hiệu này với kill, sau đó sử dụng SIGCONTđể tiếp tục (tiếp tục) quá trình. Điều này sẽ tách quá trình từ Vim.

Vì khó hiển thị với điều này sleep(làm sao bạn biết nó vẫn tiếp tục thực thi?), Tôi sẽ sử dụng gitklàm ví dụ (nhưng bất kỳ chương trình GUI nào cũng sẽ làm):

Ví dụ trong Vim:

:!gitk %

Và sau đó trong một thiết bị đầu cuối khác:

$ ps ax | grep gitk
30105 pts/10   S+     0:00 -bin/tcsh -c gitk
30108 pts/10   Sl+    0:00 wish /sbin/gitk --

$ kill -TSTP 30108
$ kill -CONT 30108

Tất nhiên bạn cũng có thể sử dụng killall, hoặc pkill; ví dụ:

$ killall -TSTP wish
$ killall -CONST wish

Bạn cần phải mở một thiết bị đầu cuối khác, điều này không lý tưởng, nhưng nó sẽ cho phép bạn tiếp tục sử dụng cả Vim và quy trình bên ngoài của bạn.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.