2010-03-05 8 views
34

में प्रोग्राम चलाने के समय को सीमित करना लिनक्स में मैं एक प्रोग्राम चलाने के लिए चाहता हूं लेकिन केवल सीमित समय के लिए, जैसे कि 1 सेकंड। यदि कार्यक्रम इस चलने वाले समय से अधिक है तो मैं प्रक्रिया को मारना और एक त्रुटि संदेश दिखाना चाहता हूं।लिनक्स

उत्तर

38

स्टैक ओवरव्लो मुझे स्वीकार किए जाने के बाद से मेरा जवाब हटाने की अनुमति नहीं देगा। यह नीचे दिए गए बेहतर समाधान के साथ सूची के शीर्ष पर है क्योंकि यह नीचे वोट प्राप्त कर रहा है। यदि आप जीएनयू सिस्टम पर हैं, तो कृपया @12R24 द्वारा सुझाए गए अनुसार timeout का उपयोग करें। उम्मीद है कि आप नीचे मतदान बंद कर देंगे में तो, यहाँ यह कैसे काम करता है:

timeout 1s ./myProgram 

आप s, m, h या d सेकंड के लिए, मिनट, घंटे या दिन का उपयोग कर सकते हैं (डिफ़ॉल्ट अगर छोड़े गए)। यहां एक निफ्टी फीचर यह है कि आप किसी अन्य 30 सेकंड के बाद सिगकिल के साथ इसे मारने के लिए -k 30s (1s से पहले) निर्दिष्ट कर सकते हैं, इसे मूल SIGTERM का जवाब नहीं देना चाहिए।

एक बहुत ही उपयोगी टूल। अब नीचे स्क्रॉल करें और @ wRAR के उत्तर को वोट दें।


वंशावली के लिए, यह मेरा मूल - निम्न - सुझाव था, यह तब भी हो सकता है जब कुछ किसी के लिए उपयोग करें।

एक साधारण बैश स्क्रिप्ट है कि यह करना चाहिए करने के लिए है कि आप

./myProgram & 
sleep 1 
kill $! 2>/dev/null && echo "myProgram didn't finish" 

के लिए सक्षम होना चाहिए।

$! पिछली पृष्ठभूमि प्रक्रिया (& के उपयोग के माध्यम से) तक फैलता है, और किसी भी प्रक्रिया को मारने पर झूठी वापसी को मारता है, इसलिए गूंज केवल तभी निष्पादित की जाती है जब यह वास्तव में कुछ मार डाले।

2>/dev/null हत्या के स्टडर को रीडायरेक्ट करता है, अन्यथा यह आपको कुछ बताएगा कि यह प्रक्रिया को मारने में असमर्थ था।

आप अपनी प्रक्रिया से छुटकारा पाने के लिए -KILL या जो भी संकेत आप उपयोग करना चाहते हैं उसे जोड़ना चाहते हैं।

संपादित
रूप ephemient ने बताया, वहाँ एक दौड़ यहाँ अगर अपने कार्यक्रम खत्म और कुछ अन्य प्रक्रिया पीआईडी ​​छीन लेती है, यह बजाय मारे करेंगे। ऐसा होने की संभावना को कम करने के लिए, आप सिगचल पर प्रतिक्रिया दे सकते हैं और ऐसा होने पर इसे मारने की कोशिश नहीं करते हैं। गलत प्रक्रिया को मारने का अभी भी मौका है, लेकिन यह बहुत दूर है।

trapped="" 
trap 'trapped=yes' SIGCHLD 
./myProgram & 
sleep 1 
[ -z "$trapped" ] && kill $! 2>/dev/null && echo '...' 
+0

यह काम किया .. धन्यवाद – Overdeath

+1

