`<& -` क्या करता है?


20

मैंने बैश के एक स्निपेट को दूरस्थ रूप से निष्पादित ssh कमांड की पृष्ठभूमि के लिए कॉपी किया:

ssh user@remote <<CMD
some process <&- >log 2>error &
CMD

क्या करता <&-है?
मेरा अनुमान है कि यह वैसा ही है< /dev/null

मेरा अगला समझ है कि तीन मुख्य फ़ाइल वर्णनकर्ता (है stdin, stdout, stderr) को रोकने के लिए बंद कर दिया जाना चाहिए:

  1. नौकरी छिपी हुई है और पटकथा से बाहर निकलना - किसी भी तरह से संघर्ष करना?
  2. जब टर्मिनल बंद हो जाता है, तो टर्मिनल से स्टड को स्वीकार करने वाली सभी प्रक्रियाएं बंद हो जाती हैं?

अप्रचलित क्रॉस-संदर्भ: देखें कि शेल के नियंत्रण और पुनर्निर्देशन ऑपरेटर क्या हैं? - हालांकि यह सब इस ऑपरेटर के बारे में कहता है कि इसका उपयोग "फ़ाइल डिस्क्रिप्टर को बंद करने या डुप्लिकेट करने के लिए किया जा सकता है" और आपको "अपने शेल के मैनुअल के संबंधित अनुभाग को देखना चाहिए"।
जी-मैन का कहना है कि 'मोनिका' की बहाली

यदि मैं सही ढंग से याद करता हूं, ssh -nNT user@remote 'command'तो एक गैर-संवादात्मक एसएसएच सत्र बनाएगा। संलग्न &यह पृष्ठभूमि, आगे जोड़ते करने nohupके लिए commandकरता है, तो आपके कनेक्शन मरता चल इसे रखने के लिए।
मार्क के कोवान

1
@ मर्ककॉवन का man sshसुझाव है कि -N पूरी तरह से रिमोट कमांड चलाने में अक्षम है, और एक त्वरित परीक्षण इसका समर्थन करता है।
टॉम हंट

आह हाँ, मैंने रिवर्स पोर्ट फ़ॉरवर्डिंग के लिए -NNTR का उपयोग किया। -N और -R पर ध्यान न दें :)
मार्क के कोवान

जवाबों:


30

<&-के रूप में एक ही बात नहीं है< /dev/null<&-एफडी 0 को बंद कर देता है, जबकि < /dev/nullइसे डिवाइस से रीडायरेक्ट करता है /dev/null, जो कभी कोई डेटा प्रदान नहीं करता है और हमेशा पढ़ने पर ईओएफ देता है। अंतर ज्यादातर यह है कि एक read(2)बंद एफडी ( <&-केस) से एक कॉल EBADF के साथ त्रुटि करेगा, जबकि एक अशक्त-पुनर्निर्देशित एफडी से एक कॉल कोई बाइट्स नहीं पढ़ेगा (अंत-फ़ाइल की स्थिति)। यदि आपका कार्यक्रम कभी भी स्टड से नहीं पढ़ता है, तो अंतर कोई मायने नहीं रखता है।

अगर आप किसी चीज़ को बैकग्राउंड कर रहे हैं तो एफडी को बंद करना अच्छा अभ्यास है, क्योंकि टीटीवाई से कुछ भी पढ़ने की कोशिश करने पर बैकग्राउंड प्रोसेस लटक जाएगा। यह उदाहरण पूरी तरह से सब कुछ नहीं संभालना चाहिए, हालांकि; आदर्श रूप से पृष्ठभूमि प्रक्रिया को पूरी तरह से अलग करने के लिए कहीं न कहीं एक आह्वान nohupया setsidआह्वान होगा।


तो मुझे nohupफाइल डिस्क्रिप्टर को बंद करने के अलावा उपयोग करना चाहिए ?
एरिक फ्रांसिस

