วิธียกเลิกการต่อเชื่อมอุปกรณ์ที่ไม่ว่าง


246

ฉันมีแซมบ้าไดรฟ์ที่ผู้ใช้หลายคนเข้าถึงได้ทุกวัน ฉันมีรหัสเพื่อรับรู้ไดรฟ์ที่ใช้ร่วมกัน (จากตาราง SQL) และติดตั้งไว้ในไดเรกทอรีพิเศษที่ผู้ใช้ทุกคนสามารถเข้าถึงได้

ฉันต้องการทราบว่าถ้าฉันลบไดรฟ์ออกจากตาราง SQL ของฉัน (ทำให้เป็นแบบออฟไลน์ได้อย่างมีประสิทธิภาพ) ทำอย่างไรหรือแม้กระทั่งมีวิธียกเลิกการต่อเชื่อมอุปกรณ์ที่ไม่ว่างใช่ไหม จนถึงตอนนี้ฉันพบว่ารูปแบบใด ๆ ของumountใช้งานไม่ได้

ไม่สนใจความเป็นไปได้ที่จะทำลายข้อมูล - เป็นไปได้ไหมที่จะเลิกเมานท์อุปกรณ์ที่กำลังอ่านอยู่ในปัจจุบัน?


3
คำตอบอยู่ทั่วไปมากขึ้นสาเหตุอื่น ๆ อีกมากมายสำหรับความล้มเหลว umount จะพบได้ที่นี่oletange.blogspot.dk/2012/04/umount-device-is-busy-why.html
Ole Tange

2
สวัสดีบางทีคุณอาจcdจะเมานเดอร์จากนั้นคุณกลายเป็นรูตหรือเข้าสู่ระบบอีกครั้งจากนั้นเปลือกอื่น ๆ ติดอยู่ ทำexitบนเปลือกหอยทั้งหมด
Smeterlink

คำตอบ:


458

ใช่!! มีวิธีแยกอุปกรณ์ที่ไม่ว่างออกทันที (แม้ว่าอุปกรณ์นั้นจะไม่ว่างและไม่สามารถถอดออกได้) คุณสามารถล้างข้อมูลทั้งหมดในภายหลัง:

umount -l /PATH/OF/BUSY-DEVICE
umount -f /PATH/OF/BUSY-NFS(NETWORK-FILE-SYSTEM)

บันทึก:

  1. คำสั่งเหล่านี้สามารถขัดขวางกระบวนการทำงานทำให้ข้อมูลสูญหายหรือไฟล์เปิดเสียหาย โปรแกรมที่เข้าถึงไฟล์ DEVICE / NFS เป้าหมายอาจทำให้เกิดข้อผิดพลาดหรือไม่สามารถทำงานได้อย่างถูกต้องหลังจากบังคับให้ unmount
  2. ลองใช้คำสั่งเหล่านี้เมื่อไม่ได้อยู่ในโฟลเดอร์ / ไดรฟ์ / อุปกรณ์ที่เมาท์

22
หมายเหตุ: -lนี่คือตัวพิมพ์เล็กL(สำหรับ "ขี้เกียจเดินเท้า") (ดูคำตอบที่เกี่ยวข้อง )
ジョージ

4
ทำงาน หนึ่งความแตกต่างถ้าคุณเข้าสู่ระบบผ่านไคลเอนต์ FTP คุณต้องออกจากระบบเพื่อที่จะประสบความสำเร็จในการถอนติดตั้งโฟลเดอร์
Alexander Kim

พวกเขาไม่ทำงาน พวกเขาทั้งคู่เพิ่งจะตาย (เดเบียน 8, cifs-utils 2: 6.4-1)
Hubro

1
-l/ --lazyจะไม่เปิดไฟล์ที่เสียหาย แต่บน Linux ดูเหมือนว่า คุณไม่รู้ว่าเมื่อไรที่อุปกรณ์ถูกถอดออกและสามารถลบออกได้
Tom Hale