शायद 'पीआईडी ​​= $!' को सहेजना चाहे, एक 'जाल' पीआईडी ​​= 'सिग्चाल्ड' सेट करें, और '[-एन $ पीआईडी] && $ pid को मार दें, ताकि आपके बच्चे से बाहर निकलने की संभावना (संभावना नहीं) और एक ही प्रक्रिया को एक ही पीआईडी ​​का पुन: उपयोग करना शुरू हो गया है, तो आप निर्दोष धारक को मार नहीं सकते हैं। – ephemient

+0

@ephemient: हाँ, मैंने भी इसे माना। पूरी तरह से दौड़ को खत्म नहीं करेगा, लेकिन यह निश्चित रूप से खिड़की को कम कर देगा। – falstro

3

आप उपयोग कर &

your_program & 
pid=$! 
sleep 1 
if [ `pgrep $pid` ] 
    then 
    kill $pid 
    echo "killed $pid because it took too long." 
fi 

आशा है कि आप विचार प्राप्त एक खोल स्क्रिप्ट में इसे लॉन्च कर सकता है, मुझे यकीन है कि यह सही है मेरे खोल कौशल कुछ ताज़ा :)

0

यदि आपके पास की जरूरत नहीं कर रहा हूँ स्रोत, आप fork()main() में शुरुआती कर सकते हैं और उसके बाद मूल प्रक्रिया समय को माप सकती है और संभवतः बाल प्रक्रिया को मार सकती है। बस मानक सिस्टम कॉल fork(), waitpid(), kill(), ... शायद कुछ मानक यूनिक्स सिग्नल हैंडलिंग का उपयोग करें। बहुत जटिल नहीं है लेकिन कुछ प्रयास करता है।

आप खोल पर कुछ भी स्क्रिप्ट कर सकते हैं हालांकि मुझे संदेह है कि यह 1 सेकंड के समय के संबंध में सटीक होगा।

यदि आप बस समय मापना चाहते हैं, तो खोल पर time <cmd ...> टाइप करें।

+0

इस तरह मैंने पहली बार ऐसा करने का विचार किया था। लेकिन मुझे स्रोत फ़ाइलों तक पहुंच के बिना प्रोग्राम को काम करने की ज़रूरत है। बहुत ही अच्छे दृष्टिकोण के लिए उत्तर – Overdeath

18

शायद सीपीयू समय सीमा (ulimit -t/setrlimit(RLIMIT_CPU)) मदद करेगा?

+0

+1 के लिए धन्यवाद! :) – falstro

+0

मैं कैसे जांच सकता हूं कि कार्यक्रम चलने वाले समय से अधिक है या नहीं? – Overdeath

+0

@ ओवरडिथ: आपको शायद अपना खुद का प्रोग्राम 'फोर्क', 'सेट्रलिमिट' और 'वेटपिड' बनाना होगा, और फिर जांचें कि क्या यह एक SIGXCPU द्वारा मारा गया है। आप अपने प्रोग्राम के रिटर्न वैल्यू को भी देख सकते हैं, बैश आमतौर पर सिग्नल द्वारा मारने पर कुछ उच्च ''?' सेट करता है। यह नहीं पता कि यह निर्धारित करना संभव है कि यह SIGXCPU है या नहीं। – falstro

1

ठीक है, तो बस एक छोटी सी प्रोग्राम है जो fork है, कहता है execlp या बच्चे में कुछ इसी तरह, माता पिता में समय का है और kill रों बच्चे लिखें। आसान होना चाहिए ...

88

आह ठीक है। timeout(1)

वर्णन
प्रारंभ कमान, और यह मारने अगर अभी भी DURATION के बाद चल रहा है।

+1

कृपया डाउनवॉटिंग पर टिप्पणी करें। – wRAR

+5

मुझे लगता है कि यहां कुछ गलतफहमी थी। एक साधारण "मैन टाइमआउट" यह दिखा सकता है कि यह जवाब हाथ से प्रश्न के लिए सबसे सटीक उत्तर (हालांकि कुछ संक्षेप में) है। –

+4

टाइमआउट (1) जीएनयू कोर्यूटिल्स में है। – minopret