2
सबसे गहन विधि (जो कार्यक्रमों को नकल करने के तरीके की नकल करती है) कुछ इस तरह है setsid some process <&- >path/to/log 2>path/to/error। तेज विधि कुछ इस तरह है nohup some process &
टॉम हंट

2
@EricFrancis: nohupयहां कोई मतलब नहीं है। सिग्नल nohupप्राप्त करने से प्रक्रिया को रोकें HUPजब उसका नियंत्रण टर्मिनल बंद हो। लेकिन आपके पास इस मामले में कोई टर्मिनल नहीं था।
cuonglm

@TomHunt: पृष्ठभूमि प्रक्रिया लटका नहीं था, ssh सत्र किया था।
cuonglm

2
Fds 0, 1 & 2 को बंद करने के लिए एक अच्छा विचार नहीं है ... आप नहीं चाहते कि अगला fd उन मूल्यों में से एक को लेने के लिए बनाए। उन्हें / dev / null में पुनर्निर्देशित करने के लिए बेहतर है
मरे जेन्सेन

7

देखें man bash:

  [n]<&word

का उपयोग इनपुट फाइल के विवरणों को डुप्लिकेट करने के लिए किया जाता है। यदि wordएक या एक से अधिक अंकों तक फैलता है, तो जिस फाइल डिस्क्रिप्टर द्वारा निरूपित किया गया nहै, वह उस फाइल डिस्क्रिप्टर की एक प्रति है। यदि word इनपुट के लिए खुला कोई फ़ाइल डिस्क्रिप्टर निर्दिष्ट नहीं करता है, तो एक पुनर्निर्देशन त्रुटि होती है। यदि शब्द का मूल्यांकन करता है -, तो फ़ाइल डिस्क्रिप्टर nबंद है। यदि nनिर्दिष्ट नहीं किया गया है, तो मानक इनपुट (फ़ाइल डिस्क्रिप्टर 0) का उपयोग किया जाता है।


सही परिभाषा यह है कि यह अनिर्दिष्ट है कि क्या होता है जब आपके पास [n]<&wordऔर शब्द में एक से अधिक अंक होते हैं।
विद्वान

क्या मतलब? क्या man bashगलत है?
एरिक फ्रांसिस

@ EricFrancis क्योंकि यह मानक में अनिर्दिष्ट है, bashइसे एक समझदार तरीके से लागू करने के लिए चुनता है ("साने" की कुछ उपयुक्त परिभाषा के लिए)। अन्य गोले ऐसा कर भी सकते हैं और नहीं भी।
मुरु

@ मुरू प्रश्न टैग किया गया है bash, नहीं posix-shell
बारमर

@ बरम ओके। इसलिए...?
मूरू

7

<&- मानक इनपुट बंद करें।

सामान्य रूप, POSIX द्वारा परिभाषित किया गया है:

[n]<&word

फ़ाइल डिस्क्रिप्टर बनाने का इसका उद्देश्य nफ़ाइल डिस्क्रिप्टर द्वारा निरूपित फ़ाइल की एक प्रति है word। यदि मान लिया गया है तो मानक मान लिया nगया है, और यदि wordहै -, तो फ़ाइल विवरणक nबंद हो जाएगा।

यह वैसा नहीं है </dev/null, जब से मामले में </dev/null, मानक इनपुट अभी भी खोला गया था, और दूसरी जगह पर पुनर्निर्देशित किया गया था।

आपको प्रक्रियाओं के सभी फ़ाइल विवरणों को बंद करने की आवश्यकता है जो ssh सॉकेट से जुड़े थे, अन्यथा, ssh सत्र बंद नहीं हो सकता।

आप स्क्रीन या tmux का उपयोग करके इसे ssh सत्र में संलग्न किए बिना रिमोट मशीन पर कमांड चला सकते हैं :

ssh user@remote 'screen -S test -d -m command'

क्यों गिरा वोट?
congonglm
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.