1
ค่อนข้างน่ากลัว ฉันขี้เกียจเดินเท้าแล้วประกอบใหม่ในขณะที่กระบวนการอื่นยังคงเข้าถึงอยู่ ดังนั้นฉันเดาฉันติดมันสองครั้งในที่สุดในตำแหน่งเดียวกันหรือไม่ ไม่แน่ใจในสิ่งที่ทำ
sudo

120

ถ้าเป็นไปได้ลองหา / ระบุกระบวนการที่ไม่ว่างฆ่ากระบวนการแล้วเลิกเมานท์แซมบ้าเพื่อลดความเสียหาย

  • lsof | grep '<mountpoint of /dev/sda1>' (หรืออะไรก็ตามที่อุปกรณ์ติดตั้งอยู่)

  • pkill target_process(ฆ่า proc ที่ไม่ว่างโดยใช้ชื่อ | kill PID| killall target_process)

  • umount /dev/sda1 (หรืออะไรก็ตามที่อุปกรณ์ติดตั้งอยู่)


6
แต่นั่นไม่ได้คืนอะไรเลย ฉันถือว่ามันเป็นไดรฟ์เครือข่ายและฉันไม่เห็นกระบวนการของคอมพิวเตอร์เครื่องอื่นที่เข้าถึงไดรฟ์ ข้อตกลงเดียวกันกับคำสั่ง "fuser"
สูงสุด

โอ้ ... คุณต้องการคำสั่ง samba ... / usr / bin / smbclient service <password>: ดูว่าสิ่งนี้ทำให้คุณเริ่มต้นได้หรือไม่ ... tldp.org/HOWTO/SMB-HOWTO-8.html
Frank Tudor

2
คำสั่ง smb เลิกใช้แล้วและแทนที่ด้วย "umount.cifs" .... ซึ่งยังใช้งานไม่ได้ ดูเหมือนว่าฉันติดอยู่กับที่ไม่สามารถนับในขณะที่ไม่ว่าง
สูงสุด

หากคุณกำลังใช้ Asuswrt-Merlin คุณต้องติดตั้งlsof:# opkg install lsof
Tonatio

1
คุณต้อง sudo lsof เพื่อให้ได้ผลลัพธ์บางอย่าง
aheigins

78

ตรวจสอบให้แน่ใจว่าคุณยังไม่ได้อยู่ในอุปกรณ์ที่เมานท์เมื่อคุณพยายามที่จะ umount


4
ว่าเพียงมีโฟลเดอร์ปัจจุบัน (ที่ตั้งอยู่บนอุปกรณ์เป้าหมาย) เปิดในสถานีของคุณ (ผ่านคำสั่ง cd เช่น) เป็น enaugh ที่จะหยุดกระบวนการ unmnounting :)
jave.web

2
ใช่ฉันมีเชลล์ที่ทำงานในไดเรกทอรีบนอุปกรณ์ ปิดหน้าต่างเทอร์มินัลและ voila
sh78

ยังให้แน่ใจว่ามีไม่อื่น ๆ umountที่ติดอยู่ภายในจุดหนึ่งที่คุณกำลังพยายามที่จะ
ชนะ

@victe ขอบคุณ; ฉันกำลังลอกโฟลเดอร์โดยใช้ pfexec mount -F vboxfs carpetacompartida ~ / เอกสารบน Solaris 11; แต่เอกสารมีโฟลเดอร์ย่อยและเป็นปัญหา
Dani Aya

44

ลองทำสิ่งต่อไปนี้ แต่ก่อนที่จะเรียกใช้โปรดทราบว่าการ-kตั้งค่าสถานะจะฆ่ากระบวนการที่กำลังทำงานอยู่ทำให้อุปกรณ์ไม่ว่าง

-iทำให้ธงfuserถามก่อนที่จะฆ่า

fuser -kim /address  # kill any processes accessing file
unmount /address

5
lsof | grep '/dev/<my-device>ไม่ได้คืนสิ่งใด แต่ใช้งานได้ดี! อาจต้องการแนะนำfuser -m /dev/<my-device>ในกรณีที่คุณต้องการค้นหากระบวนการก่อนที่จะฆ่า
modulitos

3
การรันคำสั่ง fuser ยกเลิกการเชื่อมต่อฉันทันทีจาก VPS
giorgio79

