$retMode & 0777
означает, что вы берете значение режима возврата (то есть права доступа к файлу + тип файла) и Побитовое-И оно с восьмеричным числом представления 777 (например, десятичное 511, например, двоичное) 111111111).
Технически это означает, что все биты удаляются из целого числа выше 9-го бита, поэтому, если двоичное представление режима было> 9 бит, после этой операции оставались бы только последние 9 битов, представляющих основные разрешения (чтение / запись / выполнение для другого / группы / пользователя).
Почему ? Поскольку (как показывает perldoc stat ), mode()
возвращается из stat
:
" содержит как тип файла, так и его права доступа , вы должны замаскировать часть типа файла и / или printf, используя"% o ", если вы хотите увидеть реальные разрешения".
Другими словами, он содержит данные выше 9-го разряда, но только последние 9 разрядов представляют данные о правах доступа, за которыми следует код, приведенный выше. Чтобы быть более точным, последние 12 цифр представляют разрешения (поэтому код должен вместо этого делать & 07777
), но биты 10-12 представляют специальные биты разрешения, не связанные с правами пользователя / группы / других операций чтения / записи / выполнения (например, setuid, is_directory). ).
$retMode & 006
имеет похожую механику, но другого назначения. Восьмеричное число 006 в двоичном формате равно 110, поэтому оно в основном принимает битовый вектор режима и оставляет только биты в позициях 2/3. Поскольку результат используется в логическом контексте, он просто проверяет, является ли результирующий # ненулевым, то есть, если ОДИН из этих 2 битов установлен в 1.
Обратите внимание, что & 006
на самом деле стиль кодирования ПЛОХО, так как неясно, какие биты являются какими перманентами (как я пытался слегка намекнуть на , не объясняя, что означают биты 2/3 в абзаце выше). Вместо этого вы должны импортировать константы символического режима (S_IF *) и функции (S_IS *) из модуля Fcntl:
use Fcntl ':mode';
$retMode = $retMode & 0777; # Ignoring setuid and directory bits
$other_read_or_write = $retMode & (S_IWOTH || S_IROTH);
# Bits 2/3 - Other read/write
if ($other_read_or_write) {
printf "$property|%03o|$fpath\n",$retMode;
}