Você está na página 1de 10

Pedro F.

Carvalho
Analista de Sistemas
contato@pedrofcarvalho.com.br
www.pedrofcarvlho.com.br

AULA 11 – IMPLEMENTANDO SEGURANÇA

Paramentros de segurança no Oracle

1- Protegendo o dicionário de dados:

Configurar o valor do parâmetro de sistema O7_DICTIONARY_ACCESSIBILITY


para FALSE. Isso impede que usuários com privilégios ANY TABLE acessem tabelas do
dicionário de dados, além de forçar o usuário SYS a se conectar como SYSOPER ou
SYSDBA.

Passo-a-passo:

a) Executar o comando abaixo para verificar o valor do parâmetro


O7_DICTIONARY_ACCESSIBILITY:
SHOW PARAMETER O7_DICTIONARY_ACCESSIBILITY;

b) Se o valor de O7_DICTIONARY_ACCESSIBILITY for diferente de FALSE,


execute os comandos abaixo para efetuar a alteração e reiniciar o Banco de Dados,
para que a alteração tenha efeito:
ALTER SYSTEM SET O7_DICTIONARY_ACCESSIBILITY = FALSE
SCOPE=SPFILE;
SHUTDOWN IMMEDIATE;
STARTUP;

2- Revogando privilégios públicos em packages que oferecem riscos de


segurança:

Este item requer um pouco mais de trabalho e cuidados que o item anterior. Nele
iremos revogar os privilégios de execução pública nas packages UTL_SMTP, UTL_TCP,
UTL_HTTP, UTL_FILE e DBMS_OBFUSCATION_TOOLKIT. Isso impede que usuários
maliciosos executem essas packages de forma indevida, reduzindo deste modo, os
riscos de segurança.

Passo-a-passo:

a) Executar a query abaixo para gerar um script contendo comandos necessários


para revogar privilégios públicos nas packages mencionadas neste item:
SELECT 'REVOKE EXECUTE ON ' || OBJECT_NAME || ' FROM
Pedro F. Carvalho
Analista de Sistemas
contato@pedrofcarvalho.com.br
www.pedrofcarvlho.com.br

PUBLIC;'
FROM dba_objects o
WHERE OBJECT_NAME IN
('UTL_SMTP','UTL_TCP','UTL_HTTP','UTL_FILE','DBMS_OBFUSCATION_TOOLK
IT')
AND O.OWNER = 'PUBLIC'
ORDER BY 1
Obs.: Salve o resultado em um arquivo.

b) Executar o bloco PL/SQL abaixo para gerar um script com atribuições de


privilégios necessários para que todos os usuários (schemas) que possuem objetos que
utilizam as packages deste item, possam executá-las após revogarmos os privilégios
públicos:

SET OUTPUT ON
BEGIN
DBMS_OUTPUT.ENABLE(NULL);

