วิธีฆ่ากระบวนการ Linux ด้วยหมายเลขพอร์ต

เผยแพร่แล้ว: 2022-10-08
แล็ปท็อป Linux แสดง bash prompt
fatmawati achmad zaenuri/Shutterstock.com

ในการฆ่ากระบวนการ Linux คุณต้องมี ID หรือชื่อของมัน ถ้ารู้แค่พอร์ตที่ใช้ คุณยังสามารถฆ่ามันได้หรือไม่? ใช่ในหลายวิธี

กระบวนการฆ่า

บางครั้งกระบวนการ Linux อาจไม่ตอบสนอง อาจหยุดทำงานอย่างถูกต้อง หรืออาจทำงานต่อแต่ไม่สนใจคำขอให้ปิดเครื่อง หรือเริ่มกินหน่วยความจำ CPU หรือแบนด์วิดท์เครือข่าย

วิธีฆ่ากระบวนการจาก Linux Terminal
ที่เกี่ยวข้อง วิธีการฆ่ากระบวนการจากเทอร์มินัล Linux

ไม่ว่าแรงจูงใจของคุณจะเป็นเช่นไร มีวิธีฆ่ากระบวนการจากบรรทัดคำสั่ง Linux วิธีคลาสสิกคือการใช้คำสั่ง kill กับ ID กระบวนการของกระบวนการที่คุณต้องการยุติ คำสั่ง kill มีญาติสนิทบางส่วน คำสั่ง pkill จะฆ่าโปรเซสตามชื่อ และ killall จะฆ่าโปรเซสทั้งหมดที่สามารถค้นหาส่วนที่ใช้ร่วมกันของชื่อได้

หากสิ่งที่คุณรู้เกี่ยวกับกระบวนการคือการใช้พอร์ตบนคอมพิวเตอร์ของคุณ ก็ยังมีวิธีระบุและฆ่ามัน ในแง่ของเครือข่าย “พอร์ต” อาจหมายถึงการเชื่อมต่อทางกายภาพที่คุณเสียบสายเคเบิลด้วยปลั๊กที่ปลาย เช่น สายเครือข่าย CAT5 หรือ 6 หรืออาจหมายถึงพอร์ตซอฟต์แวร์

พอร์ตซอฟต์แวร์เป็นส่วนสุดท้ายของการเชื่อมต่อเครือข่าย ที่อยู่ IP ของอุปกรณ์ระบุคอมพิวเตอร์หรืออุปกรณ์เครือข่ายอื่นๆ แอปพลิเคชันภายในคอมพิวเตอร์ใช้พอร์ตต่างๆ สิ่งเหล่านี้ให้ความละเอียดในระดับอื่น การรับส่งข้อมูลเครือข่ายมาถึงคอมพิวเตอร์ที่ถูกต้องโดยใช้ที่อยู่ IP และด้วยการใช้ที่อยู่พอร์ต ข้อมูลดังกล่าวจะถูกส่งไปยังแอปพลิเคชันที่ถูกต้อง

เหมือนกับไปรษณียภัณฑ์ที่ส่งถึงโรงแรม แล้วจัดเรียงและส่งไปยังห้องที่เหมาะสม ที่อยู่ IP เปรียบเสมือนที่อยู่ของโรงแรม และหมายเลขห้องก็เหมือนหมายเลขพอร์ต

หากคุณเห็นกิจกรรมเครือข่ายบนพอร์ต และคุณไม่รู้จักกระบวนการที่สร้างมันขึ้นมา หรือพฤติกรรมของมันคือปัญหาหรือน่าสงสัย คุณอาจต้องการปิดกระบวนการ แม้ว่าสิ่งที่คุณรู้คือหมายเลขพอร์ต คุณก็สามารถติดตามกระบวนการและฆ่ามันได้

การสร้างการเชื่อมต่อกับ socat

เพื่อให้เรามีการเชื่อมต่อที่จะฆ่า เราจะใช้ socat เพื่อสร้างการเชื่อมต่อเครือข่ายโดยใช้โปรโตคอลที่แตกต่างกัน คุณจะต้องติดตั้ง socat ในการติดตั้งบน Ubuntu ให้ใช้คำสั่งนี้:

 sudo apt ติดตั้ง socat 

การติดตั้ง socat บน Ubuntu

บน Fedora ใช้ dnf :

 sudo dnf ติดตั้ง socat 

การติดตั้ง socat บน Fedora

บน Manjaro คุณต้องพิมพ์:

 sudo pacman -S socat 

การติดตั้ง socat บน Manjaro

วากยสัมพันธ์สำหรับ socat นั้นตรงไปตรงมาถ้าใช้ยาวไปหน่อย เราจำเป็นต้องระบุที่อยู่ต้นทางและปลายทาง สำหรับแต่ละสิ่งเหล่านี้ เราจำเป็นต้องจัดเตรียมโปรโตคอล ที่อยู่ IP และหมายเลขพอร์ต เราสามารถใช้แทน STDIN หรือ STDOUT เป็นแหล่งที่มาหรือปลายทางได้

