User Tools

Site Tools


user_profiles

Pete Finnigan has a set of scripts not only to hack and find exploits but also to find things like users with privileges they should not have.

script to show schema / user profile and the profile setup

set lines 200 pages 1000
col username           for a23  head "Username"
col dba                for a5   head "DBA|privs"
col status             for a8   head "Status"
col lock_date          for a21  head "Lock|date"
col expiry_date        for a21  head "Expiry|date"
col default_tablespace for a20  head "Default|tablespace"
col profile            for a18  head "Profile"
col pwd_verify         for a20  head "Pwd|function"
col plt                for a4   head "Pwd|life"
col fla                for a8   head "Failed|logins"
col rum                for a5   head "Pwd|reuse"
col pgt                for a5   head "Pwd|grace"
col pwd_lok            for a7   head "Lock|days"

with profile_detail as
(
select dbp.profile
,      dbp.resource_name
,      decode(dbp.limit,'DEFAULT',def.limit,'NULL','','UNLIMITED','',dbp.limit) limit
from   dba_profiles dbp
,     (select def.resource_name
       ,      decode(def.limit,'NULL','','UNLIMITED','',def.limit) limit
       from   dba_profiles def
       where  profile = 'DEFAULT'
      ) def
where  1=1
and    dbp.resource_name = def.resource_name
order  by 2,1
)
select dbu.username
,      decode(dba.grantee,null,'NO','YES') dba
,      replace( replace( replace( replace(dbu.account_status,'LOCKED','LOCK'), 'EXPIRED','EXP'), '(GRACE)','(GR)'), ' & ','&') status
,      dbu.lock_date
,      dbu.expiry_date
,      dbu.default_tablespace
,      dbu.profile
,      pwd.limit pwd_verify
,      plt.limit plt
,      fla.limit fla
,      rum.limit rum
,      pgt.limit pgt
,      plk.limit pwd_lok
from   dba_users dbu
,     (select grantee
       from   dba_role_privs
       where  granted_role = 'DBA'
      ) dba
,      profile_detail pwd
,      profile_detail plt
,      profile_detail fla
,      profile_detail rum
,      profile_detail pgt
,      profile_detail plk
where  1=1
and    pwd.profile       = dbu.profile
and    pwd.resource_name = 'PASSWORD_VERIFY_FUNCTION'
and    plt.profile       = dbu.profile
and    plt.resource_name = 'PASSWORD_LIFE_TIME'
and    fla.profile       = dbu.profile
and    fla.resource_name = 'FAILED_LOGIN_ATTEMPTS'
and    rum.profile       = dbu.profile
and    rum.resource_name = 'PASSWORD_REUSE_MAX'
and    pgt.profile       = dbu.profile
and    pgt.resource_name = 'PASSWORD_GRACE_TIME'
and    plk.profile       = dbu.profile
and    plk.resource_name = 'PASSWORD_LOCK_TIME'
and    dbu.username      = dba.grantee(+)
order  by expiry_date
/

Password verification function for user profile

FUNCTION verify_function_11g
(username varchar2,
  password varchar2,
  old_password varchar2)
  RETURN boolean IS
   n boolean;
   m integer;
   differ integer;
   isdigit boolean;
   ischar  boolean;
   ispunct boolean;
   db_name varchar2(40);
   digitarray varchar2(20);
   punctarray varchar2(25);
   chararray varchar2(52);
   i_char varchar2(10);
   simple_password varchar2(10);
   reverse_user varchar2(32);