FOR cur_rec IN (SELECT o.owner,


SUM(INSTR(UPPER(S.TEXT), 'UTL_SMTP')) AS
UTL_SMTP,
SUM(INSTR(UPPER(S.TEXT), 'UTL_TCP')) AS
UTL_TCP,
SUM(INSTR(UPPER(S.TEXT), 'UTL_HTTP')) AS
UTL_HTTP,
SUM(INSTR(UPPER(S.TEXT), 'UTL_FILE')) AS
UTL_FILE,
SUM(INSTR(UPPER(s.text),
'DBMS_OBFUSCATION_TOOLKIT')) AS DBMS_OBFUSCATION_TOOLKIT
FROM dba_objects o
INNER JOIN dba_source s
ON s.owner = o.owner
AND s.type = o.object_type
AND S.NAME = O.OBJECT_NAME
WHERE OBJECT_NAME NOT IN
('UTL_SMTP','UTL_TCP','UTL_HTTP','UTL_FILE','DBMS_OBFUSCATION_TOOLK
IT')
AND S.OWNER != 'SYS'
AND (UPPER(S.TEXT) LIKE UPPER('%UTL_SMTP%')
OR UPPER(S.TEXT) LIKE UPPER('%UTL_TCP%')
OR UPPER(S.TEXT) LIKE UPPER('%UTL_HTTP%')
OR UPPER(S.TEXT) LIKE UPPER('%UTL_FILE%')
OR UPPER(S.TEXT) LIKE
UPPER('%DBMS_OBFUSCATION_TOOLKIT%'))
GROUP BY o.owner
ORDER BY 1)
LOOP
IF CUR_REC.UTL_SMTP > 0 THEN
DBMS_OUTPUT.PUT_LINE('GRANT EXECUTE ON UTL_SMTP TO '
|| CUR_REC.owner || ';');
END IF;

IF CUR_REC.UTL_TCP > 0 THEN


Pedro F. Carvalho
Analista de Sistemas
contato@pedrofcarvalho.com.br
www.pedrofcarvlho.com.br

DBMS_OUTPUT.PUT_LINE('GRANT EXECUTE ON UTL_TCP TO ' ||


CUR_REC.owner || ';');
END IF;

IF CUR_REC.UTL_HTTP > 0 THEN


DBMS_OUTPUT.PUT_LINE('GRANT EXECUTE ON UTL_HTTP TO '
|| CUR_REC.owner || ';');
END IF;

IF CUR_REC.UTL_FILE > 0 THEN


DBMS_OUTPUT.PUT_LINE('GRANT EXECUTE ON UTL_FILE TO ' ||
CUR_REC.owner || ';');
END IF;

IF CUR_REC.DBMS_OBFUSCATION_TOOLKIT > 0 THEN


DBMS_OUTPUT.PUT_LINE('GRANT EXECUTE ON
DBMS_OBFUSCATION_TOOLKIT TO ' || CUR_REC.owner || ';');
END IF;
END LOOP;
END;
/

Obs. 1: Salvar o resultado em um arquivo.

Obs. 2: O bloco PL/SQL acima não gera os privilégios necessários para objetos
compilados em código nativo ou objetos wrapped. O procedimento necessário para
estes casos não é abordado neste artigo, portanto tenha muito cuidado ao executar
este item, pois se o Banco de Dados tiver objetos wrapped ou compilados em código
nativo, estes objetos ficarão inválidos e poderão impedir o funcionamento de sistemas
que dependem deles. Para mais informações consulte os links:
http://download.oracle.com/docs/cd/B28359_01/appdev.111/b28370/wrap.htm e
http://www.oracle-
base.com/articles/11g/PlsqlNewFeaturesAndEnhancements_11gR1.php#native_compil
ation.

c) Executar os comandos do script gerado no passo "a" e em seguida executar o


script gerado no passo "b".

3- Restringindo diretórios do Sistema Operacional:

Verificar o valor do parâmetro de sistema UTL_FILE_DIR. Se este parâmetro tiver


um valor apontando para um ou mais diretório(s) do sistema de arquivos, configure no
Sistema Operacional, privilégios de gravação reduzidos (valor de cota máxima de
gravação em disco) neste(s) diretório(s) para o usuário do SO que executa os
processos do Oracle (normalmente usuário "oracle"). Se isso não for possível, pode-se
configurar no parâmetro UTL_FILE_DIR um diretório em um volume lógico separado do
volume lógico em que estão os arquivos e software Oracle. Isso reduz o risco de um
script malicioso ser executado no BD para gravar arquivos nesta pasta até estourar o
limite de tamanho do volume lógico e "parar" o Banco de Dados quando o volume
lógico "estourar".
Pedro F. Carvalho
Analista de Sistemas
contato@pedrofcarvalho.com.br
www.pedrofcarvlho.com.br

Verificando o valor do parâmetro UTL_FILE_DIR:


SHOW PARAMETER UTL_FILE_DIR;

O parâmetro UTL_FILE_DIR pode ser configurado para apontar para mais de um


diretório ou para o diretório raiz do sistema de arquivos. Por questões de segurança
evite fazer isso. Configure no máximo um diretório.

Se for desejado "limpar" (apontar para nenhum diretório) o parâmetro


UTL_FILE_DIR, para aumentar o nível de segurança, execute os comandos abaixo para
alterá-lo e reiniciar o Banco de Dados:
ALTER SYSTEM SET UTL_FILE_DIR = '' SCOPE=SPFILE;
SHUTDOWN IMMEDIATE;
STARTUP;

4- Restringindo privilégios administrativos aos usuários do Banco de


Dados:

Se um ou mais usuário(s) possuir(em) a role DBA e/ou o privilégio de sistema


SYSDBA, sem necessidade ou indevidamente, execute os procedimentos abaixo para
revogar os privilégios administrativos:

Passo-a-passo:

a) Verificando usuários com a role DBA:


