Conseils de sécurité dataSet et DataTable
Cet article s’applique à :
- .NET Framework (toutes les versions)
- .NET Core et versions ultérieures
- .NET 5 et versions ultérieures
Les types DataSet et DataTable sont des composants .NET hérités qui permettent de représenter des jeux de données en tant qu’objets managés. Ces composants ont été introduits dans .NET Framework 1.0 dans le cadre de l’infrastructure de ADO.NET d’origine. Leur objectif était de fournir un affichage managé sur un jeu de données relationnelles, en s’éloignant si la source sous-jacente des données était XML, SQL ou une autre technologie.
Pour plus d’informations sur ADO.NET, y compris les paradigmes d’affichage de données plus modernes, consultez la documentation ADO.NET.
Restrictions par défaut lors de la désérialisation d’un DataSet ou d’un DataTable à partir de XML
Sur toutes les versions prises en charge de .NET Framework, .NET Core et .NET, DataSet
et DataTable
placent les restrictions suivantes sur les types d’objets pouvant être présents dans les données désérialisées. Par défaut, cette liste est limitée à :
- Primitives et équivalents primitifs :
bool
,char
,sbyte
,byte
,short
,ushort
,int
,uint
,long
,ulong
,float
,double
,decimal
,DateTime
,DateTimeOffset
,TimeSpan
,string
,Guid
,SqlBinary
,SqlBoolean
,SqlByte
,SqlBytes
,SqlChars
,SqlDateTime
,SqlDecimal
,SqlDouble
,SqlGuid
,SqlInt16
,SqlInt32
,SqlInt64
,SqlMoney
,SqlSingle
etSqlString
. - Non primitives couramment utilisées :
Type
,Uri
etBigInteger
. - Types System.Drawing couramment utilisés :
Color
,Point
,PointF
,Rectangle
,RectangleF
,Size
etSizeF
. - Types
Enum
. - Tableaux et listes des types ci-dessus.
Si les données XML entrantes contiennent un objet dont le type ne figure pas dans cette liste :
Une exception est levée avec le message et la trace de pile suivants. Message d’erreur : System.InvalidOperationException : Type ’<Type Name>, Version=<n.n.n.n>, Culture=<culture>, PublicKeyToken=<token value>’ n’est pas autorisé ici. Trace de pile : sur System.Data.TypeLimiter.EnsureTypeIsAllowed(Type type, TypeLimiter capturedLimiter) sur System.Data.DataColumn.UpdateColumnType(Type type, StorageType typeCode) à System.Data.DataColumn.set_DataType(Valeur de type)
L’opération de désérialisation échoue.
Lors du chargement du code XML dans une instance DataSet
ou DataTable
, les définitions de colonnes existantes sont également prises en compte. Si la table contient déjà une définition de colonne d’un type personnalisé, ce type est temporairement ajouté à la liste verte pendant la durée de l’opération de désérialisation XML.
Notes
Une fois que vous avez ajouté des colonnes à une instance DataTable
, ReadXml
ne lit pas le schéma à partir du code XML, et si le schéma ne correspond pas aux enregistrements, vous devez donc ajouter toutes les colonnes vous-même pour utiliser cette méthode.
XmlReader xmlReader = GetXmlReader();
// Assume the XML blob contains data for type MyCustomClass.
// The following call to ReadXml fails because MyCustomClass isn't in the allowed types list.
DataTable table = new DataTable("MyDataTable");
table.ReadXml(xmlReader);
// However, the following call to ReadXml succeeds, since the DataTable instance
// already defines a column of type MyCustomClass.
DataTable table = new DataTable("MyDataTable");
table.Columns.Add("MyColumn", typeof(MyCustomClass));
table.ReadXml(xmlReader); // this call will succeed
Les restrictions de type objet s’appliquent également lors de l’utilisation de XmlSerializer
pour désérialiser une instance de DataSet
ou DataTable
. Toutefois, ils peuvent ne pas s’appliquer lors de l’utilisation de BinaryFormatter
pour désérialiser une instance de DataSet
ou DataTable
.
Les restrictions de type objet ne s’appliquent pas lors de l’utilisation de DataAdapter.Fill
, par exemple lorsqu’une instance DataTable
est remplie directement à partir d’une base de données sans utiliser les API de désérialisation XML.
Étendre la liste des types autorisés
Une application peut étendre la liste des types autorisés pour inclure des types personnalisés en plus des types intégrés répertoriés ci-dessus. Si vous étendez la liste des types autorisés, la modification affecte toutes les instances DataSet
et DataTable
dans l’application. Les types ne peuvent pas être supprimés de la liste des types intégrés autorisés.
Étendre la configuration (.NET Framework 4.0 et versions ultérieures)
App.config permet d’étendre la liste des types autorisés. Pour étendre la liste des types autorisés :
- Utilisez l’élément
<configSections>
pour ajouter une référence à la section de configuration System.Data. - Utilisez
<system.data.dataset.serialization>
/<allowedTypes>
pour spécifier des types supplémentaires.
Chaque élément <add>
doit spécifier un seul type à l’aide de son nom de type qualifié d’assembly. Pour ajouter des types supplémentaires à la liste des types autorisés, utilisez plusieurs éléments <add>
.
L’exemple suivant montre l’extension de la liste des types autorisés en ajoutant le type personnalisé Fabrikam.CustomType
.
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<configSections>
<sectionGroup name="system.data.dataset.serialization" type="System.Data.SerializationSettingsSectionGroup, System.Data, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
<section name="allowedTypes" type="System.Data.AllowedTypesSectionHandler, System.Data, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089"/>
</sectionGroup>
</configSections>
<system.data.dataset.serialization>
<allowedTypes>
<!-- <add type="assembly qualified type name" /> -->
<add type="Fabrikam.CustomType, Fabrikam, Version=1.0.0.0, Culture=neutral, PublicKeyToken=2b3831f2f2b744f7" />
<!-- additional <add /> elements as needed -->
</allowedTypes>
</system.data.dataset.serialization>
</configuration>
Pour récupérer le nom qualifié d’assembly d’un type, utilisez la propriété Type.AssemblyQualifiedName, comme illustré dans le code suivant.
string assemblyQualifiedName = typeof(Fabrikam.CustomType).AssemblyQualifiedName;
Étendre la configuration (.NET Framework 2.0 - 3.5)
Si votre application cible .NET Framework 2.0 ou 3.5, vous pouvez toujours utiliser le mécanisme App.config ci-dessus pour étendre la liste des types autorisés. Toutefois, votre élément <configSections>
sera légèrement différent, comme illustré dans le code suivant :
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<configSections>
<!-- The below <sectionGroup> and <section> are specific to .NET Framework 2.0 and 3.5. -->
<sectionGroup name="system.data.dataset.serialization" type="System.Data.SerializationSettingsSectionGroup, System.Data, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
<section name="allowedTypes" type="System.Data.AllowedTypesSectionHandler, System.Data, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089"/>
</sectionGroup>
</configSections>
<system.data.dataset.serialization>
<allowedTypes>
<!-- <add /> elements, as demonstrated in the .NET Framework 4.0 - 4.8 sample code above. -->
</allowedTypes>
</system.data.dataset.serialization>
</configuration>
Étendre par programmation (.NET Framework, .NET Core, .NET 5+)
La liste des types autorisés peut également être étendue par programme à l’aide d’AppDomain.SetData avec la clé connue System.Data.DataSetDefaultAllowedTypes, comme illustré dans le code suivant.
Type[] extraAllowedTypes = new Type[]
{
typeof(Fabrikam.CustomType),
typeof(Contoso.AdditionalCustomType)
};
AppDomain.CurrentDomain.SetData("System.Data.DataSetDefaultAllowedTypes", extraAllowedTypes);
Si vous utilisez le mécanisme d’extension, la valeur associée à la clé System.Data.DataSetDefaultAllowedTypes doit être de type Type[]
.
Sur .NET Framework, la liste des types autorisés peut être étendue à la fois avec App.config et AppDomain.SetData
. Dans ce cas, DataSet
et DataTable
permettent à un objet d’être désérialisé dans le cadre des données si son type est présent dans l’une ou l’autre liste.
Exécuter une application en mode audit (.NET Framework)
Dans .NET Framework, DataSet
et DataTable
fournissent une fonctionnalité de mode audit. Lorsque le mode d’audit est activé, DataSet
et DataTable
comparent les types d’objets entrants par rapport à la liste des types autorisés. Toutefois, si un objet dont le type n’est pas autorisé est visible, une exception n’est pas levée. Au lieu de cela, DataSet
et DataTable
notifient les instances TraceListener
qu’un type suspect est présent, permettant à TraceListener
de consigner ces informations. Aucune exception n’est levée et l’opération de désérialisation se poursuit.
Avertissement
L’exécution d’une application en « mode audit » ne doit être qu’une mesure temporaire utilisée pour les tests. Lorsque le mode audit est activé, DataSet
et DataTable
n’appliquent pas de restrictions de type, ce qui peut introduire une faille de sécurité dans votre application. Pour plus d’informations, consultez les sections intitulées Suppression de toutes les restrictions de type et Sécurité relative aux entrées non approuvées.
Le mode audit peut être activé via App.config :
- Consultez Extension via la configuration du présent document pour plus d’informations sur la valeur appropriée à placer pour l’élément
<configSections>
. - Utilisez
<allowedTypes auditOnly="true">
pour activer le mode audit, comme indiqué dans le balisage suivant.
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<configSections>
<!-- See the section of this document titled "Extending through configuration" for the appropriate
<sectionGroup> and <section> elements to put here, depending on whether you're running .NET
Framework 2.0 - 3.5 or 4.0 - 4.8. -->
</configSections>
<system.data.dataset.serialization>
<allowedTypes auditOnly="true"> <!-- setting auditOnly="true" enables audit mode -->
<!-- Optional <add /> elements as needed. -->
</allowedTypes>
</system.data.dataset.serialization>
</configuration>
Une fois le mode d’audit activé, vous pouvez utiliser App.config pour connecter votre classe TraceListener
à la classe DataSet
TraceSource.
prédéfinie Le nom de la source de trace intégrée est System.Data.DataSet. L’exemple suivant illustre l’écriture d’événements de trace dans la console et dans un fichier journal sur le disque.
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<system.diagnostics>
<sources>
<source name="System.Data.DataSet"
switchType="System.Diagnostics.SourceSwitch"
switchValue="Warning">
<listeners>
<!-- write to the console -->
<add name="console"
type="System.Diagnostics.ConsoleTraceListener" />
<!-- *and* write to a log file on disk -->
<add name="filelog"
type="System.Diagnostics.TextWriterTraceListener"
initializeData="c:\logs\mylog.txt" />
</listeners>
</source>
</sources>
</system.diagnostics>
</configuration>
Pour plus d’informations sur TraceSource
et TraceListener
, consultez le document Guide pratique : Utiliser des TraceSource et des filtres avec des écouteurs de trace.
Notes
L’exécution d’une application en mode audit n’est pas disponible ni dans .NET Core, ni dans .NET 5 et versions ultérieures.
Supprimer toutes les restrictions de type
Si une application doit supprimer toutes les restrictions de limitation de type de DataSet
et DataTable
:
- Il existe plusieurs options pour supprimer les restrictions de limitation de type.
- Les options disponibles dépendent de l’infrastructure cible de l’application.
Avertissement
La suppression de toutes les restrictions de type peut introduire une faille de sécurité à l’intérieur de l’application. Lorsque vous utilisez ce mécanisme, vérifiez que l’application n’utilise pasDataSet
ou DataTable
pour lire une entrée non approuvée. Pour plus d’informations, consultez CVE-2020-1147 et la section suivante intitulée Sécurité relative aux entrées non approuvées.
Via la configuration AppContext (.NET Framework 4.6 et versions ultérieures, .NET Core 2.1 et versions ultérieures, .NET 5 et versions ultérieures)
Le commutateur AppContext
, Switch.System.Data.AllowArbitraryDataSetTypeInstantiation
, lorsqu’il est défini sur true
supprime toutes les restrictions de limitation de DataSet
et de DataTable
.
Dans .NET Framework, ce commutateur peut être activé via App.config, comme indiqué dans la configuration suivante :
<configuration>
<runtime>
<!-- Warning: setting the following switch can introduce a security problem. -->
<AppContextSwitchOverrides value="Switch.System.Data.AllowArbitraryDataSetTypeInstantiation=true" />
</runtime>
</configuration>
Dans ASP.NET, l’élément <AppContextSwitchOverrides>
n’est pas disponible. Au lieu de cela, le commutateur peut être activé via Web.config, comme indiqué dans la configuration suivante :
<configuration>
<appSettings>
<!-- Warning: setting the following switch can introduce a security problem. -->
<add key="AppContext.SetSwitch:Switch.System.Data.AllowArbitraryDataSetTypeInstantiation" value="true" />
</appSettings>
</configuration>
Pour plus d’informations, consultez l’élément <AppContextSwitchOverrides>.
Dans .NET Core, .NET 5 et ASP.NET Core, ce paramètre est contrôlé par runtimeconfig.json, comme indiqué dans le code JSON suivant :
{
"runtimeOptions": {
"configProperties": {
"Switch.System.Data.AllowArbitraryDataSetTypeInstantiation": true
}
}
}
Pour plus d’informations, consultez Paramètres de configuration d’exécution .NET Core.
AllowArbitraryDataSetTypeInstantiation
peut également être défini par voie de programme via AppContext.SetSwitch, ce qui évite d’utiliser un fichier de configuration, comme indiqué dans le code suivant :
// Warning: setting the following switch can introduce a security problem.
AppContext.SetSwitch("Switch.System.Data.AllowArbitraryDataSetTypeInstantiation", true);
Si vous choisissez l’approche programmatique précédente, l’appel à AppContext.SetSwitch
doit se produire au début du démarrage des applications.
Via le registre à l’échelle de l’ordinateur (.NET Framework 2.0 - 4.x)
Si AppContext
n’est pas disponible, les vérifications de limitation de type peuvent être désactivées avec le Registre Windows :
- Un administrateur doit configurer le Registre.
- L’utilisation du Registre est une modification à l’échelle de l’ordinateur et affecte toutes les applications s’exécutant sur l’ordinateur.
Type | Valeur |
---|---|
Clé du Registre | HKLM\SOFTWARE\Microsoft\.NETFramework\AppContext |
Nom de la valeur | Switch.System.Data.AllowArbitraryDataSetTypeInstantiation |
Type de valeur | REG_SZ |
Données de valeur | true |
Sur un système d’exploitation 64 bits, cette valeur doit être ajoutée pour la clé 64 bits (indiquée ci-dessus) et la clé 32 bits. La clé 32 bits réside dans HKLM\SOFTWARE\WOW6432Node\Microsoft\.NETFramework\AppContext
.
Pour plus d’informations sur l’utilisation du Registre pour configurer AppContext
, consultez « AppContext pour les consommateurs de bibliothèque ».
Sécurité relative aux entrées non approuvées
Bien que DataSet
et DataTable
imposent des limitations par défaut sur les types autorisés à être présents lors de la désérialisation des charges utiles XML, DataSet
et DataTable
ne sont généralement pas sécurisés lorsqu’ils sont remplis avec une entrée non approuvée. Voici la liste non exhaustive des façons dont une instance DataSet
ou DataTable
peut lire une entrée non approuvée.
- Une instance
DataAdapter
fait référence à une base de données, et la méthodeDataAdapter.Fill
est utilisée pour remplir une méthodeDataSet
avec le contenu d’une requête de base de données. - La méthode
DataSet.ReadXml
ouDataTable.ReadXml
permet de lire un fichier XML contenant des informations de colonne et de ligne. - Une instance
DataSet
ouDataTable
est sérialisée dans le cadre d’un service web ASP.NET (SOAP) ou d’un point de terminaison WCF. - Un sérialiseur tel que
XmlSerializer
permet de désérialiser une instanceDataSet
ouDataTable
à partir d’un flux XML. - Un sérialiseur tel que
JsonConvert
est utilisé pour désérialiser une instanceDataSet
ouDataTable
d’un flux JSON.JsonConvert
est une méthode de la bibliothèque Newtonsoft.Json tierce prisée des développeurs. - Un sérialiseur tel que
BinaryFormatter
permet de désérialiser une instanceDataSet
ouDataTable
à partir d’un flux d’octets brut.
Ce document traite des considérations relatives à la sécurité pour les scénarios précédents.
Utilisez DataAdapter.Fill
pour remplir une instance DataSet
à partir d’une source de données non approuvée
Une instance DataSet
peut être remplie à partir d’une instance DataAdapter
à l’aide de la méthode DataAdapter.Fill
, comme illustré dans l’exemple suivant.
// Assumes that connection is a valid SqlConnection object.
string queryString =
"SELECT CustomerID, CompanyName FROM dbo.Customers";
SqlDataAdapter adapter = new SqlDataAdapter(queryString, connection);
DataSet customers = new DataSet();
adapter.Fill(customers, "Customers");
(L’exemple de code ci-dessus fait partie d’un plus grand exemple proposé par Remplissage d’un DataSet à partir d’un DataAdapter.)
La plupart des applications peuvent simplifier et supposer que leur couche de base de données est approuvée. Toutefois, si vous avez l’habitude de modéliser vos applications contre les menaces, votre modèle de menace peut considérer qu’il existe une limite d’approbation entre l’application (client) et la couche de base de données (serveur). L’utilisation de l’authentification mutuelle ou de l’authentification AAD entre le client et le serveur est un moyen d’aider à résoudre les risques associés à ce problème. Le reste de cette section décrit le résultat possible d’une connexion d’un client à un serveur non approuvé.
Les conséquences du pointage d’une instance DataAdapter
à une source de données non approuvée dépendent de l’implémentation de l’instance DataAdapter
elle-même.
SqlDataAdapter
Pour le type intégré SqlDataAdapter, le référencement d’une source de données non approuvée peut entraîner une attaque par déni de service (DoS). L’attaque DoS peut entraîner un blocage ou une absence de réponse de l’application. Si un attaquant peut planter une DLL en même temps que l’application, il peut également exécuter du code local.
Autres types DataAdapter
Les implémentations tierces DataAdapter
doivent effectuer leurs propres évaluations sur les garanties de sécurité qu’elles fournissent face aux entrées non approuvées. .NET ne peut pas garantir la sécurité concernant ces implémentations.
DataSet.ReadXml et DataTable.ReadXml
Les méthodes DataSet.ReadXml
et DataTable.ReadXml
ne sont pas sécurisées lorsqu’elles sont utilisées avec une entrée non approuvée. Nous recommandons vivement aux consommateurs d’utiliser l’une des alternatives décrites plus loin dans ce document.
Les implémentations de DataSet.ReadXml
et DataTable.ReadXml
ont été créées à l’origine avant que les vulnérabilités de sérialisation ne soient une catégorie de menace bien comprise. Par conséquent, le code ne suit pas les meilleures pratiques de sécurité actuelles. Ces API peuvent être utilisées comme vecteurs pour que les attaquants effectuent des attaques DoS contre des applications web. Ces attaques peuvent entraîner l’absence de réponse du service web ou la fin inattendue du processus. L’infrastructure ne fournit pas de mesures d’atténuation pour ces catégories d’attaques et .NET considère ce comportement comme étant le comportement « par défaut ».
.NET a publié des mises à jour de sécurité pour atténuer certains problèmes tels que la divulgation d’informations ou l’exécution de code à distance dans DataSet.ReadXml
et DataTable.ReadXml
. Les mises à jour de sécurité .NET peuvent ne pas fournir une protection complète contre ces catégories de menaces. Les consommateurs doivent évaluer leurs scénarios individuels et considérer leur exposition potentielle à ces risques.
Les consommateurs doivent savoir que les mises à jour de sécurité apportées à ces API peuvent avoir un impact sur la compatibilité des applications dans certaines situations. En outre, il est possible qu’une nouvelle vulnérabilité soit découverte dans ces API, pour laquelle .NET ne peut pratiquement pas publier de mise à jour de sécurité.
Nous recommandons aux consommateurs de ces API ce qui suit :
- Envisager d’utiliser l’une des alternatives décrites plus loin dans ce document.
- Effectuer des évaluations individuelles des risques sur leurs applications.
Il est de la seule responsabilité du consommateur de déterminer s’il doit utiliser ces API. Les consommateurs doivent évaluer les risques de sécurité, techniques et juridiques, y compris les exigences réglementaires, qui peuvent accompagner l’utilisation de ces API.
DataSet et DataTable via les services web ASP.NET ou WCF
Il est possible d’accepter une instance DataSet
ou DataTable
dans un service web ASP.NET (SOAP), comme illustré dans le code suivant :
using System.Data;
using System.Web.Services;
[WebService(Namespace = "http://contoso.com/")]
public class MyService : WebService
{
[WebMethod]
public string MyWebMethod(DataTable dataTable)
{
/* Web method implementation. */
}
}
Il n’est pas possible d’accepter DataSet
ou DataTable
directement en tant que paramètre, mais plutôt de l’accepter dans le graphique d’objet sérialisé SOAP global, comme indiqué dans le code suivant :
using System.Data;
using System.Web.Services;
[WebService(Namespace = "http://contoso.com/")]
public class MyService : WebService
{
[WebMethod]
public string MyWebMethod(MyClass data)
{
/* Web method implementation. */
}
}
public class MyClass
{
// Property of type DataTable, automatically serialized and
// deserialized as part of the overall MyClass payload.
public DataTable MyDataTable { get; set; }
}
Ou, à l’aide de WCF au lieu des services web ASP.NET :
using System.Data;
using System.ServiceModel;
[ServiceContract(Namespace = "http://contoso.com/")]
public interface IMyContract
{
[OperationContract]
string MyMethod(DataTable dataTable);
[OperationContract]
string MyOtherMethod(MyClass data);
}
public class MyClass
{
// Property of type DataTable, automatically serialized and
// deserialized as part of the overall MyClass payload.
public DataTable MyDataTable { get; set; }
}
Dans tous ces cas, le modèle de menace et les garanties de sécurité sont identiques à la section DataSet.ReadXml et DataTable.ReadXml.
Désérialiser un DataSet ou DataTable via XmlSerializer
Les développeurs peuvent utiliser XmlSerializer
pour désérialiser les instances DataSet
et DataTable
, comme illustré dans le code suivant :
using System.Data;
using System.IO;
using System.Xml.Serialization;
public DataSet PerformDeserialization1(Stream stream) {
XmlSerializer serializer = new XmlSerializer(typeof(DataSet));
return (DataSet)serializer.Deserialize(stream);
}
public MyClass PerformDeserialization2(Stream stream) {
XmlSerializer serializer = new XmlSerializer(typeof(MyClass));
return (MyClass)serializer.Deserialize(stream);
}
public class MyClass
{
// Property of type DataTable, automatically serialized and
// deserialized as part of the overall MyClass payload.
public DataTable MyDataTable { get; set; }
}
Dans ce cas, le modèle de menace et les garanties de sécurité sont identiques au contenu de la section DataSet.ReadXml et DataTable.ReadXml
Désérialiser un DataSet ou DataTable via JsonConvert
La bibliothèque Newtonsoft tierce populaire Json.NET permet de désérialiser les instances DataSet
et DataTable
, comme indiqué dans le code suivant :
using System.Data;
using Newtonsoft.Json;
public DataSet PerformDeserialization1(string json) {
return JsonConvert.DeserializeObject<DataSet>(data);
}
public MyClass PerformDeserialization2(string json) {
return JsonConvert.DeserializeObject<MyClass>(data);
}
public class MyClass
{
// Property of type DataTable, automatically serialized and
// deserialized as part of the overall MyClass payload.
public DataTable MyDataTable { get; set; }
}
La désérialisation de DataSet
ou de DataTable
de cette façon à partir d’un objet blob JSON non approuvé n’est pas sécurisé. Ce modèle est vulnérable à une attaque par déni de service. Une telle attaque peut bloquer l’application ou inactiver sa réactivité.
Notes
Microsoft ne garantit pas ou ne prend pas en charge l’implémentation de bibliothèques tierces telles que Newtonsoft.Json. Ces informations sont fournies pour être complètes et précises à compter du moment de la rédaction de ce texte.
Désérialiser un DataSet ou DataTable via BinaryFormatter
Vous ne devez jamais utiliser BinaryFormatter
, NetDataContractSerializer
, SoapFormatter
ou de formateurs unsafe connexes pour désérialiser une instance de DataSet
ou DataTable
à partir d’une charge utile non approuvée :
- Cela expose potentiellement à une attaque complète d’exécution de code à distance.
- L’utilisation de
SerializationBinder
n’est pas suffisante pour empêcher une telle attaque.
Remplacements sécurisés
Pour les applications qui :
- Acceptent
DataSet
ouDataTable
via un point de terminaison SOAP .asmx ou un point de terminaison WCF. - Désérialisent des données non approuvées dans une instance de
DataSet
ouDataTable
.
Envisagez de remplacer le modèle objet pour utiliser Entity Framework. Entity Framework :
- Est une infrastructure riche et moderne orientée objet qui peut représenter des données relationnelles.
- Apporte un écosystème diversifié de fournisseurs de base de données pour faciliter le projet de requêtes de base de données via vos modèles objet Entity Framework.
- Offre des protections intégrées lors de la désérialisation des données provenant de sources non approuvées.
Pour les applications qui utilisent des points de terminaison SOAP .aspx
, envisagez de modifier ces points de terminaison pour utiliser WCF. WCF est un remplacement plus complet pour les services web .asmx
. Les points de terminaison WCF peuvent être exposés via SOAP pour la compatibilité avec les appelants existants.
Analyseurs de code
Les règles de sécurité de l’analyseur de code, qui s’exécutent lorsque votre code source est compilé, peuvent vous aider à trouver des vulnérabilités liées à ce problème de sécurité dans le code C# et Visual Basic. Microsoft.CodeAnalysis.FxCopAnalyzers est un package NuGet d’analyseurs de code distribués sur nuget.org.
Pour obtenir une vue d’ensemble des analyseurs de code, consultez Vue d’ensemble des analyseurs de code source.
Activez les règles Microsoft.CodeAnalysis.FxCopAnalyzers suivantes :
- CA2350 : Ne pas utiliser DataTable.ReadXml() avec des données non approuvées
- CA2351 : Ne pas utiliser DataSet.ReadXml() avec des données non fiables
- CA2352 : Un jeu de données ou une table de données non sécurisé(e) dans un type sérialisable peut être vulnérable aux attaques par exécution de code à distance
- CA2353 : Jeu de données ou table de données non sécurisé(e) dans un type sérialisable
- CA2354 : Un jeu de données ou une table de données non sécurisé(e) dans un graphe d’objets désérialisé peut être vulnérable à une attaque par exécution de code à distance
- CA2355 : Type DataSet ou DataTable non sécurisé trouvé dans le graphe d’objets désérialisable
- CA2356 : Type DataSet ou DataTable non sécurisé trouvé dans un graphe d’objets désérialisable web
- CA2361 : Vérifier que la classe générée automatiquement contenant DataSet.ReadXml() n’est pas utilisée avec des données non fiables
- CA2362 : Un jeu de données ou une table de données non sécurisé dans un type sérialisable généré automatiquement peut être vulnérable aux attaques par exécution de code à distance
Pour plus d’informations sur la configuration des règles, consultez Utiliser des analyseurs de code.
Les nouvelles règles de sécurité sont disponibles dans les packages NuGet suivants :
- Microsoft.CodeAnalysis.FxCopAnalyzers 3.3.0 : pour Visual Studio 2019 version 16.3 ou ultérieure
- Microsoft.CodeAnalysis.FxCopAnalyzers 2.9.11 : pour Visual Studio 2017 version 15.9 ou ultérieure