21

หลีกเลี่ยงการ umount -l

umount -lในช่วงเวลาของการเขียนคำตอบบนลงมติขอแนะนำให้ใช้

umount -lเป็นอันตรายหรือที่ดีที่สุดที่ไม่ปลอดภัย สรุป:

  • ไม่ได้เลิกเมานท์อุปกรณ์จริง ๆ เพียงแค่ลบระบบไฟล์ออกจากเนมสเปซ เขียนไปยังไฟล์ที่เปิดสามารถดำเนินการต่อ
  • มันอาจทำให้ระบบไฟล์ btrfs เสียหายได้

หลีกเลี่ยง / ทางเลือก

พฤติกรรมที่มีประโยชน์ของการumount -lซ่อนระบบไฟล์จากการเข้าถึงโดยชื่อพา ธสัมบูรณ์ซึ่งจะช่วยลดการใช้งาน moutpoint เพิ่มเติม

พฤติกรรมเดียวกันนี้สามารถทำได้โดยการติดตั้งไดเรกทอรีว่างที่มีสิทธิ์000ในการยกเลิกการเมานท์ไดเรกทอรี

จากนั้นการเข้าถึงชื่อไฟล์ใหม่ในด้านล่างจุดเมานท์นั้นจะเข้าสู่ไดเรกทอรีที่ทับซ้อนกันใหม่โดยไม่มีการอนุญาตศูนย์ - ตัวบล็อกใหม่ของ unmount จะถูกป้องกัน

ก่อนอื่นให้ลอง remount,ro

ความสำเร็จที่ไม่ได้ติดตั้งที่สำคัญที่จะปลดล็อคคือการติดตั้งใหม่แบบอ่านอย่างเดียว เมื่อคุณได้รับremount,roป้ายแสดงว่าคุณรู้ว่า:

  1. ข้อมูลที่ค้างอยู่ทั้งหมดถูกเขียนลงดิสก์
  2. ความพยายามในการเขียนในอนาคตทั้งหมดจะล้มเหลว
  3. ข้อมูลอยู่ในสถานะที่สอดคล้องกันหากคุณจำเป็นต้องถอดอุปกรณ์ออก

mount -o remount,ro /dev/device รับประกันว่าจะล้มเหลวหากมีไฟล์ที่เปิดสำหรับการเขียนดังนั้นลองตรงนั้น คุณอาจจะรู้สึกโชคดีพังค์!

หากคุณโชคไม่ดีให้มุ่งเน้นเฉพาะกระบวนการที่เปิดไฟล์สำหรับการเขียนเท่านั้น :

lsof +f -- /dev/<devicename> | awk 'NR==1 || $4~/[0-9]+[uw -]/'

จากนั้นคุณควรจะสามารถติดตั้งอุปกรณ์แบบอ่านอย่างเดียวและให้แน่ใจว่าสถานะที่สอดคล้องกัน

ถ้าคุณไม่สามารถ remount อ่านอย่างเดียว ณ จุดนี้การตรวจสอบบางส่วนของสาเหตุที่เป็นไปได้อื่น ๆ ที่ระบุไว้ที่นี่

ความสำเร็จแบบอ่านอย่างเดียวอีกครั้งปลดล็อค unlock

ขอแสดงความยินดีขณะนี้ข้อมูลของคุณบน mountpoint สอดคล้องกันและได้รับการปกป้องจากการเขียนในอนาคต

ทำไมถึงfuserด้อยกว่าlsof

ทำไมไม่ใช้ใช้fuserก่อนหน้า? คุณสามารถมี แต่ fuserทำงานกับไดเรกทอรีไม่ใช่อุปกรณ์ดังนั้นหากคุณต้องการลบจุดเมานท์จากพื้นที่ชื่อไฟล์และยังคงใช้อยู่fuserคุณจะต้อง:

  1. ทำซ้ำจุดเมานท์ชั่วคราวกับmount -o bind /media/hdd /mntตำแหน่งอื่น
  2. ซ่อนจุดเมานท์ดั้งเดิมและบล็อกเนมสเปซ:

