Apa yang terjadi jika mv terganggu?

72

Apa yang terjadi jika mvperintah Linux terputus? Katakanlah, saya memindahkan seluruh direktori ke tempat lain dan menyela ketika sedang bergerak. Apakah direktori sumber masih belum tersentuh?

dehmann
sumber

Jawaban:

51

Jika Anda memindahkan direktori pada sistem file yang sama, Anda hanya memindahkan entri direktori dari satu lokasi di sistem file ke yang lain. Misalnya, mv /source/dir /target/dirakan menghapus entri direktori dirdari /sourcedan membuat yang baru masuk /target. Itu dilakukan oleh satu panggilan sistem atom (yaitu, tidak terputus). Inode yang berisi entri direktori dirserta konten sebenarnya dari direktori itu sendiri tidak terpengaruh.

Jika Anda memindahkan direktori dari satu sistem file ke sistem file lainnya, semua file pertama kali disalin ke sistem file baru dan kemudian dihapus tautannya dari yang asli. Jadi, jika Anda menyela mvsaat sedang menyalin, Anda mungkin berakhir dengan dua salinan dari beberapa file - di lokasi lama dan di yang baru.

bmk
sumber
6
@Wesley: Tidak, tidak akan ada file parsial. Jika sistem tetap menyala (misalnya, Anda menekan ctrl-C), itu akan dihapus secara otomatis. Jika tidak (mis., Kehilangan daya), file parsial mungkin ditinggalkan di suatu tempat yang tidak dapat diakses pada disk tujuan, tetapi harus dibersihkan oleh disk berikutnya fsck(yang kemungkinan besar akan berjalan secara otomatis saat reboot, karena disk tidak di-unmount dengan bersih).
Dave Sherohman
50
Salah. Jika Anda memindahkan dir dari satu fs ke yang lain mv / fs1 / dir / fs2 / dan Anda menyela, / fs1 / dir / akan tetap di sini sepenuhnya. / fs1 / dir dihapus hanya ketika langkah selesai.
8
user263131 benar. Jalankan strace mv /fs1/dir /fs2/- hal terakhir yang dilakukan mv adalah memanggil unlinkatsemua file sumber sekaligus (tidak satu per satu saat disalin).
Jakob
7
@JJ Sepertinya itu karena Anda menggunakan ekspansi bash, dalam hal ini mv memperlakukan setiap file dalam ekspansi sebagai sumber yang terpisah (dengan demikian melakukannya secara individual).
gkanwar
5
Jadi .... @bmk atau yang lain, apakah Anda ingin memperbarui jawaban ini menjadi kurang ... salah?
Artem Russakovskii
35

Implementasi GNU berulang pada argumen pada baris perintah, mencoba untuk mengubah nama terlebih dahulu, dan, jika gagal, secara rekursif menyalin dan kemudian secara rekursif menghapus sumber. Begitu

mv a b c/

akan menghapus a sebelum menyalin b , dan tidak akan mulai menghapus apa pun dalam a sebelum salinan tujuan selesai.

Perhatikan bahwa ini hanya berlaku untuk implementasi GNU.

Untuk memperjelas: jika a adalah direktori yang berisi d dan e , dan b adalah file, urutannya adalah

  • buat c / a
  • salin a / d -> c / a / d
  • salin a / e -> c / a / e
  • hapus a / d
  • hapus a / e
  • hapus a
  • salin b -> c / b
  • hapus b
Simon Richter
sumber
1
Bisakah Anda memberikan sumber untuk ini? Penjawab lain mengatakan file sumber dihapus segera setelah disalin ke fs yang berbeda (yaitu tidak semua disalin maka semua dihapus).
jamesbtate
1
Pengalaman. Saya telah menambahkan contoh untuk membuatnya lebih jelas bagaimana jawaban saya dan yang lainnya konsisten. Jika Anda hanya mendaftar file individual maka setiap file akan segera dihapus.
Simon Richter
Saya mengamati perilaku yang dijelaskan dalam jawaban ini pada macOS, yaitu, dengan BSD mvjuga, jadi itu bukan hanya GNU.
kirelagin
12

Anda memindahkan satu direktori, menghentikan gerakan, dan direktori asli akan tetap utuh:

$ mv a b/

Jika Anda memindahkan banyak direktori, masing-masing direktori akan utuh pada sumber atau tujuan, tergantung pada kapan Anda menyela:

$ mv a b c/

Bagaimana saya mendapat jawaban saya:

$ mv --version
mv (GNU coreutils) 8.21

$ info mv
... It first uses some of the same code that's used by `cp -a'
to copy the requested directories and files, then (assuming the copy
succeeded) it removes the originals.  If the copy fails, then the part
that was copied to the destination partition is removed.  If you were
to copy three directories from one partition to another and the copy of
the first directory succeeded, but the second didn't, the first would
be left on the destination partition and the second and third would be
left on the original partition.

Sebagai tes, saya menyalin folder besar ke direktori NFS, terputus, dan jumlah file di folder besar sumber saya tetap sama, dan sebagian konten dibiarkan di direktori NFS. Saya menggunakan "find. -Type f | wc -l" untuk memverifikasi.

Sepertinya jawaban Simon benar.

pengguna79878
sumber
9

Jawaban yang diterima jelas salah tentang pindah di antara sistem file - fakta yang menyelamatkan saya dari banyak masalah beberapa kali. Saat memindahkan direktori yang berisi subdirektori, tidak ada file dalam subdirektori yang akan dihapus sebelum seluruh subdirektori disalin. Ini adalah, btw, arti sebenarnya dari "objek demi objek" - subdirektori ADALAH objek (file) dan dengan demikian integritasnya harus dilestarikan dengan salinan lengkap di tempat tujuan sebelum sesuatu dapat dihapus. Jadi jawaban Simon nampak pada saya sebagai jawaban yang benar.

bhak
sumber
4

Tidak. Mv mengoperasikan objek demi objek, sehingga objek yang sudah diproses akan dihapus dari sumber.

Ignacio Vazquez-Abrams
sumber
2

Jelas tidak. Langkah ini dibuat objek demi objek. Oleh karena itu, objek yang dipindahkan ke tujuan hingga titik interupsi tidak akan ada lagi di sumbernya.

Jika mv dikeluarkan untuk file besar (antara berbeda) dan telah terputus maka sumbernya akan utuh. Pada target Anda akan melihat file yang tidak lengkap hingga titik gangguan.

Namun Anda dapat mengembalikan mv dengan perintah yang sama dan proses akan berlanjut.

g24l
sumber
2

Jika Anda ingin menginterupsi mv karena Anda ingin memutuskan sambungan dari terminal, Anda dapat mengirimkannya ke latar belakang:

* press Ctrl+Z

# bg
# disown
Курочка Ряба
sumber
1
Itu adalah poin yang bagus tetapi tidak menjawab pertanyaan yang sebenarnya.
Julie Pelletier
1
@JuliePelletier, tapi itulah yang saya cari sehingga seseorang mungkin tertarik melakukan ini.
Курочка Ряба