SELECT GRANTEE FROM DBA_ROLE_PRIVS WHERE GRANTED_ROLE =
'DBA';

Para revogar a role DBA para um determinado usuário execute o comando


abaixo substituindo XXX pelo nome dele:
REVOKE DBA FROM XXX;

b) Verificando usuários com o privilégio de sistema SYSDBA:


SELECT * FROM V$PWFILE_USERS;

Para revogar o privilégio de sistema SYSDBA para um determinado usuário


execute o comando abaixo substituindo XXX pelo nome dele:
REVOKE SYSDBA FROM XXX;

Mais informações sobre a role DBA e o privilégio de sistema SYSDBA, consulte


http://momendba.blogspot.com/2007/07/closer-look-at-sysdba-and-dba.html.

5- Desativando autenticação remota do Sistema Operacional:

Na configuração padrão do Oracle 10G, o Banco de Dados permite que usuários


autenticados no sistema operacional façam conexão local sem fornecer usuário e senha
do Banco de Dados.

Para permitir esse modo de conexão somente para usuários locais do Sistema
Operacional, deve-se configurar o valor do parâmetro REMOTE_OS_AUTHENT para
FALSE. Essa configuração evita que usuários remotos (usuários de qualquer
computador em uma rede) se conectem no Banco de Dados sem fornecer usuário e
Pedro F. Carvalho
Analista de Sistemas
contato@pedrofcarvalho.com.br
www.pedrofcarvlho.com.br

senha.

Passo-a-passo:

a) Verificando o valor do parâmetro REMOTE_OS_AUTHENT:


SHOW PARAMETER REMOTE_OS_AUTHENT;

b) Se o valor do parâmetro REMOTE_OS_AUTHENT for diferente de FALSE,


execute o comando abaixo para configurá-lo para FALSE e para reiniciar o Banco de
Dados, aplicando as alterações efetuadas:
ALTER SYSTEM SET REMOTE_OS_AUTHENT=FALSE SCOPE=SPFILE;
SHUTDOWN IMMEDIATE;
STARTUP;

Auditoria no Oracle 10g

Auditoria é a habilidade do banco de dados Oracle poder gerar logs de auditoria (XML,
tabelas, arquivos de SO, …) em atividades suspeitas do usuário, como por exemplo:
monitorar o que um determinado usuário está fazendo ou até mesmo saber para qual
valor a coluna de salário da tabela empregados está sendo atualizadas. Com a
auditoria, esses dados são facilmente capturados e guardados para posteriormente
serem analisados.

Realizar auditorias basicamente consiste em 2 passos:


1) Deixar o banco em modo auditoria.
2) Especificar os objetos/privilegio/instrução a serem auditados.

Para habilitar a auditoria, é necessário mudar o parâmetro de inicialização audit_trail,


para que o Oracle inicie e reconheça o tipo de auditoria que você necessita. Ele suporta
os seguintes valores, cada um com o seguinte função.

OS : Auditoria Habilitada, os registros vão ser gravados em diretorios do sistema em


arquivos de auditoria.
DB ou TRUE : Auditoria é habilitada, os registros de auditoria serão armazenadas no
database (SYS.AUD$)
XML : Auditoria é habilitada, os registros serão armazenados em formatos XML.
NONE ou FALSE : Auditoria é desabilitada.
DB_EXTENDED : Trabalha igual ao parâmetro DB, mais as colunas SQL_BIND e
SQL_TEXT são preenchidas.

Quando se seleciona os modos OS ou XML, arquivos são criados com os registros de


