सॉकेट lsof द्वारा पाया गया लेकिन नेटस्टैट द्वारा नहीं


19

मेरे पास एक एप्लिकेशन है जो फ़ाइल डिस्क्रिप्टर से बाहर चल रहा है, जाहिरा तौर पर सॉकेट खोलकर, लेकिन मुझे यह पता नहीं चल सकता है कि ये सॉकेट्स क्या करते हैं। ये lsof आउटपुट के रूप में दिखाई देते हैं

java    9689 appuser 1010u  sock       0,5          263746675 can't identify protocol
java    9689 appuser 1011u  sock       0,5          263746676 can't identify protocol
java    9689 appuser 1012u  sock       0,5          263746677 can't identify protocol
java    9689 appuser 1014u  sock       0,5          263746678 can't identify protocol
java    9689 appuser 1015u  sock       0,5          263746679 can't identify protocol
java    9689 appuser 1016u  sock       0,5          263746681 can't identify protocol

और के रूप में / खरीद / $ पीआईडी ​​/ एफडी

lrwx------ 1 appuser appuser 64 Jun 23 11:49 990 -> socket:[263732085]
lrwx------ 1 appuser appuser 64 Jun 23 11:49 991 -> socket:[263732086]
lrwx------ 1 appuser appuser 64 Jun 23 11:49 992 -> socket:[263735307]
lrwx------ 1 appuser appuser 64 Jun 23 11:49 993 -> socket:[263732088]
lrwx------ 1 appuser appuser 64 Jun 23 11:49 995 -> socket:[263735308]
lrwx------ 1 appuser appuser 64 Jun 23 11:49 996 -> socket:[263735309]
lrwx------ 1 appuser appuser 64 Jun 23 11:49 997 -> socket:[263745434]
lrwx------ 1 appuser appuser 64 Jun 23 11:49 998 -> socket:[263745435]
lrwx------ 1 appuser appuser 64 Jun 23 11:49 999 -> socket:[263745436]

लेकिन इसमें कोई समान आउटपुट नहीं है netstat -a

ये सॉकेट्स क्या हैं और मैं कैसे पता लगा सकता हूं कि वे क्या करते हैं?

संपादित करें : मैंने चलाने की कोशिश की है grep $SOCKET /proc/net, जैसा कि lsof FAQ में सुझाया गया है , जहां $ SOCKET उदाहरण के लिए 263746679 है, लेकिन इसने कोई परिणाम नहीं दिया।


पृष्ठभूमि के रूप में, एप्लिकेशन कई कार्यों के लिए एक कंटेनर है, जो दूसरों के बीच, नेटवर्क कॉल करता है। मुझे उस एक को बाहर करने की आवश्यकता है जो निडर हो जाता है, लेकिन जब तक मुझे यह पता नहीं चल जाता है कि उन लोगों ने किसके साथ संवाद किया है, मैं फंस गया हूं।


हम हाल ही में अपने एक .NET कोर वेब एप्स (उबंटू सर्वर के साथ Kestrel) में भी इस समस्या का सामना कर रहे हैं, लेकिन रिकॉर्ड किया गया डिवाइस "प्रोटोकॉल: टीसीपी" नाम के साथ "0,9" है। यह पता लगाने की कोशिश की जा रही है कि क्या उपकरण 0 और 9 मुश्किल साबित हुए हैं। लेकिन सभी लक्षण महसूस करते हैं कि बिना बंधन और उनका उपयोग किए बिना कुर्सियां ​​खोलने का एक ही मामला है।
icelava

जवाबों:


17

यदि आप सॉकेट बनाते हैं तो यह हो सकता है, लेकिन इसके साथ कभी भी कनेक्ट () या बाइंड () न करें। आपका सबसे अच्छा शर्त एप्लिकेशन को (-fF) स्ट्रेस करना हो सकता है, और फिर lsof के आउटपुट के साथ क्रॉस-रेफरेंस यह निर्धारित करने के लिए कि कौन सी सॉकेट्स समस्या पैदा कर रहे हैं। डिबगिंग की एक बोनस विधि के रूप में: यदि आप डिबगिंग जानकारी के साथ अपने सॉकेट कॉल को लपेटते हैं और उन्हें / dev / null को लिखते हैं, तो यह आपको प्रफुल्लित करने वाली बड़ी लॉग फ़ाइलों के बिना स्ट्रेस में दिखाई देगा।


