Вывод Strace не показывает системный вызов

Он может удалять файлы, но каталоги не являются «файлами».

➜  lab touch file        
➜  lab mkdir dir
➜  lab ln -sfT /home file
➜  lab ln -sfT /home dir 
ln: dir: cannot overwrite directory

Это видно в источнике :

  if (remove_existing_files || interactive || backup_type != no_backups)
    {
      dest_lstat_ok = (lstat (dest, &dest_stats) == 0);
      if (!dest_lstat_ok && errno != ENOENT)
        {
          error (0, errno, _("failed to access %s"), quoteaf (dest));
          return false;
        }
    }
[...]
  if (dest_lstat_ok)
    {
      if (S_ISDIR (dest_stats.st_mode))
        {
          error (0, 0, _("%s: cannot overwrite directory"), quotef (dest));
          return false;
        }
      if (interactive)
        {
          fprintf (stderr, _("%s: replace %s? "), program_name, quoteaf (dest));
          if (!yesno ())
            return true;
          remove_existing_files = true;
        }

dest_lstat_ok логическое значение, которое начинается как false, становится истинным, первый оператор if вызывается , поскольку remove_existing_files истинно из-за флага - force , который, в свою очередь, позволяет проверить второй оператор if. Он отказывается удалять каталоги, потому что ожидает файл .

Если вы не установите -T , что заставляет ln не обрабатывать каталог как не каталог , ln просто создаст символическую ссылку под каталог с базовым именем источник.

3
14.06.2016, 21:01
1 ответ

Причина в том, что ttyname (3) не является системным вызовом , это функция библиотеки C. Вы можете ознакомиться с его реализацией, например . в glibc , чтобы увидеть, какие системные вызовы он использует сам (и это вы затем увидите в выводе strace ).

Для отслеживания вызовов библиотеки в Linux можно использовать ltrace (который также может отслеживать системные вызовы). (Спасибо Marki555 за предложение.)

5
27.01.2020, 21:16

Теги

Похожие вопросы