คำสั่งนี้สร้างการเชื่อมต่อระหว่างซ็อกเก็ตฟัง TCP บนพอร์ต 7889 บนที่อยู่ IP แบบวนรอบ 127.0.0.1 และ STDOUT เครื่องหมาย " & " จะรันคำสั่งในเบื้องหลัง เพื่อให้เรายังคงเข้าถึงบรรทัดคำสั่งได้

 socat tcp-listen:7889,bind=127.0.0.1 stdout & 

การสร้างการเชื่อมต่อซ็อกเก็ต TCP ฟังด้วย socat

เราจะสร้างการเชื่อมต่อเพิ่มอีกสองรายการ เพื่อให้เราเลือกซ็อกเก็ตขนาดเล็กโดยใช้โปรโตคอลที่ต่างกัน เราจะสร้างการเชื่อมต่อ UDP และการเชื่อมต่อ SCTP ส่วนเดียวของคำสั่งที่เปลี่ยนแปลงคือโปรโตคอล

 socat udp-listen:7889,bind=127.0.0.1 stdout &
 socat sctp-listen:9999,bind=127.0.0.1 stdout & 

การสร้างการฟังการเชื่อมต่อซ็อกเก็ต UDP และ SCTP ด้วย socat

ที่เกี่ยวข้อง: อะไรคือความแตกต่างระหว่าง TCP และ UDP?

ใช้ Kill

แน่นอน เราสามารถใช้ kill เพื่อยุติกระบวนการได้ ตราบใดที่เรารู้ว่า ID ของกระบวนการคืออะไร ในการค้นหา PID เราสามารถใช้คำสั่ง lsof

ในการแสดงรายการรายละเอียดของกระบวนการบนพอร์ต 7889 ที่ใช้โปรโตคอล TCP เราใช้ตัวเลือก -i (ที่อยู่อินเทอร์เน็ต) เช่นนี้

 lsof -i tcp:7889 

การใช้ lsof เพื่อแสดงรายละเอียดของกระบวนการโดยใช้พอร์ตและโปรโตคอลเฉพาะ

PID ของกระบวนการนี้คือ 3141 และเราสามารถดำเนินการต่อด้วย kill :

 sudo ฆ่า 3141

เราสามารถช่วยตัวเองได้ถ้าเราใช้ท่อ หากเราไพพ์เอาต์พุตของ lsof ลงใน awk และบอกให้ awk ค้นหาบรรทัดที่มีพอร์ตที่เราสนใจ—7889—และพิมพ์ฟิลด์ที่สองจากบรรทัดนั้น เราจะแยก PID

 lsof -i tcp:7889 | awk '/7889{พิมพ์ $2}' 

วางเอาต์พุตของ lsof ลงใน awk

จากนั้นเราสามารถไพพ์เอาต์พุตจาก awk ไปยังคำสั่ง kill โดยใช้ xargs คำสั่ง xargs รับอินพุตแบบไพพ์และส่งผ่านไปยังคำสั่งอื่นเป็นพารามิเตอร์บรรทัดคำสั่ง เราจะใช้ xargs กับคำสั่ง kill

 lsof -i tcp:7889 | awk '/7889{พิมพ์ $2}' | xargs ฆ่า 

การใช้ไพพ์เพื่อนำเอาต์พุตของ lsof เป็น awk และจาก awk เป็น xargs และ kill

เราไม่ได้รับคำติชมด้วยภาพ ตามแบบฉบับของลินุกซ์ ไม่มีข่าวใดเป็นข่าวดี หากคุณต้องการตรวจสอบว่ากระบวนการถูกยกเลิก คุณสามารถใช้ lsof ได้อีกครั้ง

 lsof -i tcp:7889 

ใช้ lsof เพื่อค้นหารายละเอียดของกระบวนการโดยใช้พอร์ตและโปรโตคอลเฉพาะโดยไม่ประสบความสำเร็จ

เนื่องจาก lsof ไม่ได้รายงานอะไร เราจึงรู้ว่าไม่มีการเชื่อมต่อดังกล่าว

เราสามารถลบกระบวนการโดยใช้โปรโตคอล UDP ได้ง่ายๆ โดยแทนที่ “tcp” ด้วย “udp” ในคำสั่งก่อนหน้าของเรา

 lsof -i udp:7889 | awk '/7889{พิมพ์ $2}' | xargs ฆ่า 

การใช้ไพพ์เพื่อนำเอาต์พุตของ lsof เป็น awk และจาก awk เป็น xargs และ kill สำหรับซ็อกเก็ต UDP

อย่างไรก็ตาม lsof ไม่รู้จักโปรโตคอล SCTP

 lsof -i sctp:7889 

lsof ไม่ทำงานกับโปรโตคอล SCTP