auditoria, eles se localizam parâmetro audit_file_dest.

Em nosso exemplo prático, vamos utilizar o tipo de auditoria DB, então executares o
seguintes comandos:

SQL> ALTER SYSTEM SET audit_trail = “DB” SCOPE = SPFILE;

System altered.
Pedro F. Carvalho
Analista de Sistemas
contato@pedrofcarvalho.com.br
www.pedrofcarvlho.com.br

SQL> shutdown immediate


Database closed.
Database dismounted.
ORACLE instance shut down.

SQL> startup
ORACLE instance started.

Total System Global Area 826277888 bytes


Fixed Size 1222072 bytes
Variable Size 222300744 bytes
Database Buffers 595591168 bytes
Redo Buffers 7163904 bytes
Database mounted.
Database opened.

Agora será necessário especificar as opções de auditoria, elas são em três partes,
faremos exemplos das três. Antês disso, vamos criar o usuário user_audit, para
trabalharmos com ele na auditoria.

SQL> conn sys as sysdba


Enter password:
Connected.

SQL> create user user_audit identified by oracle


2 default tablespace users
3 temporary tablespace temp
4 quota unlimited on users;

User created.

SQL> GRANT connect to user_audit;

Grant succeeded.

Agora poderemos trabalhar com o usuário user_audit.

1) Auditoria de Instrução.

Sintaxe :

AUDIT clausula_instrução BY { SESSION | ACESS } WHENEVER [ NOT ] SUCCESSFUL;

BY SESSION : Resumi a escrita dos registros por sessão para o mesmo tipo de
instrução em um mesmo objeto, essa é a opção default.
BY ACCESS : Escreve um registro para cada vez que a auditoria é executada.
WHENEVER SUCCESSFUL : Instrução bem-sucedidas, que não mostram mensagens de
erros.
WHENEVER NOT SUCCESSFUL : Instrução não bem-sucedidas, que mostram
mensagens de erros.
Pedro F. Carvalho
Analista de Sistemas
contato@pedrofcarvalho.com.br
www.pedrofcarvlho.com.br

Queremos conceder o privilégio CREATE TABLE, mais queremos ter um registro de


auditória quando o comando for executado.

Com o usuário sys, damos o privilégio de criação de tabela para o usuário


USER_AUDIT, e criamos a auditoria de instrução TABLE, ou seja,as instruções afetadas
na tabela, incluindo CREATE TABLE, DROP TABLE e TRUNCATE TABLE.

SQL>GRANT create table TO user_audit;

Grant succeeded

SQL> AUDIT table by user_audit whenever successful;

Audit succeeded.

Agora com o usuário USER_AUDIT, criamos a tabela table_audit.

SQL> create table table_audit


2(
3 id number
4)
5/

Table created.

Para verificarmos se a auditoria foi bem sucedida, basta entrarmos como um usuário
sysdba e verificar na view dba_audi_trail o registro criado.

SQL> column username FORMAT A10


SQL> column obj_name FORMAT A10
SQL> column sql_text FORMAT A10
SQL> column timestamp FORMAT A35
SQL> column action_name FORMAT A20
SQL> set linezie 300

SQL> SELECT username, to_char(timestamp, 'DD/MM/YYYY HH24:MI:SS') timestamp,


2 obj_name, action_name
3 FROM dba_audit_trail
4 WHERE username = 'USER_AUDIT';

USERNAME TIMESTAMP OBJ_NAME ACTION_NAME


---------- ----------------------------------- ---------- --------------------
USER_AUDIT 27/09/2009 08:09:40 table_audit CREATE TABLE

Para desativar a auditoria do usuário user_audit, utilizamos o comando NOAUDIT,


como a seguir:

SQL> noaudit index by user_audit


Noaudit succeeded.
Pedro F. Carvalho
Analista de Sistemas
contato@pedrofcarvalho.com.br
www.pedrofcarvlho.com.br

Vamos fazer um outro exemplo, mais agora sobre a sessão do usuário. Há casos em
que há a necessidade de auditar, tanto os logins bem sucedidos como os
malsucedidos. Veja como é simples fazer isso com auditoria.

