बैश पूरा होने से बैश धीरे-धीरे शुरू होता है


15

मेरे ubuntu सिस्टम पर बैश शुरू करने में लगभग 2 सेकंड का समय लगता है। अगर मैं .bashrc में लोडिंग / etc / bash_completition हटाता हूं तो यह बिना देरी के शुरू होता है। बेशक, मैं पूर्णता नहीं छोड़ना चाहता और मुझे नहीं लगता कि उस फ़ाइल को 2 सेकंड की देरी के लिए वैध कारण बताया गया है।

किसी भी विचार मैं कैसे पता लगा सकता हूं कि समस्या क्या है या मैं चीजों को कैसे गति दे सकता हूं।


यह / बिन / बैश है? - कोशिश करो / बिन / डैश थोड़ा तेज हो सकता है।
साइरक्स

3
यही कारण है कि मैंने बैश-पूरा करने की स्थापना रद्द की
Vi।

जवाबों:


8

2013 में अपडेट: अधिकांश बैश-पूर्ति को केवल जरूरत पड़ने पर ऑटोलैड पूर्णता के लिए फिर से लिखा गया था। कोर लिपि अब बहुत ज्यादा लयबद्ध है।


पूर्ण स्क्रिप्ट कभी-कभी शेल स्क्रिप्ट मानकों में भारी हो सकती है । एक सर्वर पर मेरी पहुंच है, यह लगभग 1700 लाइनें (57 KB) है और यह सिर्फ मुख्य स्क्रिप्ट है । में /etc/bash_completion.dदेखते हैं ~ विभिन्न अन्य आदेश के लिए 200 अतिरिक्त लिपियों ( openssl, mutt, mount...) 25,537 लाइनों या 1.2 एमबी कुल। प्रत्येक स्क्रिप्ट, जब खट्टा हो जाता है, जाँच करता है कि क्या कमांड वास्तव में उपलब्ध हैंडलर को परिभाषित करने से पहले उपलब्ध है; ~ इस मामले में 330 बार, जिनमें से प्रत्येक में $PATHकिसी दिए गए नाम के साथ निष्पादन योग्य फ़ाइल की जाँच शामिल है । (हालांकि मुझे /usr/binस्मृति में कैश होने की उम्मीद है ...)

