Loading [MathJax]/jax/output/CommonHTML/config.js
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >CA2330:在反序列化时确保 JsonSerializer 具有安全配置

CA2330:在反序列化时确保 JsonSerializer 具有安全配置

作者头像
呆呆
发布于 2022-02-20 11:36:50
发布于 2022-02-20 11:36:50
7010
举报
文章被收录于专栏:centosDaicentosDai

规则 ID

CA2330

类别

安全性

修复是中断修复还是非中断修复

非中断

原因

如果传递到反序列化方法或初始化为字段或属性的 Newtonsoft.Json.JsonSerializer 实例满足以下两个条件,则会触发此规则:

TypeNameHandling 属性是 None 以外的值。

SerializationBinder 属性为 NULL。

此规则类似于 CA2329,但无法通过分析明确确定序列化程序的配置是否不安全。

默认情况下,此规则会分析整个代码库,但这是可配置的。

规则说明

反序列化不受信任的数据时,不安全的反序列化程序易受攻击。 攻击者可能会修改序列化数据,使其包含非预期类型,进而注入具有不良副作用的对象。 例如,针对不安全反序列化程序的攻击可以在基础操作系统上执行命令,通过网络进行通信,或删除文件。

此规则会查找 Newtonsoft.Json.JsonSerializer 实例,这些实例可能被配置为对输入中指定的类型执行反序列化,且可能未配置为限制带有 Newtonsoft.Json.Serialization.ISerializationBinder 的反序列化类型。 如果要禁止对完全在输入中指定的类型进行反序列化,请禁用规则 CA2327、CA2328、CA2329 和 CA2330,并启用规则 CA2326。

如何解决冲突

如果可能,请使用 TypeNameHandling 的 None 值。

使序列化的数据免被篡改。 序列化后,对序列化的数据进行加密签名。 在反序列化之前,验证加密签名。 保护加密密钥不被泄露,并针对密钥轮换进行设计。

限制反序列化的类型。 实现自定义 Newtonsoft.Json.Serialization.ISerializationBinder。 在对 Json.NET 执行反序列化前,请确保在 Newtonsoft.Json.JsonSerializer.SerializationBinder 属性中指定自定义 ISerializationBinder。 在已重写的 Newtonsoft.Json.Serialization.ISerializationBinder.BindToType 方法中,如果类型是非预期类型,会返回 null 或引发异常以停止反序列化。

何时禁止显示警告

在以下情况下,禁止显示此规则的警告是安全的:

已知输入为受信任输入。 考虑应用程序的信任边界和数据流可能会随时间发生变化。

你已采取如何解决冲突的某项预防措施。

你知道,当 TypeNameHandling 属性是 None 以外的值时,将始终设置 Newtonsoft.Json.JsonSerializer.SerializationBinder 属性。

配置代码以进行分析

使用下面的选项来配置代码库的哪些部分要运行此规则。

排除特定符号

排除特定类型及其派生类型

你可以仅为此规则、为所有规则或为此类别(安全性)中的所有规则配置这些选项。 有关详细信息,请参阅代码质量规则配置选项。

排除特定符号

可以从分析中排除特定符号,如类型和方法。 例如,若要指定规则不应针对名为 MyType 的类型中的任何代码运行,请将以下键值对添加到项目中的 .editorconfig 文件:

dotnet_code_quality.CAXXXX.excluded_symbol_names = MyType

选项值中允许的符号名称格式(用 | 分隔):

仅符号名称(包括具有相应名称的所有符号,不考虑包含的类型或命名空间)。

完全限定的名称,使用符号的文档 ID 格式。 每个符号名称都需要带有一个符号类型前缀,例如表示方法的 M:、表示类型的 T:,以及表示命名空间的 N:。

.ctor 表示构造函数,.cctor 表示静态构造函数。

示例:

选项值

总结

dotnet_code_quality.CAXXXX.excluded_symbol_names = MyType

匹配名为 MyType 的所有符号。