धन्यवाद, यह दिलचस्प लगता है। मैं यह पता लगाने की कोशिश करूंगा कि क्या वास्तव में हमारे आवेदन के साथ ऐसा है।
रॉबर्ट मुंटेनू

1
कुछ हद तक एक ही लाइन के साथ, क्योंकि यह जावा का उपयोग करने के लिए बहुत कठिन हो सकता है; एक बेहतर तरीका यह हो सकता है कि आप अपना स्वयं का सॉकेट उपवर्ग बनाएं, जो माता-पिता (वास्तविक) के JDK सॉकेट में जाने से पहले जानकारी लॉग करता है। स्ट्रेस केवल ओएस में अंतर्निहित जावा कॉल्स को देख सकता है और आपके थ्रेड्स के अंदर नहीं देख सकता है कि वास्तव में उन सॉकेट कॉल्स क्या कर रहे हैं, यह स्ट्रेस करने के लिए यह सिर्फ एक बड़ी गेंद जावा की तरह दिखता है।
ट्रायेंगल

@troyengel: मैंने (री) बाइटमैन की खोज की है ( jboss.org/byteman ) एक बहुत ही साफ-सुथरा उपकरण जो मुझे इन कॉलों को ट्रेस करने के लिए आवश्यक बायटेकोड को इंजेक्ट करने की अनुमति देता है।
रॉबर्ट मुंटेनु

सबसे उपयोगी जवाब, तो यह इनाम मिलता है। धन्यवाद!
रॉबर्ट मंटीनू

2

पायथन का उपयोग करते हुए, मुझे एसएसएल सॉकेट्स पर समान समस्या का सामना करना पड़ा है:

  • जब मैं सॉकेट का उपयोग करता हूँ। क्लोज़ (), सॉकेट अनिश्चित समय के लिए CLOSE_WAIT स्थिति में रहता है
  • जब मैं सॉकेट.शटडाउन () का उपयोग करता हूं, तो lsof का कहना है कि "प्रोटोकॉल की पहचान नहीं कर सकता"

बंद करने से पहले समाधान एसएसएल परत को खोलना था:

  • ओरिगोसक = सॉकेट.यून्प्रैप ()
  • origsock.close ()

यह मेरे ऐप में सॉकेट्स को ठीक से बंद कर देता है।


1

यदि आपकी फ़ाइल डिस्क्रिप्टर की सीमा है, तो पहली बात जो मैं करना चाहूंगा, वह है:

~# vi /etc/sysctl.conf
fs.file-max = 331287

आगे मैं यह सुनिश्चित करूंगा कि आपका सिस्टम अद्यतित है, इसमें सभी लाइब्रेरी और सर्वर शामिल हैं। यह संभव है कि आपका जावा एप्लिकेशन सर्वर पुराना हो (यदि आप एक का उपयोग कर रहे हैं)। यह भी एक संभावना है कि आपका एप्लिकेशन सर्वर गलत है, आपको अपनी कॉन्फ़िगरेशन फ़ाइल को देखना चाहिए और अपने connectionTimeoutऔर / या अपने को कम करना चाहिए maxKeepAliveRequests(मुझे यकीन नहीं है कि आपके द्वारा उपयोग किए जा रहे एप्लिकेशन सर्वर का उपयोग कर रहा है या नहीं ...)

मुझे यकीन नहीं है कि यह एप्लिकेशन क्या करता है, लेकिन अगर आपको नहीं लगता कि इसमें दसियों हज़ार सॉकेट्स की आवश्यकता है, तो यह लगभग निश्चित रूप से आपके जावा एप्लिकेशन में एक "फाइल डिस्क्रिप्टर लीक" है। आपको विक्रेता को बग रिपोर्ट भेजनी पड़ सकती है। इस बग रिपोर्ट में आपको समस्या को फिर से बनाने के बारे में जानकारी शामिल करनी चाहिए।

इस मुद्दे को डीबग करने के कुछ तरीके यहां दिए गए हैं।