นี่คือวิธี:

null_dir=$(sudo mktemp --directory --tmpdir empty.XXXXX")
sudo chmod 000 "$null_dir"

# A request to remount,ro will fail on a `-o bind,ro` duplicate if there are
# still files open for writing on the original as each mounted instance is
# checked.  https://unix.stackexchange.com/a/386570/143394
# So, avoid remount, and bind mount instead:
sudo mount -o bind,ro "$original" "$original_duplicate"

# Don't propagate/mirror the empty directory just about hide the original
sudo mount --make-private "$original_duplicate"

# Hide the original mountpoint
sudo mount -o bind,ro "$null_dir" "$original"

จากนั้นคุณจะมี:

  1. เนมสเปซดั้งเดิมถูกซ่อน (ไม่สามารถเปิดไฟล์ได้อีกต่อไปปัญหาจะไม่แย่ลง)
  2. ผูกติดซ้ำไดเรกทอรี (เมื่อเทียบกับอุปกรณ์) fuserที่จะเรียกใช้

นี่ซับซ้อนกว่า[1]แต่ให้คุณใช้:

fuser -vmMkiw <mountpoint>

ซึ่งจะขอให้โต้ตอบฆ่ากระบวนการด้วยไฟล์ที่เปิดสำหรับการเขียน แน่นอนคุณสามารถทำได้โดยไม่ต้องซ่อนจุดเมานท์เลยก็ได้ แต่การเลียนแบบข้างต้นumount -lไม่มีอันตรายใด ๆ

-wสวิตช์ข้อกำหนดด้านการเขียนกระบวนการและ-iมีการโต้ตอบดังนั้นหลังจากที่อ่านอย่างเดียว remount ถ้าคุณมันรีบร้อนแล้วคุณสามารถใช้:

fuser -vmMk <mountpoint>

เพื่อฆ่ากระบวนการที่เหลือทั้งหมดด้วยไฟล์ที่เปิดอยู่ใต้จุดเมานท์

หวังว่า ณ จุดนี้คุณสามารถยกเลิกการต่อเชื่อมอุปกรณ์ได้ (คุณจะต้องเรียกใช้umountบนจุดเมานท์สองครั้งหากคุณผูกเมาท์000ไดเร็กทอรีโหมดไว้ด้านบน)

หรือใช้:

fuser -vmMki <mountpoint>

เพื่อฆ่ากระบวนการแบบอ่านอย่างเดียวที่เหลืออยู่แบบบล็อกการ unmount

บ้าฉันยังได้รับtarget is busy!

ไฟล์ที่เปิดไม่ได้เป็นตัวบล็อก unmount เท่านั้น ดูที่นี่และที่นี่สำหรับสาเหตุอื่นและการแก้ไขของพวกเขา

แม้ว่าคุณจะมี gremlin ที่ซุ่มซ่อนอยู่ซึ่งทำให้คุณไม่สามารถถอดอุปกรณ์ได้อย่างสมบูรณ์ แต่อย่างน้อยคุณก็มีระบบไฟล์ของคุณอยู่ในสถานะที่สอดคล้องกัน

จากนั้นคุณสามารถใช้lsof +f -- /dev/deviceเพื่อแสดงรายการกระบวนการทั้งหมดด้วยไฟล์ที่เปิดอยู่บนอุปกรณ์ที่มีระบบไฟล์และจากนั้นฆ่าพวกเขา


[1] มันน้อยซับซ้อนกับการใช้mount --moveแต่ที่ต้องใช้ซึ่งมีผลกระทบmount --make-private /parent-mount-point โดยทั่วไปหากเมานต์เมาท์อยู่ภายใต้/ระบบไฟล์คุณต้องหลีกเลี่ยงสิ่งนี้


1
ถ้า --lazyอันตรายมากทำไมถึงไม่มีคำเตือนในumountหน้าคู่มือ? สิ่งที่กล่าวคือ " Lazy unmount แยกระบบไฟล์ออกจากลำดับชั้นไฟล์ในขณะนี้และล้างการอ้างอิงทั้งหมดไปยังระบบไฟล์นี้ทันทีที่ไม่ยุ่งอีกต่อไป "
bitinerant

7

ตรวจสอบระบบไฟล์ NFS ที่เอ็กซ์พอร์ตด้วย exportfs -v หากพบให้ลบออกด้วยไดเร็กทอรี exportfs -d: / สิ่งเหล่านี้จะไม่ปรากฏในรายการ fuser / lsof และสามารถป้องกันไม่ให้จำนวนที่ประสบความสำเร็จ


1
ขอบคุณสำหรับคำแนะนำนี้ ฉันต้องใช้ exportfs -ua เพื่อลบล็อค
FuePi

6

เช็คเอาท์ umount2 :

Linux 2.1.116 เพิ่มการเรียกระบบ umount2 () ซึ่งเช่นเดียวกับ umount () ให้ unmount เป้าหมาย แต่อนุญาตให้แฟล็กเพิ่มเติมควบคุมการทำงานของการดำเนินการ:

MNT_FORCE (ตั้งแต่ Linux 2.1.116) บังคับให้ unmount แม้ว่าจะไม่ว่าง (สำหรับการเมานต์ NFS เท่านั้น) MNT_DETACH (ตั้งแต่ Linux 2.4.11) ดำเนินการ unmount แบบขี้เกียจ: ทำให้จุดเชื่อมต่อไม่พร้อมใช้งานสำหรับการเข้าถึงใหม่และดำเนินการ unmount เมื่อจุดเมานท์สิ้นสุดการยุ่ง MNT_EXPIRE (ตั้งแต่ Linux 2.6.8) ทำเครื่องหมายที่จุดเชื่อมต่อว่าหมดอายุแล้ว หากไม่ได้ใช้จุดเมานท์ในขณะนี้การโทรเริ่มต้นไปยัง umount2 () ด้วยการตั้งค่าสถานะนี้ล้มเหลวด้วยข้อผิดพลาด EAGAIN แต่ทำเครื่องหมายจุดเชื่อมต่อว่าหมดอายุแล้ว จุดเมานท์ยังคงหมดอายุตราบใดที่ไม่สามารถเข้าถึงได้โดยกระบวนการใด ๆ การโทร umount2 () ครั้งที่สองที่ระบุ MNT_EXPIRE เลิกเมานท์จุดเมานท์ที่หมดอายุ ไม่สามารถระบุการตั้งค่าสถานะนี้ด้วย MNT_FORCE หรือ MNT_DETACH ส่งคืนค่า

เมื่อสำเร็จจะส่งคืนค่าศูนย์ เมื่อเกิดข้อผิดพลาด -1 จะถูกส่งกลับและ errno จะถูกตั้งค่าอย่างเหมาะสม


โดยไม่ได้ตั้งใจสิ่งเหล่านี้ไม่ใช่การติดตั้ง NFS แต่เป็น CIFS ฉันจะลองใช้ MNT_DETACH อย่างไรก็ตามถ้า umount -l ไม่ทำงานฉันไม่สามารถจินตนาการได้ว่ามันจะแตกต่างกันมาก ขอบคุณนะ!
สูงสุด

2

มีคนกล่าวว่าหากคุณใช้เทอร์มินัลและไดเรกทอรีปัจจุบันของคุณอยู่ในเส้นทางที่คุณต้องการยกเลิกการต่อเชื่อมคุณจะได้รับข้อผิดพลาด
ในกรณีนี้คุณlsof | grep path-to-be-unmountedต้องมีเอาต์พุตด้านล่าง:

bash ... path-to-be-unmounted

1

อีกทางเลือกหนึ่งเมื่อทำงานอะไรก็ได้แก้ไข/etc/fstabเพิ่มnoautoแฟล็กและรีบูตเครื่อง อุปกรณ์จะไม่ถูกเมานท์และเมื่อคุณทำสิ่งใดเสร็จแล้วให้ลบการตั้งค่าสถานะและรีบูตอีกครั้ง


0

คำตอบซอก:

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

sudo zpool export mypoo

แล้วยกเลิกการต่อเชื่อม

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.