dotnet_code_quality.CAXXXX.excluded_symbol_names = MyType1|MyType2

匹配名为 MyType1 或 MyType2 的所有符号。

dotnet_code_quality.CAXXXX.excluded_symbol_names = M:NS.MyType.MyMethod(ParamType)

匹配带有指定的完全限定签名的特定方法 MyMethod。

dotnet_code_quality.CAXXXX.excluded_symbol_names = M:NS1.MyType1.MyMethod1(ParamType)|M:NS2.MyType2.MyMethod2(ParamType)

匹配带有各自的完全限定签名的特定方法 MyMethod1 和 MyMethod2。

排除特定类型及其派生类型

可以从分析中排除特定类型及其派生类型。 例如,若要指定规则不应针对名为 MyType 的类型及其派生类型中的任何代码运行,请将以下键值对添加到项目中的 .editorconfig 文件:

dotnet_code_quality.CAXXXX.excluded_type_names_with_derived_types = MyType

选项值中允许的符号名称格式(用 | 分隔):

仅类型名称(包括具有相应名称的所有类型,不考虑包含的类型或命名空间)。

完全限定的名称,使用符号的文档 ID 格式,前缀为 T:(可选)。

示例:

选项值

总结

dotnet_code_quality.CAXXXX.excluded_type_names_with_derived_types = MyType

匹配名为 MyType 的所有类型及其所有派生类型。

dotnet_code_quality.CAXXXX.excluded_type_names_with_derived_types = MyType1|MyType2

匹配名为 MyType1 或 MyType2 的所有类型及其所有派生类型。

dotnet_code_quality.CAXXXX.excluded_type_names_with_derived_types = M:NS.MyType

匹配带有给定的完全限定名称的特定类型 MyType 及其所有派生类型。

dotnet_code_quality.CAXXXX.excluded_type_names_with_derived_types = M:NS1.MyType1|M:NS2.MyType2

匹配带有各自的完全限定名称的特定类型 MyType1 和 MyType2 及其所有派生类型。

伪代码示例

冲突

using System;

using Newtonsoft.Json;

using Newtonsoft.Json.Serialization;

public class BookRecordSerializationBinder : ISerializationBinder

{

// To maintain backwards compatibility with serialized data before using an ISerializationBinder.

private static readonly DefaultSerializationBinder Binder = new DefaultSerializationBinder();

public void BindToName(Type serializedType, out string assemblyName, out string typeName)

{

Binder.BindToName(serializedType, out assemblyName, out typeName);

}

public Type BindToType(string assemblyName, string typeName)

{

// If the type isn't expected, then stop deserialization.

if (typeName != "BookRecord" && typeName != "AisleLocation" && typeName != "WarehouseLocation")

{

return null;

}

return Binder.BindToType(assemblyName, typeName);

}

}

public class BookRecord

{

public string Title { get; set; }

public object Location { get; set; }

}

public abstract class Location

{

public string StoreId { get; set; }

}

public class AisleLocation : Location

{

public char Aisle { get; set; }

public byte Shelf { get; set; }

}

public class WarehouseLocation : Location

{

public string Bay { get; set; }

public byte Shelf { get; set; }

}

public static class Binders

{

public static ISerializationBinder BookRecord = new BookRecordSerializationBinder();

}

public class ExampleClass

{

public BookRecord DeserializeBookRecord(JsonReader reader)

{

JsonSerializer jsonSerializer = new JsonSerializer();

jsonSerializer.TypeNameHandling = TypeNameHandling.Auto;

jsonSerializer.SerializationBinder = Binders.BookRecord;

return jsonSerializer.Deserialize<BookRecord>(reader); // CA2330 -- SerializationBinder might be null

}

}

Imports System

Imports Newtonsoft.Json

Imports Newtonsoft.Json.Serialization

Public Class BookRecordSerializationBinder

Implements ISerializationBinder

' To maintain backwards compatibility with serialized data before using an ISerializationBinder.