เราสามารถใช้คำสั่ง ss ได้ เราใช้ตัวเลือก -S (SCTP) เพื่อค้นหาซ็อกเก็ต SCTP ตัวเลือก -a (ทั้งหมด) เพื่อค้นหาซ็อกเก็ตทุกประเภท (ฟัง ยอมรับ เชื่อมต่อ ฯลฯ) และตัวเลือก -p (กระบวนการ) เพื่อแสดงรายการรายละเอียดของกระบวนการโดยใช้ซ็อกเก็ต

 ss -ทรัพย์ 

การพิมพ์รายละเอียดของกระบวนการโดยใช้ซ็อกเก็ต SCTP ด้วย ss

เราสามารถแยกวิเคราะห์ผลลัพธ์นั้นโดยใช้ grep และ awk เราสามารถแยกวิเคราะห์ได้โดยใช้ grep และ PERL regexes แต่วิธีนี้เข้าใจง่ายกว่ามาก หากคุณกำลังจะใช้สิ่งนี้มากกว่าหนึ่งครั้งหรือสองครั้ง คุณอาจจะสร้างนามแฝงหรือฟังก์ชันเชลล์ออกมา

เราจะไพพ์เอาต์พุตจาก ss ไปที่ grep และค้นหาหมายเลขพอร์ตของเรา 7889 เราจะไพพ์เอาต์พุตจาก grep ไปที่ awk ใน awk เราใช้ตัวเลือก -F (สตริงตัวคั่น) เพื่อตั้งค่าเครื่องหมายจุลภาค “ , ” เป็นตัวคั่นฟิลด์ เราค้นหาสตริง ที่มี "pid=" และพิมพ์ฟิลด์ที่คั่นด้วยเครื่องหมายจุลภาคที่สองจากสตริงนั้น

 ss -ทรัพย์ | grep "7889" | awk -F',' '/pid=/{print $2}' 

การใช้ไพพ์เพื่อเชื่อมต่อ ss, grep และ awk เพื่อแยกสตริง PID

นั่นทำให้เรามีสตริง “pid=2859”

เราสามารถไพพ์มันใน awk อีกครั้ง ตั้งค่าตัวคั่นฟิลด์เป็นเครื่องหมายเท่ากับ “ = ” และพิมพ์ฟิลด์ที่สองจากสตริง นั้น ซึ่งจะเป็นข้อความที่อยู่ด้านหลังเครื่องหมายเท่ากับ

 ss -ทรัพย์ | grep "7889" | awk -F',' '/pid=/{print $2}' | awk -F'=' '{พิมพ์ $2}' 

การใช้ไพพ์เพื่อเชื่อมต่อ ss, grep และ awk สองครั้ง เพื่อแยก PID

ตอนนี้เราได้แยก ID กระบวนการแล้ว เราสามารถใช้ xargs เพื่อส่ง PID เพื่อ kill เป็นพารามิเตอร์บรรทัดคำสั่ง

 ss -ทรัพย์ | grep "7889" | awk -F',' '/pid=/{print $2}' | awk -F'=' '{print $2}' | xargs ฆ่า 

การใช้ไพพ์ที่มี ss, grep, awk และ xargs เพื่อยุติกระบวนการซ็อกเก็ต SCTP

นั่นฆ่ากระบวนการที่ใช้ซ็อกเก็ตโปรโตคอล SCTP บนพอร์ต 7889

คำสั่งฟิวเซอร์

คำสั่ง fuser ทำให้สิ่งต่างๆ ง่ายขึ้นมาก ข้อเสียคือใช้งานได้กับซ็อกเก็ต TCP และ UDP เท่านั้น ในด้านบวก ซ็อกเก็ตเหล่านี้เป็นซ็อกเก็ตทั่วไปสองประเภทที่คุณต้องจัดการ คำสั่ง fuser ได้รับการติดตั้งแล้วในคอมพิวเตอร์ Ubuntu, Fedora และ Manjaro ที่เราตรวจสอบ

สิ่งที่คุณต้องทำคือใช้ตัวเลือก -k (kill) และระบุพอร์ตและโปรโตคอล คุณสามารถใช้ตัวเลือก -n (เนมสเปซ) และระบุโปรโตคอลและพอร์ต หรือใช้ "ฟอร์เวิร์ดสแลชรูปแบบทางลัด" และใส่หมายเลขพอร์ตก่อน

 ฟิวเซอร์ -n tcp 7889
 ฟิวเซอร์7889/udp 

การใช้คำสั่งฟิวเซอร์เพื่อลบกระบวนการโดยใช้ซ็อกเก็ต TCP และ UDP

หมายเลขพอร์ต โปรโตคอล และ PID ของกระบวนการที่ยุติจะพิมพ์อยู่ในหน้าต่างเทอร์มินัล

ลองฟิวเซอร์ก่อน

มันอาจจะติดตั้งบนคอมพิวเตอร์ที่คุณกำลังทำงานอยู่ และโปรโตคอลน่าจะเป็น TCP หรือ UDP ดังนั้นจึงมีโอกาสมากที่วิธีที่ง่ายที่สุดจะได้ผลสำหรับคุณ