तर्क php exec () को bash script को सीमित करता है
परीक्षण करें कि php से bash script में 50000 तर्कों को पास करने में कितना समय लगेगा, यह बताता है कि मैं php से bash script में 1000 तर्क भी पास नहीं कर सकता, जब तक कि मैं नहीं कर सकता?
PHP:
$array = fetch_results_from_working_pool_temp_table (); $outputfile = "/var/www/html/outputFile";
$pidfile = "/var/www/html/pidFile"; $id = "";
$array_check=array(); foreach ( $array as $row => $column ) {
$id .= $column ['id'];
$id .= " "; } $cmd = "sudo /bin/bash /var/www/html/statistics/pass_all.sh {$id}"; exec( sprintf ( "%s >> %s 2>&1 & echo $! >> %s", $cmd, $outputfile, $pidfile ) ); bash: #!/bin/bash for ip in "$@"
do
echo "${ip}"
done
तो मेरी php ने bash को तर्क दिया , bash को आउटपुट में प्रिंट किया और साथ ही किसी भी त्रुटि के लिए। pidfile इस निष्पादन के साथ शुरू की गई प्रक्रिया का pid आयोजित करेगा। कमांड को निष्पादित भी नहीं किया जा रहा है क्योंकि मुझे कोई प्रक्रिया शुरू नहीं हुई है। क्या निष्पादन में पारित तर्कों के लिए कोई सीमा है? या PHP से या लिनक्स शेल में? मैं php 5.4 और लिनक्स रेडहैट 7 चला रहा हूं, मैं जीएनयू समानांतर का उपयोग करके प्रक्रियाएं चलाना चाहता हूं, लेकिन क्योंकि PHP एकल-थ्रेडेड है (इसे पास करने के लिए लाइब्रेरी हैं लेकिन मैं इससे बचना पसंद करूंगा)। हो सकता है कि मैं इसे किसी पाठ फ़ाइल में पास कर सकूं और इस पाठ फ़ाइल से खींचने वाली स्क्रिप्ट पर अमल कर सकूं? मदद!
** अद्यतन: मेरी मशीन सीमा: ** ●getgetf ARG_MAX 2097152 है # सुमीत-ए कोर फ़ाइल का आकार (ब्लॉक -c) 0 डेटा seg आकार (kbytes; -d) असीमित समयबद्धन प्राथमिकता (-ई) ० फ़ाइल का आकार (ब्लॉक, -f) असीमित लंबित संकेत (-आई) 256634 अधिकतम बंद मेमोरी (kbytes; -l) 64 अधिकतम स्मृति आकार (kbytes; -m) असीमित खुली फाइलें (-n) 1024 पाइप का आकार (512 बाइट्स, -पी) 8 POSIX संदेश कतार (बाइट्स, -q) 819200 वास्तविक समय प्राथमिकता (-आर) ० स्टैक आकार (kbytes; -s) 8192 सीपीयू समय (सेकंड, -t) असीमित अधिकतम उपयोगकर्ता प्रक्रिया (-यू) 4096 आभासी स्मृति (kbytes; -v) असीमित फ़ाइल ताले (-x) असीमित
जवाब
अधिकांश सिस्टम पर, कर्नेल execve()
syscall (कमांड लाइन args + एन्वायर्नमेंट वर्जन) के तर्कों के आकार को सीमित करता है । लिनक्स पर, सीमा अधिकतम स्टैक आकार से संबंधित है, हालांकि आमतौर पर आपको 8 एमबी की डिफ़ॉल्ट स्टैक आकार सीमा के लिए कम से कम 2 एमबी कुल मिलेगा। यह एकल तर्क को 128 केबी तक सीमित करता है , उदाहरण के लिए देखें क्या फ़ाइल नाम विस्तार (ग्लोबिंग) को बैश करने के लिए अधिकतम है और यदि हां, तो यह क्या है? और लिनक्स में पर्यावरण चर पर 128KiB सीमा बढ़ाएँ
यदि sh -c 'command line'
आप कॉल करते समय PHP चलाते हैं exec("command line")
तो तर्क -c
उस 128 kB सीमा से अधिक हो सकता है। तथ्य यह है कि कमांड लाइन बाद में शेल द्वारा अलग-अलग शब्दों में विभाजित हो जाती है, इससे मदद नहीं मिलेगी।
जब आपके पास यह कई तर्क होते हैं, तो आप उन्हें मानक इनपुट (स्टडिन) या फाइलों के माध्यम से जीएनयू समानांतर में पारित करना चाहते हैं।
मैं कुछ ऐसा करूंगा (अप्राप्त):
$f = popen("parallel","w"); fwrite($f,$commands); close ($f);
इस तरह आप अस्थायी फ़ाइल से बचने में सक्षम हो सकते हैं।
तो आपकी मदद से यहाँ मेरा समाधान है: PHP:
function scan_targets() {
$targetsFile= "[absolute path to the file]/targets"; $array_with_targets = fetch_from_db (); //function that gets me all the targets
$outputfile = "[absolute path to the file]/outputFile"; //output from parallel script $pidfile = "[absolute path to the file]/pidFile"; //PID of the process
$target = ""; foreach ( $array_with_targets as $row => $column ) {
$id .= $column ['id'];
$id .= " "; } file_put_contents($targetsFile, $ip) ; $cmd = "/bin/bash [absolute path to the file]/pass_targets.sh";
exec( sprintf ( "%s >> %s 2>&1 & echo $! >> %s", $cmd, $outputfile, $pidfile ) );
दे घुमा के:
#!/bin/bash
#appending arguments to the command
targets_array=()
IFS=" "
while read -r field || [ -n "$field" ]; do targets_array+=("$field")
done <[absolute path to the file]/targets
parallel bash [absolute path to the file]/check.sh ::: $targets_array
आप अपने समानांतर के साथ भी चला सकते हैं -दाल विकल्प के लिए अधिक संदर्भ है कि क्या हो रहा है, मैं 7h में लगभग 40.000 मेजबानों को स्कैन करने में कामयाब रहा। वेब सर्वर ने सेकंड में फ़ाइल के सभी लक्ष्यों को जोड़ा और जैसा कि मेरे निष्पादन ने एक पृष्ठभूमि प्रक्रिया का उपयोग किया है, परिणाम के लिए इंतजार नहीं करना पड़ता है (हम इसे फ़ाइल में आउटपुट कर रहे हैं)।
और check.sh स्क्रिप्ट किसी विशेष लक्ष्य के लिए मारीडब डेटाबेस रिकॉर्ड को भी अपडेट कर रहा है क्योंकि यह जाता है।