Private Shared ReadOnly Property Binder As New DefaultSerializationBinder()

Public Sub BindToName(serializedType As Type, ByRef assemblyName As String, ByRef typeName As String) Implements ISerializationBinder.BindToName

Binder.BindToName(serializedType, assemblyName, typeName)

End Sub

Public Function BindToType(assemblyName As String, typeName As String) As Type Implements ISerializationBinder.BindToType

' If the type isn't expected, then stop deserialization.

If typeName <> "BookRecord" AndAlso typeName <> "AisleLocation" AndAlso typeName <> "WarehouseLocation" Then

Return Nothing

End If

Return Binder.BindToType(assemblyName, typeName)

End Function

End Class

Public Class BookRecord

Public Property Title As String

Public Property Location As Location

End Class

Public MustInherit Class Location

Public Property StoreId As String

End Class

Public Class AisleLocation

Inherits Location

Public Property Aisle As Char

Public Property Shelf As Byte

End Class

Public Class WarehouseLocation

Inherits Location

Public Property Bay As String

Public Property Shelf As Byte

End Class

Public Class Binders

Public Shared Property BookRecord As ISerializationBinder = New BookRecordSerializationBinder()

End Class

Public Class ExampleClass

Public Function DeserializeBookRecord(reader As JsonReader) As BookRecord

Dim jsonSerializer As JsonSerializer = New JsonSerializer()

jsonSerializer.TypeNameHandling = TypeNameHandling.Auto

jsonSerializer.SerializationBinder = Binders.BookRecord

Return jsonSerializer.Deserialize(Of BookRecord)(reader) ' CA2330 -- SerializationBinder might be null

End Function

End Class

解决方案

using System;

using Newtonsoft.Json;

using Newtonsoft.Json.Serialization;

public class BookRecordSerializationBinder : ISerializationBinder

{

// To maintain backwards compatibility with serialized data before using an ISerializationBinder.

private static readonly DefaultSerializationBinder Binder = new DefaultSerializationBinder();

public void BindToName(Type serializedType, out string assemblyName, out string typeName)

{

Binder.BindToName(serializedType, out assemblyName, out typeName);

}

public Type BindToType(string assemblyName, string typeName)

{

// If the type isn't expected, then stop deserialization.

if (typeName != "BookRecord" && typeName != "AisleLocation" && typeName != "WarehouseLocation")

{

return null;

}

return Binder.BindToType(assemblyName, typeName);

}

}

public class BookRecord

{

public string Title { get; set; }

public object Location { get; set; }

}

public abstract class Location

{

public string StoreId { get; set; }

}

public class AisleLocation : Location

{

public char Aisle { get; set; }

public byte Shelf { get; set; }

}

public class WarehouseLocation : Location

{

public string Bay { get; set; }

public byte Shelf { get; set; }

}

public static class Binders

{

public static ISerializationBinder BookRecord = new BookRecordSerializationBinder();

}

public class ExampleClass

{

public BookRecord DeserializeBookRecord(JsonReader reader)

{

JsonSerializer jsonSerializer = new JsonSerializer();

jsonSerializer.TypeNameHandling = TypeNameHandling.Auto;

// Ensure that SerializationBinder is assigned non-null before deserializing

jsonSerializer.SerializationBinder = Binders.BookRecord ?? throw new Exception("Expected non-null");

return jsonSerializer.Deserialize<BookRecord>(reader);

}

}

Imports System

Imports Newtonsoft.Json

Imports Newtonsoft.Json.Serialization

Public Class BookRecordSerializationBinder

Implements ISerializationBinder

' To maintain backwards compatibility with serialized data before using an ISerializationBinder.

Private Shared ReadOnly Property Binder As New DefaultSerializationBinder()

Public Sub BindToName(serializedType As Type, ByRef assemblyName As String, ByRef typeName As String) Implements ISerializationBinder.BindToName

Binder.BindToName(serializedType, assemblyName, typeName)

End Sub

