开发安全之:Cross-Site Scripting (XSS) 漏洞

news/2024/2/23 13:54:43/文章来源:https://blog.csdn.net/irizhao/article/details/135626953

近期,我会结合研发云陆续发布开发安全相关的文章,欢迎大家关注!

Overview

echo json_encode($arr):向一个 Web 浏览器发送了未验证的数据,从而导致该浏览器执行恶意代码。

Details

Cross-Site Scripting (XSS) 漏洞在以下情况下发生:

1. 数据通过一个不可信赖的数据源进入 Web 应用程序。对于 Persistent(也称为 Stored)XSS,不可信赖的数据源通常为数据库或其他后端数据存储,而对于 Reflected XSS,该数据源通常为 Web 请求。

2.未经验证但包含在动态内容中的数据将传送给 Web 用户。 在这种情况下,数据通过 builtin_echo() 传送。 传送到 Web 浏览器的恶意内容通常采用 JavaScript 片段的形式,但也可能会包含一些 HTML、Flash 或者其他任意一种可以被浏览器执行的代码。

基于 XSS 的攻击手段花样百出,几乎是无穷无尽的,但通常它们都会包含传输给攻击者的私有数据(如 Cookie 或者其他会话信息)。在攻击者的控制下,指引受害者进入恶意的网络内容;或者利用易受攻击的站点,对用户的机器进行其他恶意操作。

例 1:下面的 PHP 代码片段可根据一个给定的雇员 ID 查询数据库,并显式出相应的雇员姓名。 <?php

$con = mysql_connect($server,$user,$password);

$result = mysql_query("select * from emp where id="+eid);

$row = mysql_fetch_array($result) ;

echo 'Employee name: ', mysql_result($row,0,'name');

?>

如果对 name 的值处理得当,该代码就能正常地执行各种功能;如若处理不当,就会对代码的盗取行为无能为力。这段代码暴露出的危险较小,因为 name 的值是从数据库中读取的,而且显然这些内容是由应用程序管理的。

然而,如果 name 的值来自用户提供的数据,数据库就会成为恶意内容传播的通道。如果不对数据库中存储的所有数据进行恰当的输入验证,那么攻击者就可以在用户的 Web 浏览器中执行恶意命令。这种类型的漏洞利用称为 Persistent XSS(或 Stored XSS),它极其隐蔽,因为数据存储导致的间接行为会增大辨别威胁的难度,并使多个用户受此攻击影响的可能性提高。XSS 盗取会从访问提供留言簿 (guestbook) 的网站开始。攻击者会在这些留言簿的条目中嵌入 JavaScript,接下来所有访问该留言簿页面的访问者都会执行这些恶意代码。

例 2:下面的 PHP 代码片段可从一个 HTTP 请求中读取雇员 ID eid,并将其显示给用户。

<?php $eid = $_GET['eid'];

?> ... <?php echo "Employee ID: $eid"; ?>

如Example 1 中所示,如果 eid 只包含标准的字母数字文本,此代码将会正确运行。如果 eid 中的某个值包含元字符或源代码,则 Web 浏览器就会在显示 HTTP 响应时执行该代码。 起初,这个例子似乎是不会轻易遭受攻击的。毕竟,有谁会输入导致恶意代码在自己电脑上运行的 URL 呢?真正的危险在于攻击者会创建恶意的 URL,然后采用电子邮件或社交工程的欺骗手段诱使受害者访问此 URL 的链接。当受害者单击这个链接时,他们不知不觉地通过易受攻击的网络应用程序,将恶意内容带到了自己的电脑中。这种对易受攻击的 Web 应用程序进行盗取的机制通常被称为反射式 XSS。 正如例子中所显示的,XSS 漏洞是由于 HTTP 响应中包含了未经验证的数据代码而引起的。

受害者遭受 XSS 攻击的途径有三种:

- 如Example 1 中所示,应用程序将危险数据存储在数据库或其他可信赖的数据存储中。这些危险数据随后会被读回到应用程序中,并包含在动态内容中。在以下情况下会发生 Persistent XSS 漏洞利用:攻击者将危险内容注入到数据存储中,而这些危险内容随后会被读取并包含在动态内容中。从攻击者的角度看,注入恶意内容的最佳位置莫过于显示给许多用户或显示给特定相关用户的区域。这些相关用户通常在应用程序中具备较高的特权,或者可以与敏感数据交互,这些数据对攻击者来说具有利用价值。如果某一个用户执行了恶意内容,攻击者就有可能以该用户的名义执行某些需要特权的操作,或者获得该用户个人敏感数据的访问权。

- 如Example 2 中所示,系统从 HTTP 请求中直接读取数据,并在 HTTP 响应中返回数据。当攻击者诱使用户为易受攻击的 Web 应用程序提供危险内容,而这些危险内容随后会反馈给用户并在 Web 浏览器中执行时,就会发生 Reflected XSS 漏洞利用。发送恶意内容最常用的方法是,将恶意内容作为一个参数包含在公开发布或通过电子邮件直接发送给受害者的 URL 中。以这种手段构造的 URL 已成为多种网络钓鱼阴谋的核心,攻击者会借此诱骗受害者访问指向易受攻击站点的 URL。该站点将攻击者的内容反馈给受害者后,便会执行这些内容,接下来会将用户计算机中的各种私密信息(比如可能包含会话信息的 Cookie)传输给攻击者,或者执行其他恶意活动。 — 应用程序之外的数据源将危险数据储存在一个数据库或其他数据存储器中,随后这些危险数据被当作可信赖的数据回写到应用程序中,并储存在动态内容中。

Recommendations

防止 XSS 漏洞的解决方法是确保在适当位置进行验证,并设置相关属性以防止漏洞。 由于 XSS 漏洞在应用程序的输出中包含恶意数据时出现,因此,合乎逻辑的方法是在数据流出应用程序的前一刻对其进行验证。然而,由于 Web 应用程序常常会包含复杂而难以理解的代码,用以生成动态内容,因此,这一方法容易产生遗漏错误(遗漏验证)。

降低这一风险的有效途径是对 XSS 也执行输入验证。 由于 Web 应用程序必须验证所有输入信息以避免其他漏洞(如 SQL Injection),因此,一种相对简单的解决方法是,加强应用程序的现有输入验证机制,将 XSS 检测包括其中。尽管有一定的价值,但 XSS 输入验证并不能取代严格的输出验证。应用程序可能通过共享的数据存储器或其他可信赖的数据源接受输入,而该数据存储器所接受的输入源可能并未执行适当的输入验证。因此,应用程序不能间接地依赖于该数据或其他任意数据的安全性。这就意味着,避免 XSS 漏洞的最佳方法是验证所有进入应用程序以及由应用程序传送至用户端的数据。

针对 XSS 漏洞进行验证最安全的方式是,创建一份安全字符允许列表,允许其中的字符出现在 HTTP 内容中,并且只接受完全由这些经认可的字符组成的输入。例如,有效的用户名可能仅包含字母数字字符,电话号码可能仅包含 0-9 的数字。然而,这种解决方法在 Web 应用程序中通常是行不通的,因为许多字符对浏览器来说都具有特殊的含义,编码时这些字符必须被视为合法输入,例如,一个 Web 设计电子公告栏就必须接受其用户提供的 HTML 片段。 更灵活的方法是采用拒绝列表,但其安全性较差,这种方法在使用输入之前就有选择地拒绝或转义了潜在的危险字符。为了创建这样一个列表,首先需要了解对于 Web 浏览器具有特殊含义的字符集。

虽然 HTML 标准定义了哪些字符具有特殊含义,许多 Web 浏览器仍会设法更正 HTML 中的常见错误,并可能在特定的上下文中认为其他字符具有特殊含义。这就是为何我们不鼓励使用拒绝列表作为阻止 XSS 的方法。卡耐基梅隆大学 (Carnegie Mellon University) 软件工程学院 (Software Engineering Institute) 下属的 CERT(R) (CERT(R) Coordination Center) 合作中心提供了有关各种上下文中认定的特殊字符的具体信息 [1]: 在有关块级别元素的内容中(位于一段文本的中间): - "<" 是一个特殊字符,因为它可以引入一个标签。

