0040000
é o valor tradicional de S_IFDIR
, o sinalizador de tipo de arquivo que representa um diretório. O tipo usa os 4 bits principais do valor 16-bit st_mode
, 0100000
é o valor dos arquivos regulares.
Os altos 16 bits dos atributos de arquivos externos parecem ser usados para permissões específicas do sistema operacional. Os valores do Unix são os mesmos das implementações tradicionais do Unix. Outros sistemas operacionais usam outros valores. Informações sobre os formatos usados em vários sistemas operacionais diferentes podem ser encontradas no código-fonte do Info-ZIP ( download ou por exemplo em debian apt-get source [zip or unzip]
) - arquivos relevantes são zipinfo.c
em unzip
e os arquivos específicos da plataforma em zip
.
Estes são convencionalmente definidos em octal (base 8); isso é representado em C e python prefixando o número com um 0
.
Esses valores podem ser encontrados em <sys/stat.h>
- link para a versão 4.4BSD . Estes não estão no padrão POSIX (que define macros de teste); mas são originários do AT & T Unix e do BSD. (no GNU libc / Linux, os próprios valores são definidos como __S_IFDIR
etc em bits/stat.h
, embora o cabeçalho do kernel pode ser mais fácil de ler - os valores são praticamente iguais em todos os lugares.)
#define S_IFIFO 0010000 /* named pipe (fifo) */
#define S_IFCHR 0020000 /* character special */
#define S_IFDIR 0040000 /* directory */
#define S_IFBLK 0060000 /* block special */
#define S_IFREG 0100000 /* regular */
#define S_IFLNK 0120000 /* symbolic link */
#define S_IFSOCK 0140000 /* socket */
E, claro, os outros 12 bits são para as permissões e setuid / setgid / sticky bits, o mesmo que para chmod:
#define S_ISUID 0004000 /* set user id on execution */
#define S_ISGID 0002000 /* set group id on execution */
#define S_ISTXT 0001000 /* sticky bit */
#define S_IRWXU 0000700 /* RWX mask for owner */
#define S_IRUSR 0000400 /* R for owner */
#define S_IWUSR 0000200 /* W for owner */
#define S_IXUSR 0000100 /* X for owner */
#define S_IRWXG 0000070 /* RWX mask for group */
#define S_IRGRP 0000040 /* R for group */
#define S_IWGRP 0000020 /* W for group */
#define S_IXGRP 0000010 /* X for group */
#define S_IRWXO 0000007 /* RWX mask for other */
#define S_IROTH 0000004 /* R for other */
#define S_IWOTH 0000002 /* W for other */
#define S_IXOTH 0000001 /* X for other */
#define S_ISVTX 0001000 /* save swapped text even after use */
Como uma observação histórica, a razão 0100000
é para arquivos regulares em vez de 0 é que em versões muito antigas do unix, 0 era para arquivos 'pequenos' (estes não usavam blocos indiretos no sistema de arquivos) e o alto bit do sinalizador de modo foi definido para arquivos 'grandes' que usariam blocos indiretos. Os outros dois tipos que usam esse bit foram adicionados em sistemas operacionais posteriores derivados de unix, depois que o sistema de arquivos mudou.
Então, para finalizar, o layout geral do campo de atributos estendidos para o Unix é
TTTTsstrwxrwxrwx0000000000ADVSHR
^^^^____________________________ file type as explained above
^^^_________________________ setuid, setgid, sticky
^^^^^^^^^________________ permissions
^^^^^^^^________ This is the "lower-middle byte" your post mentions
^^^^^^^^ DOS attribute bits