Public Function BindToType(assemblyName As String, typeName As String) As Type Implements ISerializationBinder.BindToType

' If the type isn't expected, then stop deserialization.

If typeName <> "BookRecord" AndAlso typeName <> "AisleLocation" AndAlso typeName <> "WarehouseLocation" Then

Return Nothing

End If

Return Binder.BindToType(assemblyName, typeName)

End Function

End Class

Public Class BookRecord

Public Property Title As String

Public Property Location As Location

End Class

Public MustInherit Class Location

Public Property StoreId As String

End Class

Public Class AisleLocation

Inherits Location

Public Property Aisle As Char

Public Property Shelf As Byte

End Class

Public Class WarehouseLocation

Inherits Location

Public Property Bay As String

Public Property Shelf As Byte

End Class

Public Class Binders

Public Shared Property BookRecord As ISerializationBinder = New BookRecordSerializationBinder()

End Class

Public Class ExampleClass

Public Function DeserializeBookRecord(reader As JsonReader) As BookRecord

Dim jsonSerializer As JsonSerializer = New JsonSerializer()

jsonSerializer.TypeNameHandling = TypeNameHandling.Auto

' Ensure SerializationBinder is non-null before deserializing

jsonSerializer.SerializationBinder = If(Binders.BookRecord, New Exception("Expected non-null"))

Return jsonSerializer.Deserialize(Of BookRecord)(reader)

End Function

End Class

相关规则

CA2326:请勿使用 None 以外的 TypeNameHandling 值

CA2327:不要使用不安全的 JsonSerializerSettings

CA2328:确保 JsonSerializerSettings 是安全的

CA2329:不要使用不安全的配置反序列化 JsonSerializer