- "&" 是一个特殊字符,因为它可以引入一个字符实体。 - ">" 是一个特殊字符,之所以某些浏览器将其认定为特殊字符,是基于一种假设,即该页的作者本想在前面添加一个 "<",却错误地将其遗漏了。

下面的这些原则适用于属性值:

- 对于外加双引号的属性值,双引号是特殊字符,因为它们标记了该属性值的结束。

- 对于外加单引号的属性值,单引号是特殊字符,因为它们标记了该属性值的结束。

- 对于不带任何引号的属性值,空格字符(如空格符和制表符)是特殊字符。

- "&" 与某些特定变量一起使用时是特殊字符,因为它引入了一个字符实体。 例如,在 URL 中,搜索引擎可能会在结果页面内提供一个链接,用户可以点击该链接来重新运行搜索。可以将这一方法运用于编写 URL 中的搜索查询语句,这将引入更多特殊字符:

- 空格符、制表符和换行符是特殊字符,因为它们标记了 URL 的结束。 - "&" 是特殊字符,因为它可引入一个字符实体或分隔 CGI 参数。

- 非 ASCII 字符(即 ISO-8859-1 编码表中所有大于 127 的字符)不允许出现在 URL 中,因此这些字符在此环境下被视为特殊字符。

- 在服务器端对在 HTTP 转义序列中编码的参数进行解码时,必须过滤掉输入中的 "%" 符号。例如,当输入中出现“%68%65%6C%6C%6F”时,只有从输入的内容中过滤掉“%”,上述字符串才能在网页上显示为“hello”。 在 <SCRIPT> </SCRIPT> 的正文内:

- 如果可以将文本直接插入到已有的脚本标签中,则必须过滤掉分号、圆括号、花括号和换行符。 服务器端脚本:

- 如果服务器端脚本会将输入中的感叹号 (!) 转换成输出中的双引号 ("),则可能需要对此进行更多过滤。 其他可能出现的情况:

- 如果攻击者以 UTF-7 格式提交了请求,则特殊字符“<”可能会显示为“+ADw-”,并可能会绕过过滤。如果输出包含在没有确切指定编码格式的网页中,某些浏览器就会设法根据内容自动识别编码(此处采用 UTF-7 格式)。

在应用程序中确定针对 XSS 攻击执行验证的正确要点,以及验证过程中要考虑的特殊字符之后,下一个难点就是确定验证过程中处理各种特殊字符的方式。如果应用程序认定某些特殊字符为无效输入,那么您可以拒绝任何带有这些无效特殊字符的输入。第二种选择就是采用过滤手段来删除这些特殊字符。然而,过滤的负面作用在于,过滤内容的显示将发生改变。在需要完整显示输入内容的情况下,过滤的这种负面作用可能是无法接受的。 如果必须接受带有特殊字符的输入,并将其准确地显示出来,验证机制一定要对所有特殊字符进行编码,以便删除其具有的含义。

官方的 HTML 规范 [2] 提供了特殊字符对应的 ISO 8859-1 编码值的完整列表。 许多应用程序服务器都试图避免应用程序出现 Cross-Site Scripting 漏洞,具体做法是为负责设置特定 HTTP 响应内容的函数提供各种实现方式,以检验是否存在进行 Cross-Site Scripting 攻击必需的字符。不要依赖运行应用程序的服务器,以此确保该应用程序的安全。

对于任何已开发的应用程序,并不能保证在其生命周期中它会在哪些应用程序服务器中运行。由于标准和已知盗取方式的演变,我们不能保证应用程序服务器将继续保持同步。
————————————————
版权声明:本文为CSDN博主「irizhao」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/irizhao/article/details/135644701

防御
标签过滤
事件过滤
敏感字符过滤
设置httponly防止Cookie被获取
内容安全策略(CSP)
在将不可信数据插入到HTML标签之间时,对这些数据进行HTML Entity编码
在将不可信数据插入到HTML属性里时,对这些数据进行HTML属性编码
在将不可信数据插入到SCRIPT里时,对这些数据进行SCRIPT编码
在将不可信数据插入到Style属性里时,对这些数据进行CSS编码

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.luyixian.cn/news_show_926036.aspx

如若内容造成侵权/违法违规/事实不符,请联系dt猫网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Angular系列教程之单向绑定与双向绑定

文章目录 介绍单向绑定双向绑定在自定义组件中实现双向绑定属性总结 介绍 在Angular开发中&#xff0c;数据的绑定是非常重要的概念。它允许我们将应用程序的数据与用户界面进行交互&#xff0c;实现数据的动态更新。在本文中&#xff0c;我们将探讨Angular中的两种数据绑定方…

jmeter-线程数设置为1,循环10次没问题,循环100次出现异常

一、多次尝试&#xff0c;发现出现异常的接口大致相同。 解决办法&#xff1a;在第一个出现异常的接口下添加超时时间&#xff0c;固定定时器&#xff1a;2000ms&#xff0c;再次运行就没问题了。 二、压力机自身存在的问题 1&#xff09;在网络编程中&#xff0c;特别是在短…

计算机三级(网络技术)——应用题

第一题 61.输出端口S0 &#xff08;直接连接&#xff09; RG的输出端口S0与RE的S1接口直接相连构成一个互联网段 对172.0.147.194和172.0.147.193 进行聚合 前三段相同&#xff0c;将第四段分别转换成二进制 11000001 11000010 前6位相同&#xff0c;加上前面三段 共30…

Debian(Linux)局域网共享文件-NFS

NFS (Network File system) 是一种客户端-服务器文件系统协议&#xff0c;允许多个系统或用户访问相同的共享文件夹或文件。最新版本是 NFS-V4&#xff0c;共享文件就像存储在本地一样。它提供了中央管理&#xff0c;可以使用防火墙和 Kerberos 身份验证进行保护。 本文将指导…

基于grpc-java开发的普通工程在k8s内部署多实例,如何实现客户端流量的负载均衡

文章目录 1. 前言2.实现方案要点3.具体实现步骤3.1 编写一个grpc服务端程序(详细实现步骤在此忽略&#xff0c;网上很多例子)3.2 编写grpc客户端程序&#xff0c;注意指定负载均衡策略和dns:///这个URI前缀&#xff0c;如下图所示3.3 在k8s中部署服务端和客户端3.3.1 服务端部署…

Spark---累加器和广播变量

文章目录 1.累加器实现原理2.自定义累加器3.广播变量 1.累加器实现原理 累加器用来把 Executor 端变量信息聚合到 Driver 端。在 Driver 程序中定义的变量&#xff0c;在Executor 端的每个 Task 都会得到这个变量的一份新的副本&#xff0c;每个 task 更新这些副本的值后&…

5个99%的人可能不知道的实用程序库!

前言 作为一名前端开发者,这些 JavaScript 库极大地提高了我的工作效率,如格式化日期、处理 URL 参数和调试移动网页。朋友们,我想和你们分享这些库。 1. 使用 “Day.js” 来格式化日期和时间 链接 作为开发者,我已经厌倦了在 JavaScript 中操作日期和时间,因为它太麻烦了。…

WDS服务企业安装Win10

计算机 操作系统 系统服务 软件安装 WDS Windows Sserver2019STD AD&#xff0c;DNS,DHCP,WDS WADK10.0 MDT2013 Update 1 Preview 1.基础配置 域控配置静态IP 域控制器&#xff1a;需要安装AD域服务&#xff0c;DHCP和DNS三个角色 默认配置 默认配置 安装完成我们将此…

微信小程序快速入门02(含案例)

&#x1f3e1;浩泽学编程&#xff1a;个人主页 &#x1f525; 推荐专栏&#xff1a;《深入浅出SpringBoot》《java项目分享》 《RabbitMQ》《Spring》《SpringMVC》 &#x1f6f8;学无止境&#xff0c;不骄不躁&#xff0c;知行合一 文章目录 前言一、页面导航1.…

HarmonyOS自学-Day5(使用List、Stack、RelativeContainer相关组件实现的小案例)

目录 文章声明⭐⭐⭐让我们开始今天的学习吧&#xff01;小案例 文章声明⭐⭐⭐ 该文章为我&#xff08;有编程语言基础&#xff0c;非编程小白&#xff09;的 HarmonyOS自学笔记&#xff0c;此类文章笔记我会默认大家都学过前端相关的知识&#xff0c;并常常以实现相关小案例…

2024“华数杯”(A题)|放射性废水扩散|国际大学生数学建模竞赛建模解析,小鹿学长带队指引全代码文章与思路

我是小鹿学长&#xff0c;就读于上海交通大学&#xff0c;截至目前已经帮200人完成了建模与思路的构建的处理了&#xff5e; 完整内容可以在文章末尾领取&#xff01; 这回带大家体验一下2024“华数杯”国际大学生数学建模竞赛呀&#xff01; 此题涉及到放射性废水从日本排放…

mac快捷创建文件的方法

mac快捷创建文件的方法 在macbook的使用中&#xff0c;当我们在桌面或访达等地方使用右键时&#xff0c;可以看到新建文件夹的选项&#xff0c;却怎么也找不到创建文件的选项。这种情况有时候会带来不便。这篇文章给大家带来一个非常简单解决这个问题。 下载 在App Store中搜索…

使用numpy处理图片——90度旋转

大纲 左旋转90度向右旋转90旋转180度 代码地址 在《使用numpy处理图片——镜像翻转和旋转》一文中&#xff0c;我们介绍了如何将图片旋转的方法。本文将使用更简单的方法旋转图片90度。 左旋转90度 import numpy as np import PIL.Image as Imagedata np.array(Image.open(t…

5.3 Verilog 带参数例化

5.3 Verilog 带参数例化 分类 Verilog 教程 关键词&#xff1a; defparam&#xff0c;参数&#xff0c;例化&#xff0c;ram 当一个模块被另一个模块引用例化时&#xff0c;高层模块可以对低层模块的参数值进行改写。这样就允许在编译时将不同的参数传递给多个相同名字的模块…

获取本地IP网卡信息

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 前言一、获取本地IP&#xff0c;以及全部网卡信息总结 前言 一、获取本地IP&#xff0c;以及全部网卡信息 const os require(node:os) function getIPAdress(){/…

初识Ubuntu

其实还是linux操作系统 命令都一样 但是在学习初级阶段&#xff0c;我还是将其分开有便于我的学习和稳固。 cat 查看文件 命令 Ubuntu工作中经常是用普通用户&#xff0c;在需要时才进行登录管理员用户 sudn -i 切换成管理用户 我们远程连接时 如果出现 hostname -I没有出现…

Spring Boot 中批量执行 SQL 脚本的实践

在Spring Boot应用中&#xff0c;有时候我们需要批量执行存储在数据库中的 SQL 脚本。本文将介绍一个实际的案例&#xff0c;演示如何通过 Spring Boot、MyBatis 和数据库来实现这一目标。 0、数据库层 CREATE TABLE batchUpdate (id INT AUTO_INCREMENT PRIMARY KEY,update_…

Shopee买家通系统:领先科技助力卖家全自动化营销

在虾皮卖家和服务商的竞争激烈的市场环境下&#xff0c;不断追求创新和效率提升是至关重要的。近期推出的Shopee买家通系统正是基于最新的防指纹防关联技术&#xff0c;以其独特的能力完全模拟真人运行&#xff0c;实现全自动化操作&#xff0c;为卖家们提供了一款卓越的营销工…

跟着cherno手搓游戏引擎【7】Input轮询

在引擎程序中任何时间&#xff0c;任何位置都能知道按键是否按下、鼠标的位置等等信息。 与事件系统的区别&#xff1a;事件系统是在按下时调用并传递按键状态&#xff1b;轮询是每时每刻都能获取按键状态 创建基类&#xff1a; YOTO/Input.h&#xff1a;名如其意 #pragma …

强化学习应用(一):基于Q-learning的无人机物流路径规划研究(提供Python代码)

一、Q-learning简介 Q-learning是一种强化学习算法&#xff0c;用于解决基于马尔可夫决策过程&#xff08;MDP&#xff09;的问题。它通过学习一个价值函数来指导智能体在环境中做出决策&#xff0c;以最大化累积奖励。 Q-learning算法的核心思想是通过不断更新一个称为Q值的…