通过发送 JSON 来执行命令?了解 Ruby 项目中不安全的反序列化漏洞如何运作

本文主要是介绍通过发送 JSON 来执行命令?了解 Ruby 项目中不安全的反序列化漏洞如何运作,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

攻击者是否可以通过发送 JSON 在远程服务器上执行任意命令?是的,如果正在运行的代码包含不安全的反序列化漏洞。但这怎么可能呢?

在这篇博文中,我们将描述不安全反序列化漏洞的工作原理以及如何在 Ruby 项目中检测它们。这篇博文中的所有示例都是使用 Ruby 的 Oj JSON 序列化库制作的,但这并不意味着它们仅限于此库。在这篇博文的最后,我们将链接到一个存储库,其中包含适用于 Oj (JSON)、Ox (XML)、Psych (YAML) 和 Marshal (自定义二进制格式) 的有效示例漏洞,并向您展示 CodeQL 如何检测此类漏洞。了解不安全反序列化的工作原理可以帮助您完全避免此类错误,而不是专注于避免某些方法。

内容

  • 一步步:为 Oj 构建检测工具链
  • 将检测工具扩展为成熟的通用远程代码执行链
  • 在源代码可用时检测不安全的反序列化

一步步:为 Oj 构建检测工具链

许多人都知道如何利用反序列化漏洞。但它究竟是如何运作的呢?(这既是魔法,也是汗水和泪水。)在本节中,我们将展示如何为 Oj(一个基于 Ruby 的 JSON 反序列化库)构建一个调用外部 URL 的不安全反序列化检测小工具。此检测小工具基于 William Bowling(又名vakzz)为 Marshal 和 Ruby 3.0.3 开发的通用反序列化小工具,适用于 Oj 和 Ruby 3.3。

1. 从课程开始

大多数情况下,不安全的反序列化漏洞都与反序列化库支持多态性的能力有关,这意味着能够实例化序列化数据中指定的任意类或类状结构。然后,攻击者将这些类链接在一起,在被利用的系统上执行代码。所有使用的类通常都必须由被利用的项目访问。在这种情况下,用于特定目的(例如执行命令或代码)的类称为小工具。而通过将这些类组合起来成为更大漏洞的一部分(例如,通过嵌套它们),我们得到了所谓的小工具链。序列化和反序列化任意构造的能力长期以来被视为一项强大的功能,它最初并非用于代码执行。2015 年,随着 FoxGlove Security 发布了一篇关于广泛存在的 Java 反序列化漏洞的博客文章,公众对此功能的看法发生了变化。2017 年,BlackHat 上展示了针对基于 Java 和 .NET 的 JSON 库的不安全反序列化攻击,标题为“ 13 号星期五:JSON 攻击”。

当使用名为 Oj 的(非默认)Ruby 库反序列化 JSON 时,项目很容易受到攻击,只需构造如下内容即可:

data = Oj.load(untrusted_json)

Oj 库默认支持 JSON 中指定的类的实例化。可以通过指定附加参数或使用来禁用此行为Oj.safe_load

正如介绍中所提到的,不安全的反序列化漏洞不仅限于 JSON;它们可能发生在从用户控制的数据反序列化的任意类或类似类的结构的任何地方。

要实例化一个名称为 且具有内容为MyClass的字段的类,必须将以下 JSON 传递给易受攻击的 Oj 接收器。membervalue

{"^o": "MyClass","member": "value"
}

2. 接下来是映射(哈希)、列表、getter、setter、构造函数等

虽然类的实例化是反序列化不安全漏洞最常见的特征,但接下来的构造块因语言而异。虽然在 Java 和类似语言中,反序列化不安全漏洞有时会使用构造函数、setter 和 getter 来初始触发代码执行,但对于 Ruby 反序列化漏洞,我们不能依赖它们。Vakzz的博客文章是关于 Ruby 二进制 Marshal 序列化的利用,它依赖于一种所谓的魔术方法(在序列化对象重建中调用的方法)_load(类似于 Java 的readObject)来触发代码执行。但是,Oj 不会调用这个魔术方法,因此为了触发我们的小工具链的执行,我们不能依赖这个方法,而必须找到其他方法。

首先回答这个问题:我们可以使用什么来触发 Oj 中的代码执行?

方法hash(code)

Oj 并不是我们依赖该hash方法作为小工具链启动的唯一反序列化库。hash当反序列化库将键值对添加到哈希图(在 Ruby 中简称为哈希本身)时,通常会在键对象上调用该方法。

下表展示了 Ruby 中流行的序列化库的启动方法:

图书馆输入数据课堂内开球方法
元帅(红宝石)二进制_load
橙汁JSONhash(类需要作为键放入哈希(映射)中)
XMLhash(类需要作为键放入哈希(映射)中)
心理学(红宝石)YAMLhash(类需要作为键放入哈希(映射)中)
init_with
JSON (Ruby)JSONjson_create([参见最后关于 json_create 的注释](#table-vulnerable-sinks))

让我们创建一个小的概念证明来演示如何使用该hash方法启动我们的小工具链。

我们假设我们有一个类,例如下面的类,在目标 Ruby 项目中可用(提示:在实际项目中不会有这样的小工具):

class SimpleClassdef initialize(cmd)@cmd = cmdenddef hashsystem(@cmd)end
end

调用“hash”将使用“system”执行“@cmd”成员变量中的命令。请注意,在 Oj 反序列化过程中,不会执行构造函数。在这里,我们使用它自己创建一个快速示例有效负载并转储生成的 JSON:

require 'oj'simple = SimpleClass.new("open -a calculator") # command for macOSjson_payload = Oj.dump(simple)
puts json_payload
注意:虽然直接序​​列化单个小工具可能有意义,但序列化甚至只是调试整个小工具链通常很危险,因为它可能会在序列化过程中触发链的执行(这不会给你预期的结果,但你会“利用”你自己的系统)。

有效载荷 JSON 如下所示:

{"^o": "SimpleClass","cmd": "open -a calculator"
}

如果我们现在加载这个 JSON,什么Oj.load也不会发生。为什么?因为实际上没有人调用 hash 方法。</

这篇关于通过发送 JSON 来执行命令?了解 Ruby 项目中不安全的反序列化漏洞如何运作的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1104528

相关文章

IDEA如何将String类型转json格式

《IDEA如何将String类型转json格式》在Java中,字符串字面量中的转义字符会被自动转换,但通过网络获取的字符串可能不会自动转换,为了解决IDEA无法识别JSON字符串的问题,可以在本地对字... 目录问题描述问题原因解决方案总结问题描述最近做项目需要使用Ai生成json,可生成String类型

Python手搓邮件发送客户端

《Python手搓邮件发送客户端》这篇文章主要为大家详细介绍了如何使用Python手搓邮件发送客户端,支持发送邮件,附件,定时发送以及个性化邮件正文,感兴趣的可以了解下... 目录1. 简介2.主要功能2.1.邮件发送功能2.2.个性签名功能2.3.定时发送功能2. 4.附件管理2.5.配置加载功能2.6.

Python 中 requests 与 aiohttp 在实际项目中的选择策略详解

《Python中requests与aiohttp在实际项目中的选择策略详解》本文主要介绍了Python爬虫开发中常用的两个库requests和aiohttp的使用方法及其区别,通过实际项目案... 目录一、requests 库二、aiohttp 库三、requests 和 aiohttp 的比较四、requ

SpringBoot项目启动后自动加载系统配置的多种实现方式

《SpringBoot项目启动后自动加载系统配置的多种实现方式》:本文主要介绍SpringBoot项目启动后自动加载系统配置的多种实现方式,并通过代码示例讲解的非常详细,对大家的学习或工作有一定的... 目录1. 使用 CommandLineRunner实现方式:2. 使用 ApplicationRunne

解决Cron定时任务中Pytest脚本无法发送邮件的问题

《解决Cron定时任务中Pytest脚本无法发送邮件的问题》文章探讨解决在Cron定时任务中运行Pytest脚本时邮件发送失败的问题,先优化环境变量,再检查Pytest邮件配置,接着配置文件确保SMT... 目录引言1. 环境变量优化:确保Cron任务可以正确执行解决方案:1.1. 创建一个脚本1.2. 修

Python中json文件和jsonl文件的区别小结

《Python中json文件和jsonl文件的区别小结》本文主要介绍了JSON和JSONL两种文件格式的区别,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下... 众所周知,jsON 文件是使用php JSON(JavaScripythonpt Object No

使用IntelliJ IDEA创建简单的Java Web项目完整步骤

《使用IntelliJIDEA创建简单的JavaWeb项目完整步骤》:本文主要介绍如何使用IntelliJIDEA创建一个简单的JavaWeb项目,实现登录、注册和查看用户列表功能,使用Se... 目录前置准备项目功能实现步骤1. 创建项目2. 配置 Tomcat3. 项目文件结构4. 创建数据库和表5.

Python项目打包部署到服务器的实现

《Python项目打包部署到服务器的实现》本文主要介绍了PyCharm和Ubuntu服务器部署Python项目,包括打包、上传、安装和设置自启动服务的步骤,具有一定的参考价值,感兴趣的可以了解一下... 目录一、准备工作二、项目打包三、部署到服务器四、设置服务自启动一、准备工作开发环境:本文以PyChar

多模块的springboot项目发布指定模块的脚本方式

《多模块的springboot项目发布指定模块的脚本方式》该文章主要介绍了如何在多模块的SpringBoot项目中发布指定模块的脚本,作者原先的脚本会清理并编译所有模块,导致发布时间过长,通过简化脚本... 目录多模块的springboot项目发布指定模块的脚本1、不计成本地全部发布2、指定模块发布总结多模

SpringBoot项目删除Bean或者不加载Bean的问题解决

《SpringBoot项目删除Bean或者不加载Bean的问题解决》文章介绍了在SpringBoot项目中如何使用@ComponentScan注解和自定义过滤器实现不加载某些Bean的方法,本文通过实... 使用@ComponentScan注解中的@ComponentScan.Filter标记不加载。@C