本文系外文翻译,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文系外文翻译,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
CA2329:不要使用不安全的配置反序列化 JsonSerializer
如果传递到反序列化方法或初始化为字段或属性的 Newtonsoft.Json.JsonSerializer 实例满足以下两个条件,则会触发此规则:
呆呆
2022/02/20
9190
CA2327:不要使用不安全的 JsonSerializerSettings
如果 Newtonsoft.Json.JsonSerializerSettings 实例的以下两个条件均为 true,则会触发此规则:
呆呆
2022/02/20
6420
CA2328:确保 JsonSerializerSettings 是安全的
如果 Newtonsoft.Json.JsonSerializerSettings 实例的以下两个条件均可为 true,则会触发此规则:
呆呆
2022/02/20
7150
CA2311:在未先设置 NetDataContractSerializer.Binder 的情况下,请不要反序列化
在未设置 Binder 属性的情况下调用或引用了 System.Runtime.Serialization.NetDataContractSerializer 反序列化方法。
用户4268038
2022/02/20
1.5K0
CA2312:确保在反序列化之前设置 NetDataContractSerializer.Binder
调用或引用了 System.Runtime.Serialization.NetDataContractSerializer 反序列化方法,但 Binder 属性可能为 NULL。
用户4268038
2022/02/26
6140
运行时序列化 5
序列化对象时,格式化器输出类型及其定义的程序集全名。反序列化对象时,格式化器根据这个信息确定要为对象构造并初始化什么类型。但是有时候有必要将对象反序列成和序列化时不同的类型。
小蜜蜂
2019/07/23
5260
CA2321:请勿使用 SimpleTypeResolver 对 JavaScriptSerializer 进行反序列化
使用 System.Web.Script.Serialization.SimpleTypeResolver 初始化后,调用或引用了 System.Web.Script.Serialization.JavaScriptSerializer 反序列化方法。
用户4268038
2022/02/20
1.5K0
CA3007:查看公开重定向漏洞的代码
处理不受信任的输入时,请注意防范开放重定向漏洞。 攻击者可以利用开放重定向漏洞,使用你的网站提供合法 URL 的外观,但将毫不知情的访客重定向到钓鱼网页或其他恶意网页。
呆呆
2022/02/20
1.1K0
CA2310:请勿使用不安全的反序列化程序 NetDataContractSerializer
调用或引用了 System.Runtime.Serialization.NetDataContractSerializer 反序列化方法。
用户4268038
2022/02/20
4300
CA3004:查看信息泄露漏洞的代码
泄漏异常信息可让攻击者深入了解应用程序的内部机制,从而帮助攻击者找到其他漏洞并利用这些漏洞。
呆呆
2022/02/20
7650
CA2302:在调用 BinaryFormatter.Deserialize 之前,确保设置 BinaryFormatter.Binder
调用或引用了 System.Runtime.Serialization.Formatters.Binary.BinaryFormatter 反序列化方法,但 Binder 属性可能为 NULL。
用户4268038
2022/02/26
1.3K0
CA2300:请勿使用不安全的反序列化程序 BinaryFormatte
调用或引用了 System.Runtime.Serialization.Formatters.Binary.BinaryFormatter 反序列化方法。
用户4268038
2022/02/20
6170
Dotnet反序列化——XmlSerializer链
本文很大程度参考了Y4er师傅的文章:https://github.com/Y4er/dotnet-deserialization/blob/main/dotnet-serialize-101.md
ConsT27
2022/03/28
7000
Dotnet反序列化——XmlSerializer链
CA2301:在未先设置 BinaryFormatter.Binder
在未设置 Binder 属性的情况下调用或引用了 System.Runtime.Serialization.Formatters.Binary.BinaryFormatter 反序列化方法。
用户4268038
2022/02/26
7840
代码审计-.NET下的序列化与反序列化(BinaryFormatter)
本文将介绍BinaryFormatter序列化与反序列化漏洞的原理以及实际应用场景中的代码审计。
重生信息安全
2020/10/26
1.7K0
CA3002:查看 XSS 漏洞的代码
在处理来自 Web 请求的不受信任的输入时,请注意防范跨站脚本 (XSS) 攻击。 XSS 攻击会将不受信任的输入注入原始 HTML 输出,使攻击者可以执行恶意脚本或恶意修改网页中的内容。 一个典型的技术是将包含恶意代码的 <script> 元素放入输入中。 有关详细信息,请参阅 OWASP 的 XSS。
呆呆
2022/02/20
8120
Android 反序列化漏洞攻防史话
Java 在历史上出现过许多反序列化的漏洞,但大部分出自 J2EE 的组件。即便是 FastJSON 这种漏洞,似乎也很少看到在 Android 中被实际的触发和利用。本文即为对历史上曾出现过的 Android Java 反序列化漏洞的分析和研究记录。
evilpan
2023/03/27
2.1K0
Android 反序列化漏洞攻防史话
Newtonsoft.Json C# Json序列化和反序列化工具的使用、类型方法大全
Newtonsoft.Json 是.Net平台操作Json的工具,他的介绍就不多说了,笔者最近在弄接口,需要操作Json。
痴者工良
2021/04/26
6.5K0
CA3003:查看文件路径注入漏洞的代码
在处理来自 Web 请求的不受信任的输入时,请谨慎使用用户控制的输入指定文件路径。 攻击者可能能够读取非预期文件,从而导致敏感数据出现信息泄漏。 或者,攻击者可能能够写入非预期文件,从而导致在未经授权的情况下修改敏感数据,或者降低服务器的安全性。 常见的攻击者技术是使用路径遍历访问预期目录之外的文件。
呆呆
2022/02/20
1.3K0
C++ 序列化和反序列化
问题: 在内存里存放的任何数据,它最基础的存储单元也是二进制比特,也就是说,我们应用程序操作的对象,它在内存中也是使用二进制存储的,既然都是二进制,为什么不能直接把内存中,对象对应的二进制数据直接通过网络发送出去,或者保存在文件中呢?为什么还需要序列化和反序列化呢?
全栈程序员站长
2022/07/05
1.9K0
C++ 序列化和反序列化
推荐阅读
相关推荐
CA2329:不要使用不安全的配置反序列化 JsonSerializer
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档