BEGIN
   digitarray:= '0123456789';
   chararray:= 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';
   punctarray:='!"#$%&()``*+,-/:;<=>?_';

   -- Check for the minimum length of the password
   IF length(password) < 8 THEN
      raise_application_error(-20001, 'Password length less than 8');
   END IF;


   -- Check if the password is same as the username or username(1-100)
   IF NLS_LOWER(password) = NLS_LOWER(username) THEN
     raise_application_error(-20002, 'Password same as or similar to user');
   END IF;
   FOR i IN 1..100 LOOP
      i_char := to_char(i);
      if NLS_LOWER(username)|| i_char = NLS_LOWER(password) THEN
        raise_application_error(-20005, 'Password same as or similar to user name ');
      END IF;
    END LOOP;

   -- Check if the password is same as the username reversed

   FOR i in REVERSE 1..length(username) LOOP
     reverse_user := reverse_user || substr(username, i, 1);
   END LOOP;
   IF NLS_LOWER(password) = NLS_LOWER(reverse_user) THEN
     raise_application_error(-20003, 'Password same as username reversed');
   END IF;

   -- Check if the password is the same as server name and or servername(1-100)
   select name into db_name from sys.v$database;
   if NLS_LOWER(db_name) = NLS_LOWER(password) THEN
      raise_application_error(-20004, 'Password same as or similar to server name');
   END IF;
   FOR i IN 1..100 LOOP
      i_char := to_char(i);
      if NLS_LOWER(db_name)|| i_char = NLS_LOWER(password) THEN
        raise_application_error(-20005, 'Password same as or similar to server name ');
      END IF;
    END LOOP;

   -- Check if the password is too simple. A dictionary of words may be
   -- maintained and a check may be made so as not to allow the words
   -- that are too simple for the password.
   IF NLS_LOWER(password) IN ('welcome1', 'database1', 'account1', 'user1234',
        'password1', 'oracle123', 'computer1', 'abcdefg1', 'change_on_install') THEN
      raise_application_error(-20006, 'Password too simple');
   END IF;

   -- Check if the password is the same as oracle (1-100)
    simple_password := 'oracle';
    FOR i IN 1..100 LOOP
      i_char := to_char(i);
      if simple_password || i_char = NLS_LOWER(password) THEN
        raise_application_error(-20007, 'Password too simple ');
      END IF;
    END LOOP;

   -- Check if the password contains at least one letter, one digit
   -- 1. Check for the digit
   isdigit:=FALSE;
   m := length(password);
   FOR i IN 1..10 LOOP
      FOR j IN 1..m LOOP
         IF substr(password,j,1) = substr(digitarray,i,1) THEN
            isdigit:=TRUE;
             GOTO findchar;
         END IF;
      END LOOP;
   END LOOP;

   IF isdigit = FALSE THEN
      raise_application_error(-20008, 'Password must contain at least one digit');
   END IF;

   -- 2. Check for the character
   <<findchar>>
   ischar:=FALSE;
   FOR i IN 1..length(chararray) LOOP
      FOR j IN 1..m LOOP
         IF substr(password,j,1) = substr(chararray,i,1) THEN
            ischar:=TRUE;
             GOTO findpunct;
         END IF;
      END LOOP;
   END LOOP;
   IF ischar = FALSE THEN
      raise_application_error(-20009, 'Password must contain at least one alphabetic character');
   END IF;

   -- 3. Check for the punctuation
   <<findpunct>>
   ispunct:=FALSE;
   FOR i IN 1..length(punctarray) LOOP
      FOR j IN 1..m LOOP
         IF substr(password,j,1) = substr(punctarray,i,1) THEN
            ispunct:=TRUE;
             GOTO endsearch;
         END IF;
      END LOOP;
   END LOOP;
   IF ispunct = FALSE THEN
      raise_application_error(-20010, 'Password should contain at least one punctuation');
   END IF;


   <<endsearch>>
   -- Check if the password differs from the previous password by at least
   -- 3 letters
   IF old_password IS NOT NULL THEN
     differ := length(old_password) - length(password);

     differ := abs(differ);
     IF differ < 3 THEN
       IF length(password) < length(old_password) THEN
         m := length(password);
       ELSE
         m := length(old_password);
       END IF;

       FOR i IN 1..m LOOP
         IF substr(password,i,1) != substr(old_password,i,1) THEN
           differ := differ + 1;
         END IF;
       END LOOP;

       IF differ < 1 THEN
         raise_application_error(-20011, 'Password should differ from the \\
            old password by at least 1 characters');
       END IF;
     END IF;
   END IF;
   -- Everything is fine; return TRUE ;
   RETURN(TRUE);
END;
user_profiles.txt · Last modified: 2020/10/25 13:51 by 127.0.0.1

Donate Powered by PHP Valid HTML5 Valid CSS Driven by DokuWiki