बेशक, यहां तक कि केवल आधा सेकंड का समय लगता है, दो पूर्ण सेकंड नहीं। लेकिन यह समस्या का कम से कम हिस्सा हो सकता है। चलाना चाहते हैं du -hs /etc/bash_completion*या wc -l /etc/bash_completion{,.d/*} | grep totalजाँच करना चाहते हैं।


आप स्क्रिप्ट को "ट्रेस" मोड में मैन्युअल रूप से सोर्स करने की कोशिश कर सकते हैं:

set -x
. /etc/bash_completion

निष्पादित होते ही आपको प्रत्येक पंक्ति दिखाई देगी। यदि कोई विशेष आदेश है जिसमें एक लंबा समय लगता है, तो आपको इसे नोटिस करना चाहिए।

( set +xट्रेस मोड अक्षम करता है।)


सरलीकृत पाठ मोड में भी रेंगना सुविधा? यह आपके विचार से अधिक संभावना है।
वि।

@Vi: zsh देखने के बाद अपनी स्टार्टअप स्क्रिप्ट को बाइटकोड के लिए संकलित करें ...
user1686

1
धन्यवाद। यह वास्तव में आसान था। अफसोस की बात है कि सभी आदेश अलग-अलग नहीं थे। तो यह इसकी वास्तव में बड़े पैमाने पर राशि की तरह लग रहा है जो समस्या पैदा कर रहा है।
15:75 पर user75250

12

मुझे थोड़ा हैकिश समाधान मिला जो काफी हद तक काम करता है।

समाधान

~/.bashrcजोड़ने के तल पर :

जाल 'स्रोत / आदि / bash_completion; जाल USR1 'USR1
{नींद 0.1; बिलियन किल -USR1 $$; } और डिसाइड किया गया

व्याख्या

trap 'source /etc/bash_completion ; trap USR1' USR1

शेल को सिग्नल प्राप्त होने पर चलाने के लिए हैंडलर सेट करें SIGUSR1; हैंडलर पूरा लोड करेगा और इसलिए यह खुद को निष्क्रिय कर देगा।

{ sleep 0.1 ; builtin kill -USR1 $$ ; } & disown

असिंक्रोनस रूप से थोड़ा इंतजार करें फिर सिग्नल को वर्तमान शेल में भेजें। प्रक्रिया नियंत्रण प्रतिक्रिया disownको दबाने के लिए आवश्यक है bashsleepअतुल्यकालिक काम करने के लिए आवश्यक है।

समस्या

किसी कारण से इस शेल को जारी किया गया पहला आदेश इतिहास में दर्ज नहीं किया जाएगा।


1
यह एक स्टार्टअप को बढ़ावा देता नहीं दिखता है - time bash -lc true0.26 के साथ उच्च संख्या की time source /etc/bash_completionरिपोर्ट करने पर भी, इसके साथ या इसके बिना ~ 0.12s रिपोर्ट करता है। क्या यह प्रभावी रूप से तय किया गया है ?
l0b0

मैं नहीं जानता कि अगर time bash -lc trueयहाँ ठीक से काम करता है तो trueइससे पहले ~0.1sकि यह कुछ भी स्रोत नहीं है खत्म कर देता है। वैसे भी time source /etc/bash_completion~ 0.17 यहां रिपोर्ट करता है और उस समय के बारे में है जब मुझे PS1प्रकट होने की प्रतीक्षा करने की आवश्यकता होती है।
cYrus

2
सरल! स्पष्टीकरण में, ट्रैप कमांड USR1अंत में याद आती है ।
फिश मॉनिटर

SIGUSR के साथ, सिग्नल हैंडलर तब तक लागू नहीं किया जाता है जब तक कि मैं शेल प्रॉम्प्ट में एंटर नहीं करता हूं। इस बिंदु पर एक ठहराव है, जबकि यह चलता है। मैंने SIGQUIT पर स्विच किया और यह ठीक काम करने लगता है।
जॉन नलले

5

आपको bash_completion के नवीनतम संस्करण (2.0) का उपयोग करना चाहिए। यदि आप डेबियन का उपयोग कर रहे हैं, तो यह मट्ठे में है, लेकिन इसका किसी अन्य मट्ठे के पैकेज पर कोई निर्भरता नहीं है, इसलिए आप इसे बिना किसी समस्या के निचोड़ पर स्थापित कर सकते हैं।

नवीनतम संस्करण उड़ान पर गतिशील रूप से पूरा लोड करता है, इसलिए इसने मेरे लिए कम से कम 10x से शीघ्र लोड समय को विभाजित किया।


1

आप एक प्लेसहोल्डर का उपयोग कर सकते हैं जब पूर्णता लोड हो रही हो; यह आपकी आँखों को चकरा देने के लिए पर्याप्त होना चाहिए। यह स्पष्ट रूप से केवल तभी काम करता है जब source /etc/bash_completionआपके द्वारा पहले शेल कमांड को टाइप करने और जारी करने के लिए आवश्यक समय से कम समय हो, अन्यथा यह विलंबित भी होगा।

यह विचार एक नकली प्रतिध्वनित करने के लिए है PS1, स्रोत को पूरा करता है और अंत में टर्मिनल को मिटा देता है।

मान लीजिए कि आपका PS1है \u@\h:\w\$, वे आप कुछ इस तरह लिख सकते हैं:

echo -ne "$USER@$HOSTNAME:${PWD/$HOME/\~}\$ "
source /etc/bash_completion
echo -ne '\e[2J\e[H'

कहाँ पे:

  • 2J टर्मिनल को मिटा देता है;
  • H कर्सर को ऊपरी दाएं कोने में ले जाएं।

नोट: आप जाँच सकते हैं कि उपयोगकर्ता रूट है और निरंतरता के #बजाय उपयोग करता है $:

echo -ne "...$([ $UID = 0 ] && echo '#' || echo '$') "

नोट: हटाने \e[2Jसे फ़्लिकरिंग से बचा जाता है लेकिन यह जंक वर्णों को छोड़ देगा यदि प्लेसहोल्डर वास्तविक प्रॉम्प्ट से अधिक लंबा हो।

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