কেন rmdir এবং দুটি পৃথক সিস্টেম কল লিঙ্কমুক্ত করা হয়?


10

এখানে এমন কিছু যা আমাকে কিছুক্ষণ ভাবতে থাকল:

[15:40:50][/tmp]$ mkdir a
[15:40:52][/tmp]$ strace rmdir a
execve("/usr/bin/rmdir", ["rmdir", "a"], [/* 78 vars */]) = 0
brk(0)                                  = 0x11bb000
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7ff3772c3000
access("/etc/ld.so.preload", R_OK)      = -1 ENOENT (No such file or directory)
open("/etc/ld.so.cache", O_RDONLY|O_CLOEXEC) = 3
fstat(3, {st_mode=S_IFREG|0644, st_size=245801, ...}) = 0
mmap(NULL, 245801, PROT_READ, MAP_PRIVATE, 3, 0) = 0x7ff377286000
close(3)                                = 0
open("/lib64/libc.so.6", O_RDONLY|O_CLOEXEC) = 3
read(3, "\177ELF\2\1\1\3\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0p\36\3428<\0\0\0"..., 832) = 832
fstat(3, {st_mode=S_IFREG|0755, st_size=2100672, ...}) = 0
mmap(0x3c38e00000, 3924576, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x3c38e00000
mprotect(0x3c38fb4000, 2097152, PROT_NONE) = 0
mmap(0x3c391b4000, 24576, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x1b4000) = 0x3c391b4000
mmap(0x3c391ba000, 16992, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x3c391ba000
close(3)                                = 0
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7ff377285000
mmap(NULL, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7ff377283000
arch_prctl(ARCH_SET_FS, 0x7ff377283740) = 0
mprotect(0x609000, 4096, PROT_READ)     = 0
mprotect(0x3c391b4000, 16384, PROT_READ) = 0
mprotect(0x3c38c1f000, 4096, PROT_READ) = 0
munmap(0x7ff377286000, 245801)          = 0
brk(0)                                  = 0x11bb000
brk(0x11dc000)                          = 0x11dc000
brk(0)                                  = 0x11dc000
open("/usr/lib/locale/locale-archive", O_RDONLY|O_CLOEXEC) = 3
fstat(3, {st_mode=S_IFREG|0644, st_size=106070960, ...}) = 0
mmap(NULL, 106070960, PROT_READ, MAP_PRIVATE, 3, 0) = 0x7ff370d5a000
close(3)                                = 0
rmdir("a")                              = 0
close(1)                                = 0
close(2)                                = 0
exit_group(0)                           = ?
+++ exited with 0 +++
[15:40:55][/tmp]$ touch a
[15:41:16][/tmp]$ strace rm a
execve("/usr/bin/rm", ["rm", "a"], [/* 78 vars */]) = 0
brk(0)                                  = 0xfa8000
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f3b2388a000
access("/etc/ld.so.preload", R_OK)      = -1 ENOENT (No such file or directory)
open("/etc/ld.so.cache", O_RDONLY|O_CLOEXEC) = 3
fstat(3, {st_mode=S_IFREG|0644, st_size=245801, ...}) = 0
mmap(NULL, 245801, PROT_READ, MAP_PRIVATE, 3, 0) = 0x7f3b2384d000
close(3)                                = 0
open("/lib64/libc.so.6", O_RDONLY|O_CLOEXEC) = 3
read(3, "\177ELF\2\1\1\3\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0p\36\3428<\0\0\0"..., 832) = 832
fstat(3, {st_mode=S_IFREG|0755, st_size=2100672, ...}) = 0
mmap(0x3c38e00000, 3924576, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x3c38e00000
mprotect(0x3c38fb4000, 2097152, PROT_NONE) = 0
mmap(0x3c391b4000, 24576, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x1b4000) = 0x3c391b4000
mmap(0x3c391ba000, 16992, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x3c391ba000
close(3)                                = 0
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f3b2384c000
mmap(NULL, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f3b2384a000
arch_prctl(ARCH_SET_FS, 0x7f3b2384a740) = 0
mprotect(0x60d000, 4096, PROT_READ)     = 0
mprotect(0x3c391b4000, 16384, PROT_READ) = 0
mprotect(0x3c38c1f000, 4096, PROT_READ) = 0
munmap(0x7f3b2384d000, 245801)          = 0
brk(0)                                  = 0xfa8000
brk(0xfc9000)                           = 0xfc9000
brk(0)                                  = 0xfc9000
open("/usr/lib/locale/locale-archive", O_RDONLY|O_CLOEXEC) = 3
fstat(3, {st_mode=S_IFREG|0644, st_size=106070960, ...}) = 0
mmap(NULL, 106070960, PROT_READ, MAP_PRIVATE, 3, 0) = 0x7f3b1d321000
close(3)                                = 0
ioctl(0, SNDCTL_TMR_TIMEBASE or SNDRV_TIMER_IOCTL_NEXT_DEVICE or TCGETS, {B38400 opost isig icanon echo ...}) = 0
newfstatat(AT_FDCWD, "a", {st_mode=S_IFREG|0664, st_size=0, ...}, AT_SYMLINK_NOFOLLOW) = 0
geteuid()                               = 1000
newfstatat(AT_FDCWD, "a", {st_mode=S_IFREG|0664, st_size=0, ...}, AT_SYMLINK_NOFOLLOW) = 0
faccessat(AT_FDCWD, "a", W_OK)          = 0
unlinkat(AT_FDCWD, "a", 0)              = 0
lseek(0, 0, SEEK_CUR)                   = -1 ESPIPE (Illegal seek)
close(0)                                = 0
close(1)                                = 0
close(2)                                = 0
exit_group(0)                           = ?
+++ exited with 0 +++

ডিরেক্টরি এবং ফাইলগুলি অপসারণের জন্য আলাদা সিস্টেম কল কেন রয়েছে? এই দুটি ক্রিয়াকলাপটি শব্দার্থগতভাবে আলাদা হবে কেন?


3
এখানে উত্তর: superuser.com/questions/430313/...
jlliagre

উত্তর:


9

ডিরেক্টরিগুলি এই অর্থে বিশেষ যে কোনও ডিরেক্টরিতে আপনার বেশ কয়েকটি ফাইল এবং ডিরেক্টরিগুলির রেফারেন্স থাকতে পারে, সুতরাং, আপনি যদি প্যারেন্ট ডিরেক্টরিটি সরিয়ে থাকেন তবে এই ফাইলগুলি যেখানে সেগুলি অ্যাক্সেস করতে পারে সেখান থেকে তাদের রেফারেন্স পয়েন্টটি হারাবে, প্রক্রিয়া সহ একই। এই ধরনের ক্ষেত্রে, rmdir()পৃথক চেক করুন, যা এর থেকে পৃথক unlink():

  • ডিরেক্টরিটি খালি না হলে। যদি কোনও ডিরেক্টরি খালি না থাকে তবে বিষয়বস্তু unlink'ডি / অপসারণ না হওয়া পর্যন্ত এটি সরাতে পারবেন না ।

       ENOTEMPTY
          pathname contains entries other than . and .. ; or, pathname has
          ..  as its final component.  POSIX.1-2001 also allows EEXIST for
          this condition.
    
  • ডিরেক্টরিটি যদি ব্যবহার হয়। যদি কোনও প্রক্রিয়া তাদের বর্তমান ডিরেক্টরি হ'ল, এটি সমস্যা এবং অপরিবর্তিত আচরণ হতে পারে। তাদের প্রতিরোধ করা ভাল।

       EBUSY  pathname  is currently in use by the system or some process that
          prevents its removal.  On Linux this means pathname is currently
          used  as  a  mount point or is the root directory of the calling
          process.
    

unlink()এই চেকগুলির ক্ষেত্রে উপস্থিত নেই। প্রকৃতপক্ষে, আপনি কোনও ফাইলের নাম মুছে ফেলতে পারেন unlink()এবং যে প্রক্রিয়াটি এখনও এটি ব্যবহার করে / রেফারেন্স তৈরি করে চলেছে, সমস্যা ছাড়াই এটি সংশোধন করতে পারে। ফাইল বর্ণনাকারী উপস্থিত না হওয়া অবধি ফাইলটি বিদ্যমান, কেবলমাত্র নতুন প্রক্রিয়াতে অ্যাক্সেসযোগ্য (যদি না আপনি কোথায় সন্ধান করতে জানেন)। এটি * এনআইএক্স ফাইল সিস্টেমের রংধনু-হ্যান্ড ম্যাজিকের অংশ।

এখন, unlinkat()যা উভয় হিসাবে আচরণ করে, unlink()বা rmdir(2)যে পথটি আপনি প্রত্যাশা করছেন তার উপর নির্ভর করে।


ভাল rm -rf "$PWD"কাজ করে এবং বর্তমান ডিরেক্টরিটি সরিয়ে দেয়। আমি মনে করি যে এর কারণ rmdir()সম্ভবত historicalতিহাসিক (প্রাথমিকভাবে ডিরেক্টরিগুলি আনলিঙ্ক করা হয়েছিল) এবং rmdir (কমান্ডটি) dir /।, Dir / .. এবং dir সংযুক্ত ছিল, এবং যখন এটি কার্নেলে স্থানান্তরিত হয়েছিল, তখন এটি হওয়া উচিত ছিল কমপক্ষে একটি संक्रमणকালীন সময়ের জন্য বা এরকম কোনও কিছুর জন্য নতুন সিস্কেল 3 টি সবই করছে)
স্টাফেন চেজেলাস

পছন্দ করেছেন
ব্রাইয়াম

আমি যদি আপনার উত্তরটি সঠিকভাবে পড়ে থাকি, আপনি বলছেন ব্যবহারে rmdir(dir)থাকলে কাজ করে না dir। এটি লিনাক্সের ক্ষেত্রে কমপক্ষে সত্য নয়, যেখানে rmdir(getcwd())ঠিক কাজ করে (বর্তমান ডিরেক্টরিটি ফাঁকা থাকলে)।
স্টাফেন চেজেলাস

@ স্টাফেনচেজেলাস সঠিক, কোনও প্রক্রিয়া দ্বারা বা মাউন্ট পয়েন্ট হিসাবে ব্যবহৃত: EBUSY প্যাথনাম বর্তমানে সিস্টেম বা কোনও প্রক্রিয়া ব্যবহার করছে যা এটি অপসারণকে বাধা দেয় । লিনাক্সে এর অর্থ পথের নামটি বর্তমানে মাউন্ট পয়েন্ট হিসাবে ব্যবহৃত হয় বা কলিং প্রক্রিয়াটির মূল ডিরেক্টরি।
ব্রায়াম

আমি নিশ্চিত নই যে তারা কলিং প্রক্রিয়াটির মূল ডিরেক্টরি বা তার অর্থ । mkdir test; sudo strace -e chroot,rmdir perl -e 'chroot("test"); rmdir("test")'chroot এবং rmdir উভয়কেই সফল দেখায়।
স্টাফেন চেজেলাস
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.