Wireshark (या cli के लिए twireshark) यह देखने के लिए सबसे अच्छा उपकरण है कि इन सॉकेट्स का उपयोग कैसे किया जा रहा है। तार के ऊपर फेंके जाने वाले ट्रैफ़िक के ब्रेक डाउन से आपको विंडशार्क मिलेगा। इसकी संभावना है कि पहले कुछ कनेक्शन सफल होंगे और फिर यह फाइल डिस्क्रिप्टर की सीमा से टकराएगा। एक बार जब फ़ाइल डिस्क्रिप्टर की सीमा हिट हो जाती है, तो विंडशर्क किसी भी चीज़ को लेने नहीं जाता है (और उस मामले के लिए नेकस्टैट), लेकिन इससे समस्या को कम करने में मदद मिलेगी। हो सकता है कि ऐसा मामला जहां बहुत सारे निवर्तमान एसवाईएन भेजे जा रहे हों, हालांकि एसवाईएन / एसीके प्राप्त नहीं किए जा रहे हैं, इसलिए बहुत सारे टीसीपी कनेक्शन सिर्फ एसवाईएन_डब्ल्यूआईटी राज्य में अटके हुए हैं।

यदि आपके पास स्रोत कोड तक पहुंच है और आप जानते हैं कि किस प्रकार के सॉकेट बनाए जा रहे हैं (जैसे कि स्ट्रेस का उपयोग करना या बस कोड खोजना) तो आप प्रोजेक्ट को ग्रहण (या किसी अन्य आईडीई) में खोल सकते हैं और फ़ंक्शन पर ब्रेक पॉइंट सेट कर सकते हैं ये सॉकेट्स बना रहा है। जब ब्रेकपॉइंट हिट हो जाता है, तो आप स्टैक ट्रेस को देख सकते हैं। यह फ़ाइल डिस्क्रिप्टर लीक शायद एक साधारण अनंत लूप या शायद सॉकेट टाइमआउट मूल्य बहुत बड़ा है। एक और संभावना यह है कि जावा ऐप socket.close()कनेक्शन को साफ करने के लिए नहीं कर रहा है । बंद करना आमतौर पर एक के finelyब्लॉक में किया जाता है try/catch(हाँ एक सॉकेट हमेशा जावा में एक कोशिश / पकड़ होना चाहिए या यह निर्माण नहीं करेगा :)। दिन के अंत में इसकी संभावना है कि जावा ऐप अपने IOException के ठीक से संचालन नहीं कर रहा है।


जवाब के लिए धन्यवाद। मैं वास्तव में इस एप्लिकेशन को विकसित कर रहा हूं - कंटेनर भाग - केवल इसे प्रबंधित करने के बजाय, और मैं सॉकेट्स से संबंधित किसी भी समस्या को बंद नहीं कर पा रहा था। लेकिन वायरशार्क / ट्वायरशार्क संकेत अच्छा है, मैं इसका उपयोग करूंगा।
रॉबर्ट मंटीनू

@ रोबर्ट मुन्नेयू यदि आप इस ऐप का निर्माण कर रहे हैं तो यह स्टेंटओवरफ्लो के लिए एक सवाल है। कभी कम आप बहुत अधिक सॉकेट खोल रहे हैं।
रूक

Rook: मैंने इस कोड-वार को खोजने पर छोड़ दिया, और इसे एक sysadmin के रूप में ट्रैक करने का प्रयास किया। इसलिए मैंने एसएफ पर पोस्ट किया। और हाँ, मुझे पता है कि किसी तरह बहुत सारे सॉकेट खुले हैं। लेकिन वहाँ शून्य सुराग के रूप में कर रहे हैं ...
रॉबर्ट Munteanu

@ रोबर्ट मुन्नेउ आपको सॉकेट निर्माण पर ब्रेक पॉइंट सेट करना होगा और उस बिंदु पर स्टैक ट्रेस और मेमोरी को देखना होगा। मुझे संदेह है कि आप एक अनंत पाश में पड़ रहे हैं। किसी भी चर और कदम को देखने में सक्षम होना हालांकि आपका कोड इस तरह की जटिल समस्याओं के लिए सबसे अच्छा तरीका है।
रूक

दुर्भाग्य से ऐसा हुआ, यह 20 सर्वरों में से एक पर यादृच्छिक रूप से होता है - हमेशा एक जैसा नहीं - केवल उत्पादन वातावरण में, और शायद प्रति सप्ताह दो बार। वरना उंगली बाहर निकालना आसान होता। वर्तमान में मैं सॉकेट निर्माण / बाइंड / कनेक्ट / क्लोज कॉल को ट्रैक करने के लिए Byteman ( jboss.org/byteman ) का उपयोग कर रहा हूं । उम्मीद है कि इससे कुछ निकलेगा।
रॉबर्ट मंटीनू
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.