Auditing Techniques for Oracle Database 11g Carl Dudley University of Wolverhampton, UK UKOUG Committee Oracle ACE Director carl.dudley@wlv.ac.uk Carl Dudley – University of Wolverhampton Auditing Techniques for Oracle Database 11g Working with Oracle since 1986 Oracle DBA Auditing Overview Working with Oracle since 1986 - OCP Oracle7, 8, 9, 10 Oracle Auditing DBA of Application Oracle DBA - OCP Oracle7, 8, 9, 10 the Year – 2002 Oracle DBA of the Year – 2002 Trigger-based Auditing Oracle ACE Director Oracle ACE Director Auditing the sys User Regular Presenter Regular Presenter at Oracle Conferences at Oracle Conferences Standard Auditing Consultant and Trainer Fine-Grained Auditing Technical Editor for a number of Oracle texts Consultant and Trainer Technical Editor for a UK number of Oracle texts Oracle User Group Director Managing the Audit Trail UK Oracle User GroupMember Director of IOUC Auditing Recommendations Member of IOUC Day job – University of Wolverhampton, UK Day job – University of Wolverhampton, UK 2 Security – Main facets A Authentication well known adage / Identification about software development — Who youit done right, “You canare have you can have it done fast, you can have it done cheap Authorisation Pick any two” — What you can do/see A possible adage about database security “You can have high performance, Auditing high security, — What you did high usability • The what, when, who, where and how Pick any one” Security should be database-centric, not application centric There is now a focus on the database 3 Auditing Overview What to audit How to audit How to use audit records Handling performance issues Auditing can also show work patterns, frequency of use etc. Auditing allows you to know when you have been robbed and by whom — Data can be 'stolen' without anyone knowing Perform selective auditing — Blanket auditing can have a negative performance effect — Also produces massive, difficult to handle, audit trails Last phase in security cycle – never dispense with it 4 Auditing Techniques for Oracle Database 11g Auditing Overview Application Auditing Trigger-based Auditing Auditing the sys User Standard Auditing Fine-Grained Auditing Managing the Audit Trail Auditing Recommendations 5 Application Auditing Programmed into an application — Often implemented in third party applications Often done for portability across DBMSs, or when database auditing is not well understood All aspects can be audited — Extremely flexible and extensible Maintenance of the code can be onerous Big applications are often targets for hackers Application can be bypassed rendering auditing useless — It’s application centric 6 Application Auditing Example CREATE TABLE emp_under_audit AS SELECT * FROM empcopy; Create a table (aud_emp) designed to capture audit information for the emp_under_audit table CREATE TABLE aud_emp ( username VARCHAR2(30) ,action VARCHAR2(12) ,empno NUMBER(4), ,column_name VARCHAR2(255) ,call_stack VARCHAR2(4000) ,client_id VARCHAR2(255) ,old_value VARCHAR2(25) ,new_value VARCHAR2(25) ,action_date DATE); 7 Application Auditing Example (continued) Create a procedure to generate auditing information CREATE OR REPLACE PROCEDURE proc_audit_emp ( pi_username IN VARCHAR2 ,pi_action IN VARCHAR2 ,pi_empno IN NUMBER ,pi_column_name IN VARCHAR2 ,pi_old_value IN VARCHAR2 ,pi_new_value IN VARCHAR2) AS BEGIN INSERT INTO aud_emp (username,action,empno,column_name,call_stack, client_id,old_value,new_value,action_date) VALUES (pi_username ,pi_action ,pi_empno ,pi_column_name ,dbms_utility.format_call_stack ,sys_context('userenv','client_identifier') ,pi_old_value ,pi_new_value ,sysdate); END; 8 Application Auditing Example (continued) Create a procedure to show and format the auditing information CREATE OR REPLACE PROCEDURE proc_format_aud_emp AS BEGIN FOR r IN (SELECT * FROM aud_emp ORDER BY action_date DESC) LOOP dbms_output.put_line('User: '||r.username); dbms_output.put_line('Client ID: '||r.client_id); dbms_output.put_line('Action: '||r.action); dbms_output.put_line('Empno: '||r.empno); dbms_output.put_line('Column: '||r.column_name); dbms_output.put_line('Old Value: '||r.old_value); dbms_output.put_line('New Value: '||r.new_value); dbms_output.put_line('Date: '|| TO_CHAR(r.action_date,'MON-DD-YYYY HH24:MI')); END LOOP; END; 9 Application Auditing Example (continued) Create an application procedure that is audited CREATE OR REPLACE PROCEDURE proc_update_sal( pi_empno IN NUMBER, pi_salary IN NUMBER) AS v_old_sal VARCHAR2(25); BEGIN SELECT sal INTO v_old_sal FROM emp_under_audit WHERE empno = p_empno FOR UPDATE; UPDATE emp_under_audit SET sal = pi_salary WHERE empno = pi_empno; proc_audit_emp (pi_username => user ,pi_action => 'UPDATE' ,pi_empno => pi_empno ,pi_column_name => 'SAL' ,pi_old_value => v_old_sal ,pi_new_value => pi_salary); END; / 10 Application Auditing Example (continued) Run application, executing the update procedure and auditing the changes BEGIN proc_update_sal(p_empno => 7369,p_salary => 950); proc_format_aud_emp; END; / Show the resultant call stack SELECT username,call_stack FROM aud_emp; USERNAME CALL_STACK -------- ------------------------------------SCOTT ----- PL/SQL Call Stack ----object line object handle number name 664B1434 1 anonymous block 6A1DFC34 10 procedure SCOTT.PROC_AUDIT_EMP 66614FA0 11 procedure SCOTT.PROC_UPDATE_SAL 6651D620 2 anonymous block 11 Application Auditing Example (continued) Show the captured audit information — The Client ID returns the IP_address if user was remote — Could capture much more about the user context BEGIN proc_format_aud_emp; END; / User: Client ID: Action: Empno: Column: Old Value: New Value: Date: SMITH 127.0.0.1 UPDATE 7369 SAL 800 950 SEP-07-2012 18:37 12 Auditing Techniques for Oracle Database 11g Auditing Overview Application Auditing Trigger-based Auditing Auditing the sys User Standard Auditing Fine-Grained Auditing Managing the Audit Trail Auditing Recommendations 13 Trigger-based Auditing Database centric – very popular — Sometimes called value-based auditing Can be used on INSERT, UPDATE, DELETE events (but not SELECTs) Transparent to all applications Flexible and extensible Do not always fire — Do not fire on TRUNCATE Cannot receive parameters – restricted to column values Need to be created for each and every object — Could call common procedures 14 Trigger-based Auditing – Simple Example Capture salary changes, who made the change and when using a simple trigger CREATE TRIGGER trg_a_idu_r_emp_sal AFTER INSERT OR DELETE OR UPDATE OF sal ON emp FOR EACH ROW BEGIN IF (:NEW.sal > :OLD.sal * 1.10) THEN INSERT INTO emp_sal_audit VALUES (:OLD.empno ,:OLD.sal ,:NEW.sal ,user ,sysdate); END IF; END; / — Triggers cannot capture the triggering statement — Cannot be used to define alert actions — Fine-Grained auditing may be a better option 15 Trigger to Populate Audit table Trigger fires on updates of sal — Executes proc_audit_emp to populate the pre-constructed audit table (aud_emp) CREATE OR REPLACE TRIGGER trg_b_u_r_emp_copy_sal BEFORE UPDATE OF sal ON emp_copy FOR EACH ROW DECLARE BEGIN proc_audit_emp (p_username => user, ,p_action => 'UPDATE' ,p_empno => :OLD.empno ,p_column_name => 'SAL' ,p_old_value => TO_CHAR(:OLD.sal) ,p_new_value => TO_CHAR(:NEW.sal)); END; / 16 Firing the Audit Trigger Smith performs an update which fires the trigger SMITH> UPDATE scott.emp_copy 2 SET sal = sal*1.1 3 WHERE job = 'ANALYST'; The call stack shows the trigger firing SCOTT> SELECT DISTINCT call_stack FROM aud_emp; CALL_STACK ---------------------------------------------------- PL/SQL Call Stack ----object line object handle number name 665C3F84 1 anonymous block 6675288C 10 procedure SCOTT.PROC_AUDIT_EMP 6A297C30 3 SCOTT.TRG_B_U_R_EMP_COPY_SAL 17 The Triggered Audit Records The auditing information shows two records suffering update SCOTT> BEGIN 2 proc_format_aud_emp; 3 END; 4 / User: Client ID: Action: Empno: Column: Old Value: New Value: Date: User: Client ID: Action: Empno: Column: Old Value: New Value: Date: SMITH UPDATE 7902 SAL 3000 3300 SEP-07-2012 19:37 SMITH UPDATE 7788 SAL 3000 3300 SEP-07-2012 19:37 18 Handling Rollback - Autonomous Transactions Scenario — User makes an update, inspects values and then rolls back the transaction — Records in the auditing table will also be rolled back • Loss of auditing information Cannot place COMMIT in the trigger — But can use Autonomous Transactions • Allows actions of triggers to commit independently of the triggering statement • Preserves the auditing information on rollback 19 Handling Rollback – Autonomous Transactions (continued) All updates will be audited CREATE OR REPLACE PROCEDURE proc_audit_emp ( p_username IN VARCHAR2 ,p_action IN VARCHAR2 ,p_empno IN NUMBER ,p_column_name IN VARCHAR2 ,p_old_value IN VARCHAR2 ,p_new_value IN VARCHAR2) AS PRAGMA AUTONOMOUS_TRANSACTION; BEGIN INSERT INTO aud_emp (username,action,empno,column_name,call_stack, client_id,old_value,new_value,action_date) VALUES (p_username ,p_action ,p_empno ,p_column_name ,dbms_utility.format_call_stack ,sys_context('userenv','client_identifier') ,p_old_value ,p_new_value ,sysdate); COMMIT; END; 20 Auditing Techniques for Oracle Database 11g Auditing Overview Application Auditing Trigger-based Auditing Auditing the sys User Standard Auditing Fine-Grained Auditing Managing the Audit Trail Auditing Recommendations 21 Mandatory Database Auditing Mandatory Auditing always records — Startup — Shutdown — User logins and logoffs with SYSDBA and SYSOPER privileges • Shows if an administrator has disabled auditing AUDIT_TRAIL = FALSE (or NONE) Records must be stored in the operating system because database not available on starting or stopping — On Windows in the Event Logs — On Linux and unix in $ORACLE_HOME/rdbms/audit 22 Auditing the SYS User with AUDIT_SYS_OPERATIONS ALTER SYSTEM SET AUDIT_SYS_OPERATIONS = TRUE SCOPE = SPFILE; Actions by users having SYSDBA or SYSOPER are written to OS files (XML as appropriate), not the database — All successful sys top-level SQL actions are audited • Can be seen in the Windows Event Viewer (not in aud$) — These database users should not have access to the audit records The parameter is deliberately not dynamic — Database must be 'bounced' to change its value — Stops the DBA from simply turning off auditing, perform a malicious action and then turning auditing back on • Having to bounce the database captures the disabling of the auditing 23 Example sys Audit CONNECT / AS SYSDBA ALTER SYSTEM FLUSH SHARED_POOL; UPDATE scott.emp SET sal=1000 WHERE ename='SCOTT'; When sys auditing is enabled, both the ALTER SYSTEM and UPDATE statements are displayed in the OS audit file or event log: Audit trail: LENGTH: '177' ACTION :[7] 'CONNECT' DATABASE USER:[1] '/' PRIVILEGE :[6] 'SYSDBA' CLIENT USER:[10] 'UNV\in8308' CLIENT TERMINAL:[14] 'WXPLTITR12680' STATUS:[1] '0' DBID:[10] '1318485259' . Audit trail: LENGTH: '201' ACTION :[30] 'ALTER SYSTEM FLUSH SHARED_POOL' DATABASE USER:[1] '/' PRIVILEGE :[6] 'SYSDBA' CLIENT USER:[10] 'UNV\in8308' CLIENT TERMINAL:[14] 'WXPLT-ITR12680' STATUS:[1] '0' DBID:[10] '1318485259' . Audit trail: LENGTH: '220' ACTION :[49] 'UPDATE scott.emp SET sal=1000 WHERE ename='SCOTT'' DATABASE USER:[1] '/' PRIVILEGE :[6] 'SYSDBA' CLIENT USER:[10] 'UNV\in8308' CLIENT TERMINAL:[14] 'WXPLT-ITR12680' STATUS:[1] '0' DBID:[10] '1318485259' . 24 Auditing Auditing Overview Application Auditing Trigger-based Auditing Auditing the sys User Standard Auditing Fine-Grained Auditing Managing the Audit Trail Auditing Recommendations 25 Values of AUDIT_TRAIL for Standard Auditing Value of AUDIT_TRAIL Auditing Activity FALSE (Default) (NONE on Oracle10g) No standard auditing activity OS Records are written to OS Do this for same reasons as for AUDIT_SYS_OPERATIONS Accessible when database is down XML (or XML,EXTENDED) Records written as XML New view (V$XML_AUDIT_TRAIL ) shows these records in relational format and makes them 'queryable' via SQL EXTENDED causes audit of sql text and bind variable values DB (or DB,EXTENDED) Records are written to a database table (sys.aud$) Makes it easier to run reports The audit trail does not store data values 26 Setting Standard Auditing ALTER SYSTEM SET AUDIT_TRAIL = DB,EXTENDED SCOPE = SPFILE; The parameter is deliberately not dynamic — Database must be 'bounced' to change its value — Set this value on database creation to avoid a database 'bounce' later If AUDIT_FILE_DEST is not specified, the default OS location is — Solaris $ORACLE_BASE/admin/$DB_UNIQUE_NAME/adump — Windows $ORACLE_BASE\admin\$DB_UNIQUE_NAME\adump 27 Scoping Audit Activity – Standard Auditing Specific objects Executing procedures Use of a system privilege Specific users Successful and/or unsuccessful actions Per action or per session (per session is not a realistic option on 11g) Allows focussing of auditing activity — Important to fine tune this to avoid performance and storage issues Allows monitoring of privileged users – DBAS etc. 28 Auditing Connections Need to know who and when — Most outages are down to human activity — Not easy for users of applications using connection pools Generates lots of records — Need adequate disk space and purging policy To audit connections, two criteria must be set — Ensure AUDIT_TRAIL = DB,EXTENDED — When connected as the user system, issue the command AUDIT SESSION; AUDIT SESSION BY scott,smith; — Audits connections only for scott and smith Not much defence for not having this information 29 Auditing Connections (continued) Script to report on audit of user logons and logoffs BEGIN FOR r IN (SELECT username ,action_name ,TO_CHAR(timestamp, 'DD-MON HH24:MI') LOGON ,TO_CHAR(logoff_time, 'DD-MON HH24:MI') LOGOFF ,priv_used ,comment_text FROM dba_audit_trail) LOOP dbms_output.put_line('User: '||r.username); dbms_output.put_line('Action: '||r.action_name); dbms_output.put_line('Logon: '||r.LOGON); dbms_output.put_line('Logoff: '||r.LOGOFF); dbms_output.put_line('Priv: '||r.priv_used); dbms_output.put_line('Comments: '||r.comment_text); dbms_output.put_line('-----End of audit record-----'); END LOOP; END; 30 Audit Report Output User scott has created a session and then exited almost immediately SYS>/ User: SCOTT Action: LOGON Logon: 12-SEP 09:24 Logoff: User has yet to logoff Priv: CREATE SESSION Comments: Authenticated by: DATABASE; Client address: (ADDRESS=(PROTOCOL=tcp)(HOST=169.254.207.135)(PORT=2817)) ------End of audit record-----PL/SQL procedure successfully completed. SYS> / User: SCOTT Action: LOGOFF Logon: 12-SEP 09:24 Logoff: 12-SEP 09:25 Priv: CREATE SESSION Comments: Authenticated by: DATABASE; Client address: (ADDRESS=(PROTOCOL=tcp)(HOST=169.254.207.135)(PORT=2817)) ---------End of audit record--------— On Oracle11g you may see DBSNMP and SYSMAN activity 31 Statement Auditing The use of any kind of SQL statement can be audited — Can be based on whether the statement is successful, unsuccessful or both Examples of auditing based on statements affecting types of objects AUDIT ROLE,TABLE; — Audits CREATE, ALTER, DROP of any role or table AUDIT CREATE TABLE; — Audits CREATE TABLE statements AUDIT ALTER TABLE WHENEVER NOT SUCCESSFUL; — Audits ALTER TABLE statements only when they are unsuccessful 32 Statement Auditing (continued) Audit all unsuccessful SELECT, INSERT, DELETE statements on all tables and any unsuccessful attempt at executing a procedure AUDIT SELECT TABLE, INSERT TABLE, DELETE TABLE, EXECUTE PROCEDURE BY ACCESS WHENEVER NOT SUCCESSFUL; Can be specified on a per user basis AUDIT DELETE TABLE BY tt BY ACCESS; 33 Tracking Statement Auditing Statement level auditing is shown in dba_stmt_audit_opts AUDIT CREATE EXTERNAL JOB BY tt; SELECT * FROM dba_stmt_audit_opts; USER_NAME PROXY_NAME AUDIT_OPTION --------- ---------- ------------------: : DROP ANY TABLE CREATE EXTERNAL JOB TT CREATE EXTERNAL JOB : : SUCCESS ---------: BY SESSION BY SESSION BY SESSION : FAILURE ---------: BY SESSION BY SESSION BY SESSION : NOAUDIT CREATE EXTERNAL JOB; SELECT * FROM dba_stmt_audit_opts; USER_NAME PROXY_NAME AUDIT_OPTION --------- ---------- ------------------: : DROP ANY TABLE TT CREATE EXTERNAL JOB : : SUCCESS ---------: BY SESSION BY SESSION : FAILURE ---------: BY SESSION BY SESSION : 34 Privilege-Based Auditing Examples of auditing on types of privileges AUDIT DELETE ANY TABLE; — Audits any successful or unsuccessful action that depends on the DELETE ANY TABLE privilege AUDIT UPDATE ANY TABLE BY ACCESS WHENEVER NOT SUCCESSFUL; — Audits each unsuccessful use of the UPDATE ANY TABLE privilege • Default is BY SESSION The AUDIT SYSTEM privilege is required by any user that sets up system or privilege-based auditing — This would normally be the security administrator and no-one else 35 Object-based Auditing Object owners and administrators can set object-based auditing — AUDIT ANY allows auditing to be set on any object Examples of auditing on specific objects — Audit successful attempts to query the emp table on a session basis AUDIT SELECT ON emp WHENEVER SUCCESSFUL; — Audit all unsuccessful attempts to query scott's dept table by access AUDIT SELECT, INSERT, DELETE ON scott.dept BY ACCESS WHENEVER NOT SUCCESSFUL; 36 Object-based Auditing (continued) Object Option ALTER Table X View -- Seq X Proc Func Pkg -- AUDIT X X X X X COMMENT X X -- -- DELETE X X -- EXECUTE -- -- FLASHBACK X GRANT Lib -- Object Type X Context -- X -- X X X -- -- -- -- -- X -- -- -- -- -- X -- -- X -- -- X -- -- -- -- -- -- -- X X X X -- X X X X INDEX X -- -- -- X -- -- -- -- INSERT X X -- -- X -- -- -- -- LOCK X X -- -- X -- -- -- -- READ -- -- -- -- -- X -- -- -- WRI ???? RENAME X X -- -- -- -- -- -- -- REF SELECT Obsolete, do not use X X X -- X -- -- -- -- UPDATE X -- X -- -- -- -- CRE ???? X -- Mview X Dir -- 37 Object Level Auditing Cannot be specified on a per user basis AUDIT DELETE,UPDATE ON SCOTT.EMP WHENEVER NOT SUCCESSFUL; AUDIT SELECT ON SCOTT.EMP BY ACCESS; AUDIT INSERT ON SCOTT.EMP BY ACCESS WHENEVER SUCCESSFUL; SELECT * FROM dba_obj_audit_opts; OBJECT_ OWNER OBJECT_NAME TYPE ALT AUD COM DEL GRA IND INS LOC REN SEL UPD REF EXE CRE REA WRI FBK ----- ----------- ------- --- --- --- --- --- --- --- --- --- --- --- --- --- --- --- --- --SCOTT EMP TABLE -/- -/- -/- -/S -/- -/- A/- -/- -/- A/A -/S -/- -/- -/- -/- -/- -/- AUDIT ALL ON dept; — Audits all possible options on the object NOAUDIT ALL ON dept; — Removes EVERY audit option on the object 38 BY SESSION vs BY ACCESS Originally, BY SESSION created one audit record for statements causing the same auditing activity — BY ACCESS creates audit record each time an auditable statement is run On Oracle 11g BY SESSION causes auditing as many times as BY ACCESS but records less information — Still remains as default Oracle recommend to use BY ACCESS — Similar overheads but more information 39 Monitoring Object Auditing Status of objects being audited SELECT upd "Update Option" FROM dba_obj_audit_opts WHERE object_name IN ('DEPT','EMP'); OBJECT_NAME ----------DEPT EMP Update Option ------------A/S/A S = by session A = by access - = no auditing First character shows if auditing is enabled for successful attempts Character after the '/' shows if auditing is enabled for unsuccessful attempts Object auditing in audit trail SELECT ses_actions,returncode FROM dba_audit_object; SES_ACTIONS RETURNCODE ---------------- ------------------F-----913 ---F-----------913 ---------S-----0 ---S-----------0 delete select DELETE FROM emp WHERE empno = (SELECT * FROM emp WHERE ename = 'x'); ORA-00913: too many values DELETE FROM emp WHERE empno = (SELECT empno FROM emp WHERE ename = 'x'); 40 Monitoring System Wide Auditing Show auditing status of user logins with dba_stmt_audit_opts SELECT * FROM dba_stmt_audit_opts; USER_NAME PROXY_NAME AUDIT_OPTION SUCCESS FAILURE --------- ---------- -------------- --------- --------CREATE SESSION BY ACCESS BY ACCESS Show auditing status of system privileges with dba_priv_audit_opts SELECT * FROM dba_priv_audit_opts; USER_NAME PROXY_NAME PRIVILEGE SUCCESS FAILURE --------- ---------- ---------------- --------- --------SELECT ANY TABLE BY ACCESS BY ACCESS The dba_common_audit_trail view shows all auditing information — Includes Fine-Grained Auditing 41 Auditing the Audit Trail If ordinary users have access to sys.aud$ then that access needs to be audited AUDIT SELECT, INSERT, UPDATE, DELETE ON sys.aud$ BY ACCESS; — Any actions performed by non-SYSDBA users will now be audited A simple SELECT on sys.aud$ will generate an audit record in aud$ — A DELETE of this audit record will succeed, but it will generate another record of the delete operation Any records of DML performed on aud$ cannot be deleted by regular users Setting up this type of auditing acts as a safety feature, potentially revealing unusual or unauthorized actions 42 The Auditing Views STMT_AUDIT_OPTION_MAP AUDIT_ACTIONS ALL_DEF_AUDIT_OPTS DBA_STMT_AUDIT_OPTS DBA_PRIV_AUDIT_OPTS DBA_OBJ_AUDIT_OPTS USER_OBJ_AUDIT_OPTS DBA_AUDIT_TRAIL USER_AUDIT_TRAIL DBA_AUDIT_OBJECT USER_AUDIT_OBJECT DBA_AUDIT_SESSION USER_AUDIT_SESSION DBA_AUDIT_STATEMENT USER_AUDIT_STATEMENT DBA_AUDIT_EXISTS DBA_AUDIT_POLICIES DBA_FGA_AUDIT_TRAIL DBA_COMMON_AUDIT_TRAIL Contains information about auditing option type codes. Created by the SQL.BSQ script at CREATE DATABASE time. Contains descriptions for audit trail action type codes Contains default object-auditing options to be applied on object creation Describes current system auditing options across system and by user Describes current system privileges being audited across system and by user Describes auditing options on all objects The USER view shows auditing options on all objects owned by current user Lists all audit trail entries The USER view shows audit trail entries relating to current user. Contains audit trail records for all objects in the system The USER view lists audit trail records for statements concerning objects that are accessible to the current user Lists all audit trail records concerning CONNECT and DISCONNECT The USER view lists all audit trail records concerning connections and disconnections for the current user Lists audit trail records concerning GRANT, REVOKE, AUDIT, NOAUDIT, and ALTER SYSTEM statements throughout the database , or for the USER view, issued by the user. Lists audit trail entries produced by AUDIT NOT EXISTS Shows all the auditing policies on the system. Lists audit trail records for value-based auditing Combines standard and fine-grained audit log records, and includes sys and mandatory audit records written in XML format 43 Setting up Audit Information Trigger sets the client identifier for each session at login time CREATE OR REPLACE TRIGGER trg_set_client_info AFTER LOGON ON DATABASE DECLARE v_module v$session.module%TYPE; BEGIN SELECT module INTO v_module FROM v$process p, v$session s WHERE p.addr = s.paddr AND s.audsid = USERENV('sessionid'); dbms_session.set_identifier(sys_context ('userenv','ip_address') ||' - '||v_module); END; / — Could set many other criteria such as authentication method 44 Auditing Statements Example shows three SELECT statements that will generate audit records — The statement issued by system will generate three audit records CONN system/manager SELECT ename,sal FROM scott.emp WHERE sal < (SELECT sal FROM scott.emp WHERE ename = 'WARD') AND job = (SELECT job FROM scott.emp WHERE ename = 'WARD'); CONN scott/tiger SELECT job FROM scott.emp; SELECT empno FROM scott.emp; 45 Correlating Audit Records CREATE OR REPLACE PROCEDURE format_aud AS BEGIN FOR r IN (SELECT db_user ,client_id ,object_schema ,object_name ,extended_timestamp ,sql_text ,statementid FROM dba_common_audit_trail GROUP BY db_user ,statementid ,sql_text The grouping of statementids will cause ,object_schema the system statement to show as one entry ,object_name ,client_id ,extended_timestamp ORDER BY extended_timestamp ASC) LOOP dbms_output.put_line('Who: '||r.db_user); dbms_output.put_line('What: '||r.object_schema||'.'||r.object_name); dbms_output.put_line('Where: '||r.client_id); dbms_output.put_line('When: ' ||TO_CHAR(r.extended_timestamp,'MON-DD HH24:MI')); dbms_output.put_line('How: '||r.sql_text); dbms_output.put_line('--------------End of audit record--------------'); END LOOP; END; 46 Correlated Output from the Audit Trail The system record shows only once SQLPLUS is shown as part of the identifier (set by the trigger) Who: SYSTEM What: SCOTT.EMP Where: 127.0.0.1 - sqlplus.exe When: SEP-2012 11:15 How: SELECT ename,sal FROM scott.emp WHERE sal < (SELECT sal FROM scott.emp WHERE ename = 'WARD') AND job = (SELECT job FROM scott.emp WHERE ename = 'WARD') --------------End of audit Record-------------Who: SCOTT What: SCOTT.EMP Where: 127.0.0.1 - sqlplus.exe When: SEP-2012 11:15 How: SELECT job FROM scott.emp --------------End of audit Record-------------Who: SCOTT What: SCOTT.EMP Where: 127.0.0.1 - sqlplus.exe When: SEP-2012 11:15 How: SELECT ename FROM scott.emp; The SELECT statement is captured because AUDIT_TRAIL = DB,EXTENDED 47 Performance Impact of Audit With auditing CREATE OR REPLACE PROCEDURE perf_test_aud AS BEGIN FOR rec IN 1..50000 LOOP FOR inner_rec IN (SELECT ename FROM scott.emp) LOOP NULL; END LOOP; END LOOP; END; / EXEC perf_test_aud Elapsed : 39.93 seconds 48 Performance Impact of Audit (continued) Disable auditing and then re-execute NOAUDIT SELECT ON scott.emp; CREATE OR REPLACE PROCEDURE perf_test_aud AS BEGIN FOR rec IN 1 ..50000 LOOP FOR inner_rec IN (SELECT ename FROM scott.emp) LOOP NULL; END LOOP; END LOOP; END; / EXEC perf_test_aud Elapsed : 12.26 seconds 49 Auditing Limitations Not able to show what data the user actually saw — But captures SCN of the operation — Could use Flashback based on the SCN to see the data • Depends on UNDO_RETENTION — Oracle Consultancy have Selective Audit as a 'full' solution Audit data persists after a rollback Audit is generated even when no rows affected Cannot audit on specific columns or conditions Fine-grained auditing gives extra possibilities 50 Auditing Auditing Overview Application Auditing Trigger-based Auditing Auditing the sys User Standard Auditing Fine-Grained Auditing Managing the Audit Trail Auditing Recommendations 51 Fine-Grained Auditing (FGA) Features 1. Boolean condition check — Anything specified in SQL — Comparison of function call results 2. Column sensitivity 3. Event Handler 4. SQL capture Conditional auditing helps to reduce unnecessary audits Business rule — Employees should see only their own record • Auditing on the table generates audit information for all SELECTs • Sifting through the audit is cumbersome 52 Setting UP FGA FGA does not depend on any initialisation parameters Implement auditing for users accessing other employees' records BEGIN dbms_fga.add_policy(object_schema => 'SCOTT' ,object_name => 'EMPTAB_FGA' ,policy_name => 'fga_emp' ,audit_condition => 'ENAME != USER' ,audit_trail => dbms_fga.db + dbms_fga.extended); END; audit_trail will place audit in fga_log$ (with sql texts) (default) — Can alternatively be specified as XML If audit_condition is left as NULL, the audit always happens Requires the use of the cost-based optimizer and generation of statistics 53 Generating FGA records Two statements using the emptab_fga table SELECT sal,ename FROM scott.emptab_fga WHERE ename = 'SCOTT'; SAL ENAME ---------- ---------3000 SCOTT SELECT sal,ename FROM scott.emptab_fga WHERE ename = 'SMITH'; SAL ENAME ---------- ---------2850 SMITH — Only one entry is placed in the audit table (SMITH is not the user SCOTT) Who: SCOTT What: SCOTT.EMPTAB_FGA Where: - sqlplusw.exe When: Nov-09 12:52 How: SELECT sal,ename FROM scott.emptab_fga WHERE ename = 'SMITH' --------------End of audit record-------------- 54 Fine Grained Auditing Features When AUDIT_TRAIL = DB or DB,EXTENDED, the FGA records are stored in the fga_log$ table owned by sys by default — Shown in dba_fga_audit_trail — Also seen in dba_common_audit_trail with other auditing information • Clearing out aud$ will not remove FGA records Fine-grained auditing goes beyond triggers — Triggers incur a PL/SQL call for every row processed • Create an audit record only when a relevant column is changed by DML — FGA is not invoked for every row - only once for every policy • Audit occurs when a specified column is either changed or used in selection criteria – Uncovers users who hope their actions will be masked because they use the sensitive columns only in the selection criteria 55 Targeting Fine-Grained Auditing Use functions to perform complex checking — Gives flexibility to policies CREATE OR REPLACE FUNCTION outside_hours RETURN BINARY_INTEGER AS v_return_val NUMBER; v_day_of_week VARCHAR2(1) := TO_CHAR(sysdate,'DY'); v_hour NUMBER(2):= TO_NUMBER(TO_CHAR(sysdate, 'HH24')); BEGIN IF (v_day_of_week IN ('SAT', 'SUN') OR v_hour < 8 OR v_hour > 17) THEN v_return_val := 1; ELSE v_return_val := 0; END IF; RETURN v_return_val; END; — Checks if time is outside of working hours 56 Manipulating Auditing Polices Auditing occurs on emptab_fga if function outside_hours returns '1' — Outside of working hours BEGIN dbms_fga.drop_policy( object_schema => 'SCOTT' ,object_name => 'EMPTAB_FGA' ,policy_name => 'fga_emp'); END; / BEGIN dbms_fga.add_policy( object_schema => ,object_name => ,policy_name => ,audit_condition => END; / 'SCOTT' 'EMPTAB_FGA' 'fga_emp' 'SECADMIN.OUTSIDE_HOURS = 1'); 57 Column Sensitivity Any employee is allowed to access other employee's records — But must not access the sensitive sal column This rule needs column sensitivity — Auditing occurs only if the column is retrieved and the condition is met — If no condition, auditing happens when the column is retrieved or manipulated BEGIN dbms_fga.add_policy(object_schema ,object_name ,policy_name ,audit_condition ,audit_column END; / => => => => => 'SCOTT' 'EMPTAB_FGA' 'fga_emp' 'ENAME != USER' 'SAL'); 58 Options for Column Auditing Use audit_column_opts — Relevant only when there is a list of columns in audit_column — Governs whether a statement is audited Value of audit_column_opts Auditing action any_columns the statement is audited if it references any column specified in the audit_column parameter (default value) all_columns the statement must reference all columns listed in audit_column to be audited 59 Column Sensitive Audit Test Which of the following statements will be audited? 1. SELECT AVG(sal) FROM emptab_fga; 2. SELECT sal FROM emptab_fga WHERE ename = 'SCOTT'; 3. SELECT empno,job,sal FROM emptab_fga WHERE deptno = 10; 4. SELECT empno,job FROM emptab_fga WHERE deptno = 10; 5. SELECT sal FROM emptab_fga WHERE ename = 'ZULU'; 6. SELECT ename FROM emptab_fga WHERE ename = 'SMITH'; 7. SELECT ename FROM emptab_fga WHERE sal > 2975; 60 Audited Statements Statements 1, 3 and 7 Who: SCOTT What: SCOTT.EMPTAB_FGA Where: - sqlplusw.exe When: Nov-11 16:18 How: SELECT AVG(sal) FROM emptab_fga --------------End of audit record-------------Who: SCOTT What: SCOTT.EMPTAB_FGA Where: - sqlplusw.exe When: Nov-11 16:18 How: SELECT empno,job,sal FROM emptab_fga WHERE deptno = 10 --------------End of audit record-------------Who: SCOTT What: SCOTT.EMPTAB_FGA Where: - sqlplusw.exe When: Nov-11 16:18 How: SELECT ename FROM emptab_fga WHERE sal > 2975 --------------End of audit record-------------- 61 Pushing Audit Information Could be a delay before audit records are seen Push alerts out to DBAs — Use an event handler — No need to query the audit log for information BEGIN dbms_fga.add_policy(object_schema ,object_name ,policy_name ,audit_condition ,audit_column ,handler_schema ,handler_module END; / => => => => => => => 'SCOTT', 'EMPTAB_FGA' 'fga_emp' 'ENAME != USER' 'SAL' 'SECADMIN' 'FGA_ALERT'); 62 The Event Handler CREATE OR REPLACE PROCEDURE fga_alert (pi_sch VARCHAR2 ,pi_tab VARCHAR2 ,pi_pol VARCHAR2) AS msg VARCHAR2(20000); BEGIN msg := 'Wake up Carl - the '||pi_tab||' table owned by '|| pi_sch||' has been accessed with this statement : '||sys_context('userenv','current_sql')||'. The time is : ' ||TO_CHAR(SYSDATE, 'Day DD MON, YYYY HH24:MI:SS'); UTL_MAIL.SEND ( sender => 'oracle_database@wlv.ac.uk' ,recipients => 'carl.dudley@wlv.ac.uk' ,subject => 'Salaries in the HR.EMPLOYEES table have been accessed' ,message => msg); END email_alert; / 63 FGA Summary FGA will not see modifications to queries caused by RLS FGA does not show the data that the user received FGA does not occur when no rows are returned or updated — Could combine it with standard auditing Cannot circumvent any fine-grained auditing arrangements — Database centric 64 Auditing Auditing Overview Application Auditing Trigger-based Auditing Auditing the sys User Standard Auditing Fine-Grained Auditing Managing the Audit Trail Auditing Recommendations 65 Managing Auditing – the aud$ Table When AUDIT_TRAIL is set to DB or DB,EXTENDED — Auditing information is stored in sys.aud$ in the system tablespace — Maximum size governed by storage parameters for system tablespace Periodically remove data from aud$ to free up space and aid searching — The aud$ (and fga_log$) tables are ABSOLUTELY THE ONLY dictionary tables on which direct DML can be performed • Do not insert, update or delete records in any other dictionary table — Ordinarily, only sys can perform deletes on the aud$ table Any delete on the audit trail is itself audited — Beware sys can TRUNCATE the aud$ table 66 Audit Trail – Manual Management If audit trail is full and CREATE SESSION is being audited — Users cannot connect to the database — In this case, connect as SYS and make space in the audit trail DELETE FROM sys.aud$ WHERE ntimestamp# > TO_TIMESTAMP ('01-JAN-12 08.08.58.427000 PM') AND ntimestamp# < TO_TIMESTAMP ('31-MAR-12 10.23.59.681000 PM'); DELETE FROM sys.aud$; Shrink or truncate aud$ to regain the space if required ALTER TABLE sys.aud$ SHRINK SPACE; TRUNCATE TABLE sys.aud$; 67 Audit Trail Management Settings SELECT * FROM dba_audit_mgmt_config_params; PARAMETER_NAME ------------------------DB AUDIT TABLESPACE DB AUDIT TABLESPACE AUDIT FILE MAX SIZE AUDIT FILE MAX SIZE AUDIT FILE MAX AGE AUDIT FILE MAX AGE DB AUDIT CLEAN BATCH SIZE DB AUDIT CLEAN BATCH SIZE OS FILE CLEAN BATCH SIZE OS FILE CLEAN BATCH SIZE PARAMETER_VALUE --------------SYSAUX SYSAUX 10000 10000 5 5 10000 10000 1000 1000 AUDIT_TRAIL -------------------STANDARD AUDIT TRAIL FGA AUDIT TRAIL OS AUDIT TRAIL XML AUDIT TRAIL OS AUDIT TRAIL XML AUDIT TRAIL STANDARD AUDIT TRAIL FGA AUDIT TRAIL OS AUDIT TRAIL XML AUDIT TRAIL Values can be set using dbms_audit_mgmt — Part of SE and EE from Oracle11gR2 • Previously available only through Audit Vault 68 Audit Trail – Automatic Management For the database audit trail, individual audit records created before a specified timestamp can be purged using dbms_audit_mgmt For the operating system audit trail, you purge whole audit files that were created before the timestamp — Can take a while to complete Preliminary steps : 1. If necessary, tune online and archive redo log sizes • Deleting the audit trail can generate much redo and undo • Could move audit trail to sysaux tablespace – Use dbms_audit_mgmt.set_audit_trail_location 2. Plan a timestamp and archive strategy • Decide how much audit to keep 3. Initialize the audit trail cleanup operation • Use dbms_audit_mgmt.init_cleanup 69 Automatic Management using dbms_audit_trail BEGIN dbms_audit_mgmt.init_cleanup( audit_trail_type => dbms_audit_mgmt.audit_trail_fga_std ,default_cleanup_interval => 24); END; FGA audit trail will now be in sysaux CREATE OR REPLACE PROCEDURE sys.delete_dbfga_records IS BEGIN dbms_audit_mgmt.set_last_archive_timestamp( audit_trail_type => dbms_audit_mgmt.audit_trail_fga_std ,last_archive_time => SYSTIMESTAMP – 1); dbms_audit_mgmt.clean_audit_trail( audit_trail_type => dbms_audit_mgmt.audit_trail_fga_std ,use_last_arch_timestamp => TRUE); END; Cleans out FGA audit records earlier than the newly set timestamp 70 Create Job with Schedule to Clean the Audit Trail Test routine cleans the audit trail every ten seconds BEGIN dbms_scheduler.create_schedule ( schedule_name => 'DELETE_DBFGA_RECORDS_SCHED' ,repeat_interval =>'FREQ = SECONDLY; INTERVAL = 10;’); END; BEGIN dbms_scheduler.create_job ( job_name => 'DELETE_DBFGA_RECORDS_JOB' ,job_type => 'STORED_PROCEDURE' ,job_action => 'SYS.DELETE_DBFGA_RECORDS' ,enabled => TRUE ,auto_drop => false ,schedule_name => 'DELETE_DBFGA_RECORDS_SCHED'); END; 71 dbms_audit_mgmt.create_purge_job Automates setting up the job for purging (wrapper on dbms_scheduler) BEGIN dbms_audit_mgmt.create_purge_job( audit_trail_type => dbms_audit_mgmt.audit_trail_fga_std ,audit_trail_purge_interval => 1 ,audit_trail_purge_name => 'HOURLY_PURGE_FGA' ,use_last_arch_timestamp => TRUE); END; — But cannot advance/change the timestamp • Still need to set up a procedure and job/schedule to do the advance — Minimum interval is one hour See the Oracle Support document — Known Issues When Using: DBMS_AUDIT_MGMT [ID 804624.1] 72 Automatic of Audit Trail Audit Trail Purging – Automatic Management (continued) Optionally, Configure audit trail records to be deleted in batches BEGIN dbms_audit_mgmt.set_audit_trail_property( audit_trail_type => dbms_audit_mgmt.audit_trail_db_std ,audit_trail_property => dbms_audit_mgmt.db_delete_batch_size ,audit_trail_property_value => 100000); Standard auditing END; — audit_trail_type can be set to • audit_trail_db_std • audit_trail_db_aud ?? • audit_trail_xml • audit_trail_all ?? 1st purge Start auditing 2nd purge audit_trail_fga_std audit_trail_os audit_trail_files 3rd purge 4th purge time 73 Auditing Auditing Overview Application Auditing Trigger-based Auditing Auditing the sys User Standard Auditing Fine-Grained Auditing Managing the Audit Trail Auditing Recommendations 74 Auditing Recommendations Use system level auditing Use FGA where appropriate Audit access and change to critical data Analyse the audit trail and logs — Tools can help here Create reports Create procedures / policies Review report contents Set alerts Act on the contents 75 Auditing Techniques for Oracle Database 11g Carl Dudley University of Wolverhampton, UK UKOUG Committee Oracle ACE Director carl.dudley@wlv.ac.uk Carl Dudley – University of Wolverhampton