Segurança e auditoria de sistemas Carlos Oberdan Rolim Ciência da Computação Sistemas de informação Segurança em sistemas operacionais Unix Motivação Por que é importante conhecer sistemas unix ? Histórico Unix As raízes do UNIX datam dos meados dos anos 60, quando a AT&T, Honeywell, GE e o MIT embarcaram em um massivo projeto para desenvolvimento de um utilitário de informação, chamado Multics (Multiplexed Information and Computing Service). Em 1969, o projeto estava muito atrasado em relação ao seu cronograma e a AT&T resolveu abandona-lo. O projeto continuou no MIT. Neste mesmo ano, Ken Thompson, um pesquisador da AT&T que havia trabalhado no Projeto Multics, pegou um computador PDP-7 para pesquisar algumas idéias do Multics por conta própria. Logo Dennis Ritchie, que também trabalhou no Multics, se juntou a ele. Enquanto Multics tentava fazer várias coisas, UNIX tentava fazer uma coisa bem: rodar programas. Histórico Unix 1972 - Ken Thompson e Dennis M. Ritchie com um PDP-11 Histórico Unix Este pequeno escopo era todo ímpeto que os pesquisadores precisavam. Em 1971 saiu a primeira versão do UNIX, V1, muitos meses antes do Multics, em assembler em um computador PDP-11 da Digital. Incluía sistema de arquivos, fork(), roff, ed. Era utilizado como uma ferramenta de processamento de texto para a preparação de patentes. Pipe() apareceu na V2. Em 1973 o UNIX foi reescrito em C, talvez o fato mais importante da história deste sistema operacional. Isto significava que o UNIX poderia ser portado para novo hardware em meses, e que mudanças eram fáceis. A linguagem C foi projetada para o sistema operacional UNIX, e portanto há uma grande sinergia entre C e UNIX. Histórico Unix Em 1975 foi lançada a V6. Disponível para universidades Em 1978 Berkley Software Distribuition lança a série 2.xBSD para PDP - 11 (a versão 2.11 foi lançada em 1992). Nesta versão saiu o csh. Neste ano também saiu a série 3BSD, que teve uma importante contribuição, virtual memory. Em 1979 saiu a V7 e o Unix foi portado para o novo VAX da Digital. Esta versão incluia C K&R completo, uucp, Bourne Shell. O kernel tinha meramente 40 bytes! Esta foi a primeira versão vendida comercialmente do sistema, mas usada principalmente por universidades. Em 1983 é lançado o System V da AT&T e o 4.2 BSD. O SV incluía o pacote IPC (shm, msg, sem) para comunicação entre processos. Surgiram outras versões do SV com a inclusão de novas características como sharedlibs no SVR4. Histórico Unix O 4.2BSD foi talvez uma das mais importantes versões do UNIX. O seu software de conexão de redes tornava muito fácil a tarefa de conectar computadores UNIX a redes locais. Nessa versão é que foram integrados os softwares que implementam TCP/IP e sockets. Em 1988 foi lançado o SVR4. Este sistema era um merge de releases anteriores do SV, BSD e SunOs, uma implementação decendente de BSD. Neste release foram incorporados as seguintes características: BSD: TCP/IP, sockets, csh, ... SVR3: sysadmin, ... SunOs: NFS, OpenLook GUI, X11/NeWS, virtual memory subsystem with memoy mapped files, shared libraries (!= SVR3) ksh Histórico Unix O 4.4BSD foi lançado em 1992 para várias plataformas: HP 9000/300, Sparc, 386, DEC e outras, mas não em VAX. Entre as novas características estão: Novo sistema de memória virtual baseado em Mach 2.5 Suporte ISO/OSI (baseado em ISODE) A Sun Microsystem também lançou a sua versão do UNIX a partir do BSD. Isto ocorreu até a versão SunOs 4.x. A nova versão, SunOs 5.x está baseada no SVR4, embora tenha herdado algumas características do SunOs 4.x. O novo sistema operacional da Sun, Solaris 2.x, é um SO que engloba SunOs 5.x, Open Network Computing e Open Windows. É o solaris que provê o pacote de compatibilidade entre os BSD/SunOs e o SVR4/SunOs 5.x. Evolução do Unix Linux O Kernel do Linux foi, originalmente, escrito por Linus Torvalds do Departamento de Ciência da Computação da Universidades de Helsinki, Finlândia, com a ajuda de vários programadores voluntários através da Internet. Linus Torvalds iniciou cortando (hacking) o kernel como um projeto particular, inspirado em seu interesse no Minix, um pequeno sistema UNIX desenvolvido por Andy Tannenbaum. Ele se limitou a criar, em suas próprias palavras, "um Minix melhor que o Minix" ("a better Minix than Minix"). E depois de algum tempo de trabalho em seu projeto, sozinho, ele enviou a seguinte mensagem para comp.os.minix: Linux “Você suspira por melhores dias do Minix-1.1, quando homens serão homens e escreverão seus próprios "device drivers" ? Você está sem um bom projeto e esta morrendo por colocar as mãos em um S.O. no qual você possa modificar de acordo com suas necessidades ? Você está achando frustrante quando tudo trabalha em Minix ? Chega de atravessar noites para obter programas que trabalhem correto ? Então esta mensagem pode ser exatamente para você.Como eu mencionei há um mês atrás, estou trabalhando em uma versão independente de um S.O. similar ao Minix para computadores AT-386. Ele está, finalmente, próximo do estágio em que poderá ser utilizado (embora possa não ser o que você esteja esperando), e eu estou disposto a colocar os fontes para ampla distribuição. Ele está na versão 0.02... contudo eu tive sucesso rodando bash, gcc, gnu-make, gnused, compressão, etc. nele. “ From Linus Benedict Torvalds to comp.os.minix newsgroup 5 Oct 91 05:41:06 GMT Linux No dia 5 de outubro de 1991 Linus Torvalds anunciou a primeira versão "oficial" do Linux, versão 0.02. Desde então muitos programadores têm respondido ao seu chamado, e têm ajudado a fazer do Linux o Sistema Operacional que é hoje. Kernel O Kernel de um sistema operacional é entendido como o núcleo deste ou, numa tradução literal, cerne. Ele representa a camada de software mais próxima do hardware, sendo responsável por gerenciar os recursos do sistema computacional como um todo. A responsabilidade do kernel consiste, tradicionalmente (particularmente no kernel monolítico), em abstrair a interface do hardware, permitindo que processos utilizem este recurso concorrentemente, de forma segura e padronizada. Computador carrega o kernel no momento do boot Kernel Implementa o sistema de arquivos: Permite processos criar, ler, escrever e acessar estes arquivos Gerencia Daemons: Move páginas do disco para memória Prioridades Gerencia drivers de dispositivos Gerencia software de rede que implementa serviços de rede Gerencia facilidades de comunicação entre processos Provê facilidades para criar, examinar e modificar processos Provê funções de gerenciamento do sistema Provê funções miscelâneas que tornam os recursos do sistema disponíveis aos processos, como, por exemplo: memória Shell Shell é um programa que conecta e interpreta os comandos digitados por um usuário. É a interface que o usuário utiliza para enviar comandos para o sistema. Dos vários programas shell existentes, o Bourne shell, o Korn shell e o C shell se destacam por serem os mais utilizadas e conhecidos. Mas qualquer programador pode fazer o seu shell. Estes shells tornaram-se conhecidos pois já vinham com o sistema, exceto o Korn que tinha que ser adquirido separadamente. O Bourne shell vinha com o SV e C shell com o BSD. O Korn shell é uma melhoria do Bourne shell. Usuários e grupos Cada usuário registrado possui um nome de login, uma senha e um identificador numérico associado (UID). Os usuários são organizados em grupos. Um usuário sempre pertence a um grupo primário e pode pertencer a outros grupos secundários. Cada grupo é identificado por um nome e um identificador de grupo (GID). O comando id user permite visualizar as informações de usuários e grupos. O comando finger user oferece informações adicionais sobre o usuário. Arquivos /etc/passwd - /etc/shadow /etc/group Usuários e grupos O usuário root e outros usuários especiais O usuário com UID = 0 é chamado “root” e possui poderes especiais no sistema: Acesso a todos os arquivos e diretórios Reboot/shutdown do sistema Lançamento e cancelamento de qualquer processo Montagem de diretórios de rede e de dispositivos externos Assim, torna-se óbvio que a senha de root é de grande importância para a segurança do sistema. Além do root, outros usuários são definidos para a implantação de serviços específicos. Esse é o caso dos usuários “bin”, “daemon”,“lp”, “mail”, “news”, “ftp” e “nobody”, que não correspondem a seres humanos. Normalmente esses usuários não são acessíveis via login, existindo apenas internamente no sistema. Sistema de arquivos O UNIX tem uma organização de diretórios hierárquica em formato de árvore conhecida como filesystem O acesso a arquivos é organizado através de propriedades e proteções. Toda segurança do sistema depende, em grande parte, da combinação entre a propriedade e proteções setadas em seus arquivos e suas contas de usuários e grupos. Enfatizando: Tudo em UNIX é um arquivo Unix tem uma organização hierárquica de arquivos chamada de filesystem Acesso aos arquivos é organizado através de propriedades e proteções Sistema de arquivos Um inodo é uma estrutura de dados em disco que descreve e armazena os atributos do arquivo, incluindo sua localização: Campos de um inode user e group tipo do arquivo tempo de criação, acesso e modificação (modo) número de links tamanho endereço no disco Sistema de arquivos Tipos de arquivos Arquivos comuns Diretórios Especiais utilizados para I/O de dispositivos no UNIX. Links Hard: associa dois ou mais filenames com o mesmo inodo. Hard links compartilham o mesmo bloco de dados embora funcionando como entradas de diretório independentes Simbolic: são pointers files que apontam para outro filename no filesystem Sistema de arquivos Arquivos especiais: Sockets tipo especial de arquivo utilizado para comunicação entre processos. São parte da funcionalidade de interconectividade TCP/IP, primeiramente disponível nos sistemas BSD, mas parte de qualquer versão moderna hoje Named pipes são canais abertos pelo nome por aplicações. São características do SV que migraram para todas as versões de UNIX. Named pipes frequentemente residem no diretório /dev, e eles servem como outro mecanismo para facilitar a comunicação entre processos. Sistema de arquivos Principais diretórios /home: raiz dos diretórios home dos usuários. /boot: arquivos de boot (núcleo do sistema, etc) /var: arquivos variáveis, áreas de spool (impressão, e-mail, news), arquivos de log /etc: arquivos de configuração dos serviços /usr: aplicações voltadas aos usuários /tmp: arquivos temporários /mnt: montagem de diretórios compartilhados temporários /bin: aplicações de base para o sistema /dev: arquivos de acesso aos dispositivos físicos e conexões de rede /lib: bibliotecas básicas do sistema Sistema de arquivos Permissões: são conjuntos de direitos que são aplicados a arquivos ou diretórios do sistema de arquivo. Elas garantem que um usuário que não se enquadre nas permissão atribuídas a um arquivo, não tenha acesso ao mesmo, ou não possa executá-lo, ou ainda alterá-lo Duas formas definir permissões: Extendida e Octal Sistema de arquivos Exemplo: $ ls –l -rw-r--r-- 1 root root 2149 2006-11-07 10:50 adduser.conf -rw-r--r-- 1 root root 47 2008-09-23 13:38 adjtime -rw-r--r-- 1 root root 209 2008-08-23 21:54 aliases drwxr-xr-x 2 root root 4096 2008-07-02 22:44 alternatives drwxr-xr-x 3 root root 4096 2006-11-07 14:20 apt { r w x } – {r w x } – { r w x } Owner Grupo Others Sistema de arquivos Forma extendida $ chmod u=rw,g=rw,o= arquivo $ ls -l -rw-rw---- 1 coletivo coletivo 4096 2006-11-07 14:20 arquivo Forma octal $ chmod 755 arquivo $ ls –l -rwxr-xr-x 1 coletivo coletivo 4096 2006-11-07 14:20 arquivo Suid Para encontrar suid/sgid files # find / \( -perm -004000 -o -perm -002000 \) -type f -print Cuidado com o /tmp Processos Um processo é um simples programa que está rodando em seu espaço de endereçamento virtual próprio. Daemons Atributos Process ID (PID) Parent process (PPID) TTY UID real e efetiva (RUID, EUID) GID real e efetiva (RGID, EGID) Cuidado com processos startados pelo usuário root Processos $ ps -auxx USER PID %CPU %MEM VSZ root 49070 root 782 root RSS TT STAT STARTED TIME COMMAND 79,2 0,2 3896 2032 pk- R Ter15 868:15,58 -su (bash) 2,0 0,3 5960 2660 ?? Ss 5Set08 610:40,10 /usr/bin/perl 68077 1,1 0,1 2392 980 ?? 6Set08 382:05,17 /usr/local/sb Ss User = usuario Pid = identificacao do processo %cpu e %mem = %consumido Vsz = virtual size em kbytes Rss = tamanho do processo residente em memória Tt = terminal de controle Stat = Status do processo Start time = tempo de inicio Command = comando rodando Cuidado com processos startados pelo usuário root Interfaces de rede Comunicação com o mundo externo Kernel reconhece e gerencia as interfaces de rede Comandos a nível de usuário para interagir com interfaces Exemplo: eth0 Link encap:Ethernet HWaddr 00:50:04:99:25:7B inet addr:200.200.200.2 Bcast:200.200.200.255 Mask:255.255.255.0 inet6 addr: fe80::250:4ff:fe99:257b/64 Scope:Link UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1 RX packets:33642869 errors:0 dropped:0 overruns:5738 frame:0 TX packets:37327420 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:1000 RX bytes:310178592 (295.8 MiB) TX bytes:1866164000 (1.7 GiB) Interrupt:193 Interface de loopback lo Link encap:Local Loopback inet addr:127.0.0.1 Mask:255.0.0.0 inet6 addr: ::1/128 Scope:Host Cuidado: Interfaces em modo promiscuo Sistema de logs Sistema mantém controle sobre tarefas executadas pelo sistema e por seus usuários Daemon responsável por logs Syslog Diretório /var/log Sempre ficar de olhos nos arquivos nesse diretório Alternativa ideal: logs centralizados Sistema de logs Inicio de uma sessão Sep 23 08:17:01 localhost CRON[18951]: (pam_unix) session opened for user root by (uid=0) Sep 23 08:17:01 localhost CRON[18951]: (pam_unix) session closed for user root Tentativa de invasão BREAKIN ATTEMPT! Sep 23 08:27:21 localhost sshd[19022]: Illegal user blair from 83.138.128.119 Sep 23 08:27:21 localhost sshd[19022]: reverse mapping checking getaddrinfo for fw.prescreen.co.uk failed POSSIBLE BREAKIN ATTEMPT! Agendamento de tafefas Cron: daemon responsável pela execução de tarefas agendadas /etc/crontab #minute hour mday month wday who command # Rotate log files every hour, if necessary. 0 * * * * root newsyslog # Script que roda como root 0/15 * * * * root /bin/sh /tmp/danger.sh >> /dev/null Cuidado com scripts de usuários que rodam com permissão de root Firewall Têm por função regular o tráfego de dados entre redes distintas e impedir a transmissão e/ou recepção de acessos nocivos ou não autorizados de uma rede para outra. Baseado em fluxos de dados: Tipos de pacotes Protocolos. Portas, enderecos de origem / destino Exemplos: Iptables Ipchains Ipf Pf Ipfw Inetd Chamado de ``Super-Servidor Internet'' porque ele gerencia conexões para diversos daemons O inetd atua como um servidor gerenciador para outros daemons. Quando uma conexão é recebida pelo inetd, ele determina para qual daemon a conexão é destinada e executa o daemon correspondente e a ele delega o socket. Executar uma instância do inetd reduz a carga no sistema de forma geral, comparado a se executar cada daemon individualmente. Uma entrada de exemplo para o daemon ftpd usando IPv4: ftp stream tcp nowait root /usr/libexec/ftpd ftpd –l E se fosse feita a seguinte entrada ??? Afff.. 1008 stream tcp nowait root /bin/sh sh Conclusão