SQL> audit session whenever successful;

Audit succeeded.

SQL> audit session whenever not successful;

Audit succeeded.

Para verificar as trilhas basta:

SQL> select username, to_char(timestamp, 'DD/MM/YYYY HH24:MI:SS') Timestamp,


2 returncode, action_name
3 FROM dba_audit_trail
4 WHERE action_name in ('LOGON', 'LOGOFF');

USERNAME TIMESTAMP RETURNCODE ACTION_NAME


------------ --------------- ------------ ---------------
SYSMAN 27/09/2009 07:15:40 0 LOGOFF
USER_AUDIT 27/09/2009 09:20:25 1017 LOGON

Observe a coluna returncode no usuário user_audit, ela representa o número da


mensagem de erro da Oracle, o ORA-1017 indica que a senha está incorreta, uma
outra alternativa se estivéssemos interessados somentes nos logons e logoffs,
poderiamos usar a view DBA_AUDIT_SESSION.

2) Auditoria de objetos.

Para auditar comandos DML em tabelas, devemos utilizar esse tipo de auditoria, a
sintaxe é parecida com o de instrução. Se quiséssemos auditar todos os comandos
update executados na tabela audit_table do usuário user_audit, poderiamos fazer …

SQL> audit update on user_audit.audit_table by access whenever successful

Se o usuário user_audit decidir atualizar a tabela, ele será auditado.

SQL> update table_audit set id = 1 where id = 2;

1 row updated.

Podemos verificar na view dba_audit_trail a auditoria.

SQL> select username, to_char(timestamp, 'DD/MM/YYYY HH24:MI:SS') Timestamp,


action_name
2 FROM dba_audit_trail
3 WHERE username = 'USER_AUDIT'
Pedro F. Carvalho
Analista de Sistemas
contato@pedrofcarvalho.com.br
www.pedrofcarvlho.com.br

USERNAME TIMESTAMP ACTION_NAME


--------------------- --------------------- -------------------
USER_AUDIT 27/09/2009 11:38:41 UPDATE
USER_AUDIT 27/09/2009 11:38:58 UPDATE

3) Auditoria de privilégios.

Auditoria de privilégios tem quase a mesma sintaxe básica dos outros tipos …

SQL> audit alter tablespace by access whenever successful;

Audit succeed.

Toda vez que o privilégio ALTER TABLESPACE é utilizado com sucesso, um novo
registro é adicionado a SYS.AUD$.

Não há só a dba_audit_trail para a visualização dos registros de auditoria, para


verificar todas as views disponível, podemos fazer uma busca na dba_views.

SQL> SELECT view_name FROM dba_views


2 WHERE view_name LIKE 'DBA%AUDIT%'
3 ORDER BY view_name;

VIEW_NAME
------------------------------
DBA_AUDIT_EXISTS
DBA_AUDIT_OBJECT
DBA_AUDIT_POLICIES
DBA_AUDIT_POLICY_COLUMNS
DBA_AUDIT_SESSION
DBA_AUDIT_STATEMENT
DBA_AUDIT_TRAIL
DBA_COMMON_AUDIT_TRAIL
DBA_FGA_AUDIT_TRAIL
DBA_OBJ_AUDIT_OPTS
DBA_PRIV_AUDIT_OPTS

VIEW_NAME
------------------------------
DBA_REPAUDIT_ATTRIBUTE
DBA_REPAUDIT_COLUMN
DBA_STMT_AUDIT_OPTS

14 rows selected.

Por fim, faltou falar sobre a auditoria FGA, que é uma auditoria refinada (Fine-grained
object auditing), que é implementada pelo package DBMS_FGA. A auditoria padrão que
acabamos de aprender, é feita facilmente em objetos que foram acessados e quem
acessou, mais não se você quizer descobrir as colunas ou linhas que foram acessadas,
é nessa parte que entra a auditoria refinada, em um outro artigo falarei somente sobre
a FGA, até lá.
Pedro F. Carvalho
Analista de Sistemas
contato@pedrofcarvalho.com.br
www.